4.9 KiB
Task 02b — Wire the token layer in
Agent: design-system-keeper · Model: agy (Gemini 3.1 Pro — needs
vision for the screenshot diffs) Depends on: 02 · Blocks: 02c
Worktree: .agents/scripts/worktree.sh start 02b token-layer-wiring
Why this task exists
Task 02 built the token layer and it was never connected to anything. This is
not a criticism of that task — its brief and its done-when list never asked for
the wiring, and check-tokens.mjs only looks for violations in src/, so
nothing could have caught it.
Verify each of these yourself before you start; do not take my word for it:
src/styles/tokens.cssis imported by nothing. The only reference in the repo issrc/styles/base.css:2, andbase.cssis itself imported nowhere. The whole layer is dead code.- The pages import the legacy stylesheets instead, drifted
:rootblocks and all:src/layouts/ChapterLayout.astro:16→../../chapters.css?urlsrc/pages/skills.astro:11→../../skills/styles.css?urlsrc/pages/skills-review.astro:4,5→skills-review/styles.css,change-lens.css
- So task 02's
--bluedecision never reached a page. It chose#527f9fand wrote it down. The built CSS today ships both values:dist/_astro/chapters.*.css --blue:#215675 dist/_astro/rules.*.css --blue: #527f9f dist/_astro/styles.*.css --blue:#215675
Scope
src/styles/tokens.css, src/styles/base.css,
.agents/scripts/check-tokens.mjs — you are the only writer of these — plus the
four import sites listed above and whatever layout work the wiring needs.
Deliver
1. One loaded token layer
Make tokens.css actually load on every route. Either fix base.css and import
it from the layouts, or drop base.css and import tokens.css directly — your
call, but say which and why. A file that exists and is never loaded is worse
than no file, because it reads as done.
2. The legacy stylesheet imports reconciled
Those three ?url imports are how the drifted palettes reach production. You do
not have to delete them in this task — much of that CSS is still load-bearing
until task 15e and task 20 — but the :root blocks inside them must stop
overriding the canonical tokens. Make the layer authoritative and prove with
screenshots that nothing moved except what you intend.
--blue is the one real difference: #527f9f vs #215675 is visible. Task 02
already decided #527f9f. Apply that decision; do not re-open it. If applying
it looks wrong on a real page, screenshot it and escalate rather than quietly
picking the other value.
3. Font tokens
Manrope and DM Mono are real now — self-hosted in public/fonts/, wired
through public/fonts/fonts.css (linked by BaseLayout.astro, @imported by
the legacy root styles.css). Read .agents/context/design-system.md; the old
"delete the dead rule, fall back to Arial" instruction is superseded and must
not be re-applied.
Add --font-sans and --font-mono and point the stacks at them. Do not touch
public/fonts/fonts.css itself, and do not remove the faces.
4. A check so this cannot recur
The gap that let a dead token layer ship is that nothing asserts the tokens are
loaded. Add that check — a build-output assertion that every route resolves
the canonical palette, or an equivalent. Put it in check-tokens.mjs, which you
own. Do not touch scripts/verify.mjs; it stays at 42 assertions and only
the verification-engineer may change it.
Screenshots: your baseline is HEAD, not history
The self-hosted fonts landed in 7f11b6e and changed how every page
renders, deliberately — that is the one sanctioned visual change in this
migration. Any screenshot taken before it shows Arial and is not a valid
baseline. Capture your own "before" from HEAD at the start of this task.
Widths: 560 / 800 / 1100 / 1600, plus the eight breakpoints task 02 removed (520, 530, 600, 620, 720, 850, 880, 900) — that is where regressions hide.
Do not
- Do not resolve the ~164
token-gap:markers. That is task 02c, and doing it here would collide with task 15d's page work. Report the count. - Do not delete
responsive.css. That is 15e. - Do not convert the
gap:1pxover a coloured parent trick intoborder— it is deliberate house style and appears everywhere. - Do not rename tokens to numeric scales (
--color-neutral-900). - Never use
--no-verify; never setcore.hooksPath.
Done when
tokens.cssloads on every route, proven from built output- One value per token in the shipped CSS —
--blueis#527f9feverywhere --font-sans/--font-monoexist and are used; the faces still load- A check exists that fails if the token layer stops being loaded
- Before/after screenshots at all twelve widths, every difference explained
pnpm run gategreen — the full gate; 42 assertions intact