feat(web): retheme every surface on shared design tokens (AGT-4201) - #558
Merged
Conversation
One token vocabulary (tokens.css) now paints all seven pages — cockpit, chat, orchestration, threads, warehouse, and the two server-rendered legacy pages — with a light theme as a value swap under [data-theme="light"] stamped by themeBoot.js before first paint, and a toggle on every page. shell.css carries the shared primitives: topbar, buttons, inputs, chips, badges, focus ring, empty/status lines, in-page confirm card, reduced-motion. Chat gets the guideline's composer (autogrow textarea, Enter sends / Shift+Enter newline / IME-safe, empty-disabled, in-place sending state, draft persistence, labelled attachment chips, drop overlay) and stream following (80px slack, "↓ Latest" button, one live-region announcement per batch). Threads' resolve and the warehouse's overwrite ask in the page, naming the target. Role/kind/status colours in the JS colour maps are token references, so the SVG graph re-paints with the theme. tests/web/tokens.test.ts is the gate: every var() resolves, no hex literal outside tokens.css, no inline <style> in a shell, every shell links tokens+shell+themeBoot in order and shares one nav, every icon-only button has a name. The brand font (Inter, latin subset) is vendored with its OFL licence.
…/typecheck 10 minutes Two consecutive Lint runs on this branch sat silent for the full five minutes inside `npm ci` — after the reify warnings, before any output — and were cancelled by the job timeout, while the same lockfile installs in ~20 s on main. Nothing in package.json or the lockfile changed. The one network call `npm ci` makes after install is the audit report, and it has no timeout of its own, so a slow audit endpoint stalls the whole job. `--no-audit --no-fund` removes that dependency and `--prefer-offline` uses the restored cache first; the wider timeouts keep a genuinely slow runner from failing the gate.
Merged
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What
The web surface (cockpit, chat, orchestration, threads, warehouse, and the two server-rendered legacy pages
/and/issues) now draws from one token vocabulary (web/static/css/tokens.css), ported from the chat-ui agent guideline's §8.1 vocabulary to this vanilla ESM stack.--bg-app/--bg-surface/…,--fg-*, accent/danger/warning/success, radius, 4pt spacing, type scale, motion, z-index, code + chart + role colours). Light theme is a value swap under[data-theme="light"], stamped bythemeBoot.jsbefore first paint;theme.mjsowns the toggle (persisted, follows the OS until a choice is made,aria-pressed+ a label naming the mode it switches to). Every page has the toggle..btnfamily, inputs, chips, badges, cards, status lines, empty state, scroll-to-latest, in-page confirm card, drop overlay,:focus-visiblering (neveroutline:nonealone),prefers-reduced-motionkill,.sr-only.composer.mjs— autogrow textarea (≤40vh), Enter sends / Shift+Enter newline /isComposing+229 guard, Send disabled on empty, in-place "Sending…" witharia-busy, draft persistence, labelled chip-remove buttons, drop overlay.scrollFollow.mjs— 80px slack, "↓ Latest" (with unseen count), one live-region announcement per batch. Loading / empty / unreachable states.window.confirm); warehouse overwrite arms on first click naming the file.ROLE_COLORS,KIND_COLORS,statusColor()are token references; SVG paints go throughpaint()(attribute + inline style) so the graph re-paints with the theme.dashboardHtml.ts/issueBoardHtml.tskeep their inline stylesheets (their scripts are asserted by name in tests) but their:rootblocks are now aliases into tokens.css; all 34 hex literals removed; brand font applied.Gate
tests/web/tokens.test.tsenforces the guideline permanently: everyvar()resolves; no hex literal outside tokens.css; no inline<style>in a shell; every shell links tokens+shell+themeBoot in order and shares one nav; every icon-only button hasaria-label; legacy pages link tokens, boot the theme, offer a toggle, and carry no colour literal.New unit tests:
composer.test.ts,scrollFollow.test.ts,theme.test.ts, plus a two-step resolve case inthreadBoard.test.ts.Verification
npm run typecheck✓ ·npm run lint✓ (one pre-existing warning in vega adapter test) ·LC_ALL=C npx vitest run→ 5524 passed, 10 skipped (398 files)chatView.test.ts,orchestrationView.test.ts,threadBoard.test.ts) unchanged and green.Guideline §12 self-check