From 643b9094cd80e896f0179c0550cf8476b24074d2 Mon Sep 17 00:00:00 2001 From: argszero Date: Sat, 12 Sep 2026 00:57:57 +0800 Subject: [PATCH] fix(ui): restore data-label coverage and colspan parity in the admin models table MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit `renderAdminModels()` was the only one of the seven table renderers that violated the interface conventions documented in `ui/README.md`, in two ways at once (both introduced by the same commit that created the table, 98a7a9b): 1. `data-label` coverage was 1 of 8 cells. Under `@media (max-width:560px)` the thead is hidden and each row is rendered as a card via `td::before { content: attr(data-label) }`, so seven of the eight fields were displayed without any label. The other six renderers are complete (mk-body 7/7, share-body 8/8, api-keys 6/6, emp-body 7/7, dept-body 7/7, ops-body 4/4). Added the seven missing labels as literal strings, matching the existing convention used by the other renderers (they are all literal rather than i18n-driven). 2. The empty and error rows used `colspan=7` against an eight-column table (the 读图 column has existed since the table was created), so the cell under-covered the table: measured in Chrome at 1400px the cell was 984px of a 1044px table, leaving a 60px gap. Both rows now use `colspan=8`. Bumped the asset cache-bust to 20260911-7. Verified in a headless Chrome A/B harness, with both the baseline and the fixed tree produced by the same generator (baseline rebuilt from git HEAD): card mode @<=560px goes from 1/8 to 8/8 labelled cells over the same seven identity-keyed cells, while desktop keeps the thead rendered; the desktop error row goes from 94.3% to 100% of the table width. Mobile card mode is unaffected by the colspan change (thead hidden -> block layout). --- ui/index.html | 10 +++++----- ui/js/app.js | 18 +++++++++--------- 2 files changed, 14 insertions(+), 14 deletions(-) diff --git a/ui/index.html b/ui/index.html index 96b04b7..bf82a35 100644 --- a/ui/index.html +++ b/ui/index.html @@ -5,7 +5,7 @@ AITokenPool - + @@ -842,9 +842,9 @@

使用模型

- - - - + + + + diff --git a/ui/js/app.js b/ui/js/app.js index 85146b0..288aaaa 100644 --- a/ui/js/app.js +++ b/ui/js/app.js @@ -2232,7 +2232,7 @@ // 模型搜索过滤 + 表格渲染(数据来自 /api/admin/models;零 mock:加载失败 → 空态 + 重试) function renderAdminModels() { if (!Live.adminModels) { - $("#model-body").innerHTML = loadErrorRow(7, T("admin.models.loadFail"), T("err.loadFail")); + $("#model-body").innerHTML = loadErrorRow(8, T("admin.models.loadFail"), T("err.loadFail")); pulseTbody($("#model-body")); return; } @@ -2241,16 +2241,16 @@ const list = Live.adminModels.filter((m) => !q || (m.provider || "").toLowerCase().includes(q) || (m.model || "").toLowerCase().includes(q)); $("#model-body").innerHTML = list.length ? list.map((m, i) => - "" + esc(m.provider) + "" + - "" + esc(m.model) + "" + - '' + D.fmt(m.input_per_m || 0) + "" + - '' + D.fmt(m.output_per_m || 0) + "" + - '' + fmtCtx(m.context_length || m.context_window || 0) + "" + - '' + fmtCtx(m.max_output || 0) + "" + - "" + (m.vision ? '' + T("admin.models.vision.yes") + "" : '' + T("admin.models.vision.no") + "") + "" + + "" + esc(m.provider) + "" + + "" + esc(m.model) + "" + + '' + D.fmt(m.input_per_m || 0) + "" + + '' + D.fmt(m.output_per_m || 0) + "" + + '' + fmtCtx(m.context_length || m.context_window || 0) + "" + + '' + fmtCtx(m.max_output || 0) + "" + + "" + (m.vision ? '' + T("admin.models.vision.yes") + "" : '' + T("admin.models.vision.no") + "") + "" + " " + "" - ).join("") : emptyRow(7, T("admin.models.empty"), T("admin.models.empty.sub")); + ).join("") : emptyRow(8, T("admin.models.empty"), T("admin.models.empty.sub")); pulseTbody($("#model-body")); }