Cursor: Read this skill when the user asks for a design audit, design chain check, token audit, color audit, typography audit, Tailwind cleanup, or "flush drift." This is the unified audit — it supersedes running design-audit, color-audit, tailwind-cleanup, and typography-polish individually by combining all four with chain-specific rules.
Before starting
- Read the design chain reference:
_docs/_build/_stitch/_design-system/DESIGN-CHAIN.md - Read the runtime tokens:
src/app/globals.css(the@theme { }block) - Identify the target scope from the user (specific files, a route, or "full sweep").
If the user says "flush" or "flush drift," run all 5 layers as a full sweep across src/.
Layer 1 — Token Drift
Goal: No hardcoded colors exist where semantic tokens should be used.
Checks
# Hardcoded hex in className
grep -rn "bg-\[#" src/components src/app --include="*.tsx"
grep -rn "text-\[#" src/components src/app --include="*.tsx"
grep -rn "border-\[#" src/components src/app --include="*.tsx"
grep -rn "from-\[#" src/components src/app --include="*.tsx"
# Tailwind palette colors (should be semantic tokens)
grep -rnE "(bg|text|border|ring|divide)-(slate|gray|zinc|neutral|stone|red|orange|amber|yellow|lime|green|emerald|teal|cyan|sky|blue|indigo|violet|purple|fuchsia|pink|rose)-[0-9]" src/components src/app --include="*.tsx"
# Raw hex/rgb in inline style
grep -rnE "style=.*#[0-9a-fA-F]{3,8}" src/components src/app --include="*.tsx"
grep -rnE "style=.*rgb" src/components src/app --include="*.tsx"
Severity
- CRITICAL if found in dashboard/shell components (these must be 100% token-aligned)
- HIGH if found in editor components (except known dark-theme exceptions)
- INFO if in known exception list (see DESIGN-CHAIN.md "Known Intentional Exceptions")
Token replacement map
When fixing, use this map (not exhaustive — refer to DESIGN-CHAIN.md Layer 1 tables):
| Hardcoded | Replace with |
|---|---|
bg-[#fbf9f4] |
bg-surface |
bg-[#ffffff] |
bg-surface-container-lowest |
bg-[#f5f3ee] |
bg-surface-container-low |
bg-[#f0eee9] |
bg-surface-container |
bg-[#eae8e3] |
bg-surface-container-high |
bg-[#37285e] |
bg-tertiary-container |
bg-[#14006a] |
bg-primary |
bg-[#260b9e] |
bg-primary-container |
bg-[#e3dfff] |
bg-primary-fixed |
text-[#1b1c19] / text-[#121311] |
text-on-surface |
text-[#352f3d] / text-[#4c4451] |
text-on-surface-variant |
text-[#a290ce] |
text-on-tertiary-container |
text-[#14006a] |
text-primary |
text-[#938bff] |
text-on-primary-container |
border-[#7d7483] / border-[#5f5668] |
border-outline |
border-[#cec3d3] / border-[#b5a8c4] |
border-outline-variant |
from-[#14006a] |
from-primary |
to-[#260b9e] |
to-primary-container |
text-black |
text-on-surface |
bg-white |
bg-surface-container-lowest |
text-white (on dark bg) |
text-on-tertiary or text-on-primary (context-dependent) |
ve-* scope check
Confirm ve-* tokens appear only in:
src/components/video-editor/src/components/ai-suite/Audiobook*src/app/(editor)/video/
Flag any ve-* usage on cream dashboard surfaces.
Layer 2 — Primitive Drift
Goal: Design system rules are encoded once in src/components/ui/ and composed
everywhere else — not reimplemented.
Checks
# Raw <button> outside ui/ (should use Button primitive)
grep -rn "<button" src/components src/app --include="*.tsx" | grep -v "components/ui/" | grep -v "type=\"button\""
# Raw <input> outside ui/ (should use Input primitive)
grep -rn '<input\b' src/components src/app --include="*.tsx" | grep -v "components/ui/"
# Inline gradient reimplementation (should use Button variant="primary" or documented pattern)
grep -rn "from-primary to-primary-container" src/components src/app --include="*.tsx" | grep -v "components/ui/"
# Inline status color mapping (should use StatusChip)
grep -rnE "bg-(secondary-container|primary-fixed|tertiary-fixed|error-container).*text-(on-secondary-container|on-primary-fixed|on-tertiary-fixed|on-error-container)" src/ --include="*.tsx" | grep -v "components/ui/"
Evaluation
Not every raw <button> is a violation — toggle buttons, icon-only triggers, and
specialized controls may intentionally skip the primitive. But they must still:
- Use semantic token colors (not raw hex)
- Have focus-visible indicators
- Have accessible names
Report each hit with a USE PRIMITIVE or ACCEPTABLE OVERRIDE judgment.
Layer 3 — Component & Style Drift
This layer combines the checks from color-audit, tailwind-cleanup, and design-audit.
3a. Color & contrast
Read the @theme block and verify:
- Every surface/text pair maintains WCAG AA contrast:
- Normal text < 18px: 4.5:1 minimum
- Large text: 3:1 minimum
- UI controls: 3:1 minimum
- Critical pairs to check:
on-surface(#121311) onsurface(#fbf9f4) — must passon-surface-variant(#352f3d) onsurface(#fbf9f4) — must passon-tertiary-container(#a290ce) ontertiary-container(#37285e) — must passon-primary(#ffffff) onprimary(#14006a) — must passon-primary-container(#938bff) onprimary-container(#260b9e) — must passon-error-container(#93000a) onerror-container(#ffdad6) — must passon-lilac(#311c7e) onlilac(#c9beff) — must pass (documented as 7.7:1)
- Error distinguishable from primary (hue difference, not just lightness)
- No opacity modifiers pushing text below contrast thresholds
3b. Typography
- Page titles:
font-serif(Newsreader),text-4xl+,font-medium+,tracking-tight - Section titles:
font-serif,text-2xl+,font-semibold - Form labels:
font-displayorfont-sans,text-xs,uppercase,tracking-wider - Nav section headers:
font-sans,text-xs,uppercase,tracking-tight–tracking-widest - Body copy:
font-sans,text-base(nottext-smas default) - Stat numbers:
font-serif,tabular-numswhere alignment matters - No
font-serifused for body paragraphs - No
font-sansused for page-level headlines - Long-form prose:
~65chmax measure,leading-relaxed(1.6–1.8 line-height) - No orphaned headings (heading at bottom of viewport without content below)
3c. Pattern & layout
- No-Line Rule: No
border-b,border-t,<hr>between content sections — use background tier shifts- Exception:
border-t border-outline-variant/15as ghost border is acceptable - Exception: Input bottom borders are part of the input pattern
- Exception:
- Consistent spacing: Tailwind scale, no arbitrary spacing where scale suffices
- Responsive: mobile (
375px), tablet (768px), desktop (~1280px) - No horizontal scroll on any breakpoint
- Content sections logically grouped
- Dashboard grids:
grid-cols-12 gap-6 - Page padding:
p-8 - Content max-width:
max-w-7xl(dashboard) ormax-w-5xl–max-w-6xl(editors)
3d. Roundness
# Find over-rounded elements (max is rounded-md)
grep -rnE "rounded-(lg|xl|2xl|3xl)" src/components src/app --include="*.tsx"
- No
rounded-lgor larger (exceptrounded-fullfor avatars/pills) - CTAs use
rounded-sm(precision-cut) - Cards and modals use
rounded-mdmaximum
3e. Shadows
- Floating elements use ambient shadow:
shadow-[0_20px_40px_rgba(27,28,25,0.06)] - No
shadow-lgorshadow-xlon cards (use surface tier shifts instead) - Shadow color derived from
on-surface, not generic black
3f. Tailwind hygiene
- No
text-black/bg-whitewhere semantic tokens exist - No absurdly long
classNamestrings (extract tocn()or component) - No duplicate utilities in the same className
-
cn()used for conditional class merging - No raw
fetch()in leaf UI components (use hooks/services)
Layer 4 — Layout & Shell Drift
Checks
-
AppSidebarwidth matchesDASHBOARD_LEFT_NAV_EXPANDED_PX(240px) -
DashboardMainColumnuses nav insets context for dynamic left margin -
TopBaris sticky,h-14,z-50, no bottom border - Sidebar uses
bg-tertiary-container(not a dark substitute) - Active nav item has
bg-primary-fixedleft-edge vertical pill - Footer border on sidebar uses
border-tertiary-fixed/30(ghost, not solid) - AI panel slides from right, uses frosted glass pattern
- Command palette opens with ⌘K, uses
surface-container-lowestbase - Page scroll is on main content, not on body/sidebar
Layer 5 — Interactions & Accessibility
Checks
- Hover states: cream surfaces step up one tier; sidebar items use
hover:bg-tertiary-container/55 - Focus visible on all interactive elements:
focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-primary - Input focus: bottom border transitions
outline→primary - Button press:
active:scale-95where used - Transitions:
transition-colorsfor color;transition-all duration-150for compound -
prefers-reduced-motionrespected for animations - Images have meaningful
alttext (or aria decorative pattern) - No color-only meaning (status uses text label + color)
- Keyboard: no focus traps
- Tap targets ≥ 44×44px for touch interfaces
- Icon-only controls have
aria-labelor accessible name - Locked nav items (
pointer-events-none opacity-40) have "Soon" badge for visual explanation
Output format
## Design Chain Audit: [target]
### Chain Health: X/5 layers passing
### Layer 1 — Token Drift
**Status:** PASS | DRIFT DETECTED
- [file:line] — [severity] — description
Fix: replacement
### Layer 2 — Primitive Drift
**Status:** PASS | DRIFT DETECTED
- [file:line] — [USE PRIMITIVE | ACCEPTABLE OVERRIDE] — description
### Layer 3 — Component & Style Drift
#### 3a. Color & contrast
**Status:** PASS | ISSUES
- ...
#### 3b. Typography
**Status:** PASS | ISSUES
- ...
#### 3c. Pattern & layout
**Status:** PASS | ISSUES
- ...
#### 3d. Roundness
**Status:** PASS | ISSUES
- ...
#### 3e. Shadows
**Status:** PASS | ISSUES
- ...
#### 3f. Tailwind hygiene
**Status:** PASS | ISSUES
- ...
### Layer 4 — Layout & Shell Drift
**Status:** PASS | DRIFT DETECTED
- ...
### Layer 5 — Interactions & Accessibility
**Status:** PASS | ISSUES
- ...
### Summary
- Total issues: N (X critical, Y high, Z medium, W low)
- Files requiring changes: [list]
- Recommended fix order: [prioritized list]
Quick flush (CLI)
For a fast automated check without a full report, run:
# Token drift — should return zero results
echo "=== TOKEN DRIFT ===" && \
grep -rn "bg-\[#" src/components src/app --include="*.tsx" | grep -cv "_stitch" && \
grep -rn "text-\[#" src/components src/app --include="*.tsx" | grep -cv "_stitch" && \
grep -rnE "(bg|text|border)-(slate|gray|zinc|blue|red|green)-[0-9]" src/ --include="*.tsx" | wc -l && \
# Roundness drift
echo "=== ROUNDNESS DRIFT ===" && \
grep -rnE "rounded-(lg|xl|2xl)" src/ --include="*.tsx" | wc -l && \
# Shadow drift
echo "=== SHADOW DRIFT ===" && \
grep -rnE "shadow-(lg|xl|2xl)" src/ --include="*.tsx" | wc -l && \
echo "=== DONE ==="
Reference documents
| Document | Path | Use |
|---|---|---|
| Design Chain (this audit's bible) | _docs/_build/_stitch/_design-system/DESIGN-CHAIN.md |
Full token tables, rules, hierarchy |
| Token spec | _docs/_build/_stitch/_design-system/tokens.md |
Extracted Stitch tokens |
| Design system spec | _docs/_build/_stitch/_design-system/design-system-spec.md |
Creative North Star, No-Line Rule |
| Component catalog | _docs/_build/_stitch/_design-system/component-catalog.md |
Token→component mapping |
| Runtime tokens | src/app/globals.css (@theme) |
Live token values |
| Designer dashboard skill | .claude/skills/designer-dashboard/SKILL.md |
Dashboard-specific guidance |
Rules
- Present the full audit report before applying any fixes.
- Fix at the correct layer: token issue → fix in
globals.css; primitive issue → fix inui/; component issue → fix in the component. - Do not change brand primary hue without explicit user approval.
- Contrast fixes: prefer lightness adjustments over hue shifts.
- Do not modify
_docs/_build/_stitch/HTML files — they are reference only. - When in doubt about whether a hardcoded value is intentional, check the "Known Intentional Exceptions" in DESIGN-CHAIN.md.