Skip to content

Add #582 source-CSS audit gates (D1–D6) - #584

Merged
jackgranatowski merged 6 commits into
mainfrom
claude/issue-582-opchuq
Jul 9, 2026
Merged

Add #582 source-CSS audit gates (D1–D6)#584
jackgranatowski merged 6 commits into
mainfrom
claude/issue-582-opchuq

Conversation

@jackgranatowski

@jackgranatowski jackgranatowski commented Jul 9, 2026

Copy link
Copy Markdown
Contributor

Implements the six CI gates from #582 to enforce consistency between token declarations, annotations, and framework consumption. These gates prevent silent failures and documentation drift by mechanically verifying:

New audit scripts:

  • check-dead-knobs.js (D1): Fails if an annotation claims a token is "wired" (e.g. "Maps to @page margin") but no rule actually consumes it
  • check-annotations.js (D2): Fails if a ~Nms or ~Npx figure in token annotations disagrees with the token's resolved value
  • check-mirrors.js (D4): Verifies three families of hand-maintained mirrors stay in sync:
    • @Property initial-values ↔ :root declarations (char-for-char)
    • Container-query re-derivations in .sf-fluid-cq > * match their base formulas
    • Dark-source @Property values match SL-001 oklch clamp() derivations from light values
  • check-hook-tokens.js (D5): Enforces the fallback-only hook-token policy — undeclared tokens consumed only via var(--sf-hook, <default>) must be listed in scripts/hook-tokens.js and documented in docs/llm-guide.md
  • check-bundle-defs.js (D6): Fails if a bundle consumes a token (without fallback) that it never declares

Supporting changes:

  • scripts/hook-tokens.js: Canonical list of fallback-only hook tokens (--sf-color-code-block-bg, --sf-color-code-block-text, --sf-overlap-host-pad) with documentation
  • scripts/lib/parse.js: Enhanced with stripComments() helper for CSS parsing
  • check-llm-guide.js: Updated to recognize hook tokens as live (D5) and tighten declaration detection to exclude bare consumption (D3)
  • tests/check-source-audit-gates.test.js: Comprehensive negative tests confirming each gate still fails on its specific defect

Documentation & annotation fixes:

  • Fixed --sf-duration-instant annotation: ~50ms → ~100ms (matches actual calc(100ms * var(--sf-motion-scale)))
  • Fixed --sf-duration-fast annotation: ~100ms → ~150ms (matches actual calc(150ms * var(--sf-motion-scale)))
  • Fixed --sf-duration-normal annotation: ~200ms → ~300ms
  • Fixed --sf-duration-slow annotation: ~350ms → ~500ms
  • Updated --sf-field-padding-inline default from var(--sf-space-l) to var(--sf-space-xs) in token-index
  • Added clarifying comments to core/tokens.css, core/print.css, optional/forms.css, optional/components.css, and optional/tokens.components.css explaining fallback patterns and override hooks

CI integration:

  • Added five new npm run check:* commands to package.json
  • Integrated all gates into .github/workflows/ci.yml after the existing token checks

All gates are designed to be conservative (hard-fail only on unambiguous violations, warn on edge cases) and support SLASHED_ROOT environment variable for testing against fixture trees.

https://claude.ai/code/session_012i9DDskbZqmuMeDwQMjPjF

Summary by CodeRabbit

  • New Features

    • Updated button and form sizing so controls now follow a clearer size scale, with touch targets staying accessible.
    • Added configurable print page size and margins for more predictable PDF output.
  • Bug Fixes

    • Improved consistency across size, spacing, and motion token references.
    • Refined heading and long-text wrapping behavior for better layout stability.
  • Documentation

    • Expanded design-token and migration docs to reflect the latest sizing and touch-target guidance.

Address every verified finding from the source-CSS audit in one pass:
wire the dead knobs render-safely, correct annotation/doc drift, document
the intentional architecture, and add five CI gates that stop the whole
class of defects from recurring.

Workstream A — wire dead knobs (zero render change; every var() fallback
equals today's literal):
- core/print.css @page now reads --sf-print-page-size / -margin (verified
  in Chromium that var() is honoured inside @page descriptors; a new
  Chromium-only e2e asserts an override reaches the page box).
- optional/forms.css field metrics resolve through --sf-field-padding-block
  / -inline / --sf-field-radius, then the core --sf-field-block rhythm knob,
  then the literal. --sf-field-block's :root default is unified to space-xs
  to match the shipped field padding so wiring changes nothing.

Workstream B/C — docs & comments:
- Fix annotation drift caught by the new value gate: the whole duration
  scale (fast 150ms, normal 250ms, slow 400ms), size-s (32px), size-m
  (~40px, not "default for buttons/inputs"), size-xl (56px), instant 100ms.
- architecture.md --sf-blur-* → --sf-blur; motion.md → --sf-color-primary-
  source-light; llm-guide.md --sf-field-block default.
- Comment the @Property initial-value ≠ :root default (and its effect on
  fallbacks), the deliberate .sf-btn min-height ladder offset, and the
  .sf-h* / core heading mirror (adds overflow-wrap; margins intentionally
  not reset).

Workstream D — new CI gates (+ negative tests):
- check:dead-knobs — an annotation that promises wiring ("Maps to …") must
  have a real consumer.
- check:annotations — ~Nms/~Npx prose must match the resolved token value.
- check:hook-tokens — the fallback-only hook tokens (new scripts/hook-tokens.js)
  are undeclared, consumed with a fallback, and documented; no new hook escapes.
- check:mirrors — @Property↔:root char mirrors, 21 container-query
  re-derivations, and 10 SL-001 dark derivations stay in sync.
- check:bundle-defs — every no-fallback token consumption ships its
  definition in the same bundle.
- check-llm-guide now counts only declarations (not consumption) and allows
  the documented hook tokens (D3/D5).

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_012i9DDskbZqmuMeDwQMjPjF
@qodo-code-review

Copy link
Copy Markdown

ⓘ Qodo reviews are paused because your trial has ended. Ask your workspace admin to add credits to resume reviews. Manage billing

@coderabbitai

coderabbitai Bot commented Jul 9, 2026

Copy link
Copy Markdown

Review Change Stack

Warning

Review limit reached

@jackgranatowski, you've reached your PR review limit, so we couldn't start this review.

Next review available in: 31 minutes

Enable usage-based reviews in Billing to review now. Otherwise, wait until the next included review is available.
You're only billed for reviews past your plan's rate limits ($0.25/file).

How can I continue?

After more reviews become available, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews.

How do review limits work?

CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability.

For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window.

Please refer docs for additional details.

Review details
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro Plus

Run ID: 5f464565-e187-46bf-8bf9-8825d4e46f65

📥 Commits

Reviewing files that changed from the base of the PR and between aa11767 and d6bd963.

📒 Files selected for processing (3)
  • docs/migration.md
  • scripts/check-annotations.js
  • scripts/check-dead-knobs.js
📝 Walkthrough

Walkthrough

This PR decouples --sf-touch-target (now a fixed 2.75rem), --sf-size-l (now 3rem), and --sf-field-block (now uses --sf-space-xs) from prior aliasing relationships, updates print page sizing to use CSS variables, remaps .sf-btn min-height to --sf-size-*, regenerates docs/token catalogs, and adds five new Node.js CI audit gate scripts (dead-knobs, annotations, hook-tokens, mirrors, bundle-defs) with supporting tests and CI wiring.

Changes

Token Decoupling

Layer / File(s) Summary
Core token value changes
core/tokens.css
--sf-size-l changes to 3rem, --sf-touch-target becomes a fixed 2.75rem, --sf-field-block uses --sf-space-xs, with expanded @property documentation.
Print page size/margin tokenization
core/print.css, tests/print.spec.js
@page size/margin now read from --sf-print-page-size/-margin with fallbacks; new Playwright test verifies default and overridden PDF dimensions.
Button/form component wiring
optional/components.css, optional/forms.css, optional/tokens.components.css, optional/utilities.css, docs/components.md, tests/button.spec.js, tests/a11y-patterns.spec.js
.sf-btn min-height maps onto --sf-size-* instead of --sf-touch-target; field padding/radius fallbacks added; new tests validate the size ladder and touch-target independence.
Generated token catalogs and demos
configurator/src/data/api-index.generated.json, docs/api-index.*, docs/token-index.*, docs/tokens.md, docs/token-annotations.json, demos/*
Generated docs/catalogs and demo files reflect the updated token values, roles, and counts.
Narrative documentation
docs/llm-guide.md, docs/migration.md, docs/architecture.md, docs/motion.md
Guide, migration, architecture, and motion docs updated to describe the decoupling and naming changes.

Estimated code review effort: 3 (Moderate) | ~25 minutes

New CI Audit Gates

Layer / File(s) Summary
Hook token registry
scripts/hook-tokens.js, scripts/check-llm-guide.js, tests/check-llm-guide.test.js
Adds HOOK_TOKENS/HOOK_TOKEN_NAMES for fallback-only tokens; updates live-token-set logic and adds tests.
Dead-knobs and annotations gates
scripts/check-dead-knobs.js, scripts/check-annotations.js
New scripts detect unwired annotation claims and mismatched ms/px annotations against resolved CSS values.
Hook-tokens and mirrors gates
scripts/check-hook-tokens.js, scripts/check-mirrors.js
New scripts validate fallback-only hook tokens and CSS mirror/derivation consistency (root vs @property, fluid CQ, dark-theme colors).
Bundle definitions gate
scripts/check-bundle-defs.js
New script verifies each CSS bundle defines all consumed bare tokens.
CI/npm wiring and test suite
package.json, .github/workflows/ci.yml, tests/check-source-audit-gates.test.js
New check:* npm scripts and CI steps run the gates; new test suite exercises each gate on clean and mutated repo clones.

Estimated code review effort: 4 (Complex) | ~60 minutes

Possibly related issues

Possibly related PRs

  • codeslash-dev/SLASHED#351: Adds a CI gate validating docs/token-annotations.json, the same annotation system introduced by that PR.
  • codeslash-dev/SLASHED#383: Directly modifies the same scripts/check-llm-guide.js live-token logic introduced there.
  • codeslash-dev/SLASHED#141: Both modify tests/a11y-patterns.spec.js coverage for --sf-touch-target independence from --sf-size-*.
🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 75.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title clearly summarizes the main change: adding the #582 source-CSS audit gates D1–D6.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch claude/issue-582-opchuq

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

claude added 4 commits July 9, 2026 11:31
# Conflicts:
#	configurator/src/data/api-index.generated.json
…-* rungs (#582 E1)

The button size scale now maps 1:1 onto the --sf-size-* rungs
(--xs→xs, --s→s, m→m, --l→l, --xl→xl) instead of the one-rung offset that
pinned the default button to the 44px --sf-touch-target floor. Every
non-xs/s button becomes shorter; the default drops from 44px (--sf-size-l,
via --sf-touch-target) to 40px (--sf-size-m).

BREAKING CHANGE: default/.sf-btn--l/.sf-btn--xl min-block-size shrink by one
rung. The default control still clears the WCAG 2.2 AA 24px target but no
longer meets the 44px AAA target by default — restore it globally with
`:root { --sf-btn-min-height: var(--sf-touch-target) }` or per-button with
`.sf-btn--l`. See docs/migration.md (0.7.8 → 0.8.0).

- optional/components.css: base min-height--size → --sf-size-m; --l → --sf-size-l;
  --xl → --sf-size-xl; rewrite the ladder comment (the offset is gone).
- docs/migration.md: add the 0.7.8 → 0.8.0 breaking entry with a before/after
  table and the opt-back-in recipe.
- docs/components.md, docs/llm-guide.md: update the --sf-btn-min-height default.
- tests/button.spec.js: assert the 1:1 min-height↔--sf-size-* mapping (both themes).

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_012i9DDskbZqmuMeDwQMjPjF
…E1 follow-up)

After the ladder remap the default button reads --sf-size-m, so the
annotation's "not currently consumed by any shipped rule" is stale. Point it
at the real consumer instead and regenerate the derived indexes.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_012i9DDskbZqmuMeDwQMjPjF
… the size scale (#582)

An accessibility constraint must own its value, not borrow it from a
configurable design scale. --sf-touch-target was `var(--sf-size-l)`, so
retuning the (fully configurable) --sf-size-* scale could silently drag the
WCAG 2.5.5 floor below spec. It now holds a fixed 2.75rem (44px) literal,
independent of the scale.

Freed from carrying the 44px anchor, --sf-size-l returns to its natural rung:
the UI size ladder is now a clean +8px geometric scale
(24 · 32 · 40 · 48 · 56) instead of 24 · 32 · 40 · 44 · 56.

Audited the whole token set for the same anti-pattern (a spec/physical
constraint aliased to a configurable scale rung); --sf-touch-target was the
only instance — focus-ring dims, header/sticky heights, icon sizes and
measure max-widths all already own literal values.

BREAKING CHANGE: --sf-size-l is now 3rem (48px), was 2.75rem (44px); the WCAG
44px guarantee now lives only on --sf-touch-target (read that, not --sf-size-l,
for a target-size floor). .sf-btn--l follows --sf-size-l to 48px. The a11y
min-target helper is unchanged (still 44px). See docs/migration.md.

- core/tokens.css: --sf-size-l 2.75rem→3rem; --sf-touch-target literal 2.75rem;
  comments on the geometric scale and the independent a11y anchor.
- tests/a11y-patterns.spec.js: new test proving --sf-touch-target survives a
  --sf-size-* override.
- docs/migration.md, llm-guide.md, token-annotations.json + regenerated indexes.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_012i9DDskbZqmuMeDwQMjPjF
@jackgranatowski

Copy link
Copy Markdown
Contributor Author

@coderabbitai review

@coderabbitai

coderabbitai Bot commented Jul 9, 2026

Copy link
Copy Markdown
✅ Action performed

Review finished.

Note: CodeRabbit is an incremental review system and does not re-review already reviewed commits. This command is applicable only when automatic reviews are paused.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 3

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
docs/api-index.json (1)

1728-1751: 🗄️ Data Integrity & Integration | 🟡 Minor | ⚡ Quick win

Update --sf-btn-min-height copy The description still says it defaults to --sf-touch-target, but the current fallback is --sf-size-m unless the knob is overridden.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@docs/api-index.json` around lines 1728 - 1751, The `--sf-btn-min-height`
token description is stale and still mentions `--sf-touch-target` as the
default. Update the `description` for this token in the API index to reflect the
current behavior that it falls back to `--sf-size-m` unless overridden, keeping
the wording aligned with the `--sf-btn-min-height` entry and related button
token metadata.
🧹 Nitpick comments (3)
tests/check-source-audit-gates.test.js (2)

40-45: 🩺 Stability & Availability | 🔵 Trivial | ⚡ Quick win

Add a timeout to spawnSync to prevent CI hangs.

runGate has no timeout option. If a gate script ever hangs (e.g., an infinite loop introduced by a future bug), the test suite will hang indefinitely in CI with no output.

⏱️ Proposed fix
 function runGate(gate, dir) {
   return spawnSync(process.execPath, [path.join(ROOT, 'scripts', gate)], {
     encoding: 'utf8',
     env: { ...process.env, SLASHED_ROOT: dir },
+    timeout: 30000,
   });
 }
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@tests/check-source-audit-gates.test.js` around lines 40 - 45, The `runGate`
helper currently calls `spawnSync` without a timeout, so a hanging gate script
can block `check-source-audit-gates.test.js` indefinitely. Update `runGate(gate,
dir)` to pass a reasonable timeout option to `spawnSync`, and make sure the test
handles the timeout case cleanly when the spawned process exceeds that limit.

53-66: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Assert that string mutations actually took effect to avoid confusing test failures.

The .replace() calls at lines 60, 91–92, and 108–109 use exact string matching against current CSS values. If those values change in the future, the replace silently no-ops, the mutation never happens, the gate passes (status 0), and the assert.equal(r.status, 1) failure message becomes confusing — it says "expected failure" but the gate actually passed because nothing was mutated.

Adding a guard that the mutated string differs from the original makes the failure mode clear: "mutation did not apply, test fixture is stale."

This applies to all three mutation-by-replace tests (D1 line 60, D4 lines 91–92, D5 lines 108–109).

🛡️ Example fix for the D1 test (apply similarly to D4 and D5)
     const original = readCss(dir, 'core/print.css');
     const css = original
       .replace('var(--sf-print-page-margin, 2cm)', '2cm');
+    assert.notEqual(original, css, 'mutation did not apply — fixture string is stale');
     writeCss(dir, 'core/print.css', css);
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@tests/check-source-audit-gates.test.js` around lines 53 - 66, The
mutation-by-replace tests in this suite can silently no-op if the expected CSS
text changes, which makes the later gate assertion misleading. Add an explicit
guard in each affected test around the existing readCss/writeCss flow in
check-dead-knobs.js tests so the test fails immediately when the replacement
does not change the fixture, and apply the same safeguard to the other
replace-based cases in the same file (including the D4 and D5 scenarios) using
the same helper/readCss/writeCss pattern.
configurator/src/data/api-index.generated.json (1)

12790-12809: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low value

Stale "touch-friendly" phrasing after touch-target decoupling.

The note still reads "Large UI component height (~48px). Touch-friendly interactive elements." Since --sf-touch-target is now explicitly decoupled from --sf-size-l in this PR (fixed 2.75rem regardless of size scale), keeping "touch-friendly" framing on --sf-size-l is a minor holdover from the old aliasing relationship and could confuse consumers into thinking overriding --sf-size-l still affects touch-target compliance.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@configurator/src/data/api-index.generated.json` around lines 12790 - 12809,
The note for the `--sf-size-l` token still uses “touch-friendly” language that
implies size drives touch-target behavior. Update the generated token metadata
so the `note` for `--sf-size-l` no longer ties this size token to touch-target
compliance, and instead reflects only the component height description; use the
`api-index.generated.json` entry for `--sf-size-l` as the source to align
wording with the new decoupled `--sf-touch-target` behavior.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@core/tokens.css`:
- Line 1629: Document the breaking default change for the `--sf-field-block`
token in `docs/migration.md`, since `core/tokens.css` now sets it to
`var(--sf-space-xs)` instead of the previous `var(--sf-space-l)`. Add this to
the existing token migration notes alongside the other token shifts, and make
sure the migration guide clearly calls out the new default and any affected form
spacing behavior.

In `@scripts/check-annotations.js`:
- Around line 82-86: `resolveMs` is matching `ms` anywhere in the string and can
misread calc()-based values as literals; update the `resolveMs` helper in
`check-annotations.js` to behave like `resolvePx` by only accepting fully
literal duration strings. Use the `baseValue(name)` result and tighten the regex
with start/end anchors so `calc(...)` or other compound expressions return
`null` instead of a partial number.

In `@scripts/check-dead-knobs.js`:
- Line 37: The WIRING_CLAIM pattern in check-dead-knobs.js is too broad because
it will still match wiring phrases like “applied to” or “wired to” even when
they are negated. Update the regex/validation around WIRING_CLAIM and the
token-scanning loop so negated annotations are ignored before treating them as
evidence of wiring, using the existing dead-knob check logic to guard against
false CI failures.

---

Outside diff comments:
In `@docs/api-index.json`:
- Around line 1728-1751: The `--sf-btn-min-height` token description is stale
and still mentions `--sf-touch-target` as the default. Update the `description`
for this token in the API index to reflect the current behavior that it falls
back to `--sf-size-m` unless overridden, keeping the wording aligned with the
`--sf-btn-min-height` entry and related button token metadata.

---

Nitpick comments:
In `@configurator/src/data/api-index.generated.json`:
- Around line 12790-12809: The note for the `--sf-size-l` token still uses
“touch-friendly” language that implies size drives touch-target behavior. Update
the generated token metadata so the `note` for `--sf-size-l` no longer ties this
size token to touch-target compliance, and instead reflects only the component
height description; use the `api-index.generated.json` entry for `--sf-size-l`
as the source to align wording with the new decoupled `--sf-touch-target`
behavior.

In `@tests/check-source-audit-gates.test.js`:
- Around line 40-45: The `runGate` helper currently calls `spawnSync` without a
timeout, so a hanging gate script can block `check-source-audit-gates.test.js`
indefinitely. Update `runGate(gate, dir)` to pass a reasonable timeout option to
`spawnSync`, and make sure the test handles the timeout case cleanly when the
spawned process exceeds that limit.
- Around line 53-66: The mutation-by-replace tests in this suite can silently
no-op if the expected CSS text changes, which makes the later gate assertion
misleading. Add an explicit guard in each affected test around the existing
readCss/writeCss flow in check-dead-knobs.js tests so the test fails immediately
when the replacement does not change the fixture, and apply the same safeguard
to the other replace-based cases in the same file (including the D4 and D5
scenarios) using the same helper/readCss/writeCss pattern.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro Plus

Run ID: 1f3ae1b8-a42e-42dd-af7b-c2aac84cd7bd

📥 Commits

Reviewing files that changed from the base of the PR and between 1a2821b and aa11767.

⛔ Files ignored due to path filters (1)
  • dist/css-custom-data.json is excluded by !**/dist/**
📒 Files selected for processing (35)
  • .github/workflows/ci.yml
  • configurator/src/data/api-index.generated.json
  • core/print.css
  • core/tokens.css
  • demos/full-api-demo-with-overrides.html
  • demos/full-api-demo.html
  • demos/ultimate-override.css
  • docs/api-index.json
  • docs/api-index.md
  • docs/architecture.md
  • docs/components.md
  • docs/llm-guide.md
  • docs/migration.md
  • docs/motion.md
  • docs/token-annotations.json
  • docs/token-index.json
  • docs/token-index.md
  • docs/tokens.md
  • optional/components.css
  • optional/forms.css
  • optional/tokens.components.css
  • optional/utilities.css
  • package.json
  • scripts/check-annotations.js
  • scripts/check-bundle-defs.js
  • scripts/check-dead-knobs.js
  • scripts/check-hook-tokens.js
  • scripts/check-llm-guide.js
  • scripts/check-mirrors.js
  • scripts/hook-tokens.js
  • tests/a11y-patterns.spec.js
  • tests/button.spec.js
  • tests/check-llm-guide.test.js
  • tests/check-source-audit-gates.test.js
  • tests/print.spec.js

Comment thread core/tokens.css
Comment thread scripts/check-annotations.js
Comment thread scripts/check-dead-knobs.js
- check-annotations: anchor resolveMs so compound calc() expressions
  resolve to null instead of yielding the first ms literal, while still
  resolving the framework's scaled calc(Nms * var(--sf-motion-scale)) form
- check-dead-knobs: skip negated wiring disclaimers ("not wired to any
  rule") so a truthful annotation can't trip the gate
- migration: document the breaking --sf-field-block default change from
  var(--sf-space-l) to var(--sf-space-xs)

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0114fqDEQ6xsTpmowzLiQWVp
@jackgranatowski
jackgranatowski merged commit 4e10193 into main Jul 9, 2026
13 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants