design-review — independently scanned and version-tracked by SaferSkills.
SaferSkills independently audited design-review (Agent Skill) and scored it 100/100 (green). The audit ran 55 deterministic rules across Security, Supply Chain, Maintenance, Transparency, and Community; it found 0 high-severity and 0 lower-severity findings. The full rule-by-rule trace and per-finding evidence are below. Free, methodology-open.
Findings & checks · 0 flagged
Every scanned point with the score it earned and what moved between them.
First recorded scan — no prior version to compare against.
The primary manifest — the file an agent reads to learn what this artifact does.
Use when asked to "audit the design", "visual QA", "check if it looks good", or "design polish".
Proactively suggest when the user mentions visual inconsistencies or wants to polish the look of a live site.
eval "$(~/.vibestack/bin/vibe-slug 2>/dev/null)" 2>/dev/null || SLUG="unknown"
_LEARN_FILE="${VIBESTACK_HOME:-$HOME/.vibestack}/projects/${SLUG:-unknown}/learnings.jsonl"
if [ -f "$_LEARN_FILE" ]; then
_LEARN_COUNT=$(wc -l < "$_LEARN_FILE" 2>/dev/null | tr -d ' ')
echo "LEARNINGS: $_LEARN_COUNT entries loaded"
if [ "$_LEARN_COUNT" -gt 5 ] 2>/dev/null; then
~/.vibestack/bin/vibe-learnings-search --limit 5 2>/dev/null || true
fi
else
echo "LEARNINGS: none yet"
fi{{include lib/snippets/session-host.md}}
{{include lib/snippets/decision-brief.md}}
{{include lib/snippets/working-protocols.md}}
{{include lib/snippets/state-protocols.md}}
Parse the user's request for these parameters:
| Parameter | Default | Override example |
|---|---|---|
| Target URL | (auto-detect or ask) | https://myapp.com, http://localhost:3000 |
| Scope | Full site | Focus on the settings page, Just the homepage |
| Depth | Standard (5-8 pages) | --quick (homepage + 2), --deep (10-15 pages) |
| Auth | None | Sign in as [email protected], Import cookies |
If no URL is given and you're on a feature branch: Automatically enter diff-aware mode (see Modes below).
If no URL is given and you're on main/master: Ask the user for a URL.
CDP mode detection: Check if browse is connected to the user's real browser:
$B status 2>/dev/null | grep -q "Mode: cdp" && echo "CDP_MODE=true" || echo "CDP_MODE=false"If CDP_MODE=true: skip cookie import steps — the real browser already has cookies and auth sessions. Skip headless detection workarounds.
Check for DESIGN.md:
Look for DESIGN.md, design-system.md, or similar in the repo root. If found, read it — all design decisions must be calibrated against it. Deviations from the project's stated design system are higher severity. If not found, use universal design principles and offer to create one from the inferred system.
Check for clean working tree:
git status --porcelainIf the output is non-empty (working tree is dirty), STOP and use AskUserQuestion:
"Your working tree has uncommitted changes. /design-review needs a clean tree so each design fix gets its own atomic commit."
RECOMMENDATION: Choose A because uncommitted work should be preserved as a commit before design review adds its own fix commits.
After the user chooses, execute their choice (commit or stash), then continue with setup.
{{include lib/snippets/browse-setup.md}}
Detect existing test framework and project runtime:
setopt +o nomatch 2>/dev/null || true # zsh compat
# Detect project runtime
[ -f Gemfile ] && echo "RUNTIME:ruby"
[ -f package.json ] && echo "RUNTIME:node"
[ -f requirements.txt ] || [ -f pyproject.toml ] && echo "RUNTIME:python"
[ -f go.mod ] && echo "RUNTIME:go"
[ -f Cargo.toml ] && echo "RUNTIME:rust"
[ -f composer.json ] && echo "RUNTIME:php"
[ -f mix.exs ] && echo "RUNTIME:elixir"
# Detect sub-frameworks
[ -f Gemfile ] && grep -q "rails" Gemfile 2>/dev/null && echo "FRAMEWORK:rails"
[ -f package.json ] && grep -q '"next"' package.json 2>/dev/null && echo "FRAMEWORK:nextjs"
# Check for existing test infrastructure
ls jest.config.* vitest.config.* playwright.config.* .rspec pytest.ini pyproject.toml phpunit.xml 2>/dev/null
ls -d test/ tests/ spec/ __tests__/ cypress/ e2e/ 2>/dev/null
# Check opt-out marker
[ -f .vibestack/no-test-bootstrap ] && echo "BOOTSTRAP_DECLINED"If test framework detected (config files or test directories found): Print "Test framework detected: {name} ({N} existing tests). Skipping bootstrap." Read 2-3 existing test files to learn conventions (naming, imports, assertion style, setup patterns). Store conventions as prose context for use in Phase 8e.5 or Step 7. Skip the rest of bootstrap.
If BOOTSTRAP_DECLINED appears: Print "Test bootstrap previously declined — skipping." Skip the rest of bootstrap.
If NO runtime detected (no config files found): Use AskUserQuestion: "I couldn't detect your project's language. What runtime are you using?" Options: A) Node.js/TypeScript B) Ruby/Rails C) Python D) Go E) Rust F) PHP G) Elixir H) This project doesn't need tests. If user picks H → write .vibestack/no-test-bootstrap and continue without tests.
If runtime detected but no test framework — bootstrap:
Use WebSearch to find current best practices for the detected runtime:
"[runtime] best test framework 2025 2026""[framework A] vs [framework B] comparison"If WebSearch is unavailable, use this built-in knowledge table:
| Runtime | Primary recommendation | Alternative |
|---|---|---|
| Ruby/Rails | minitest + fixtures + capybara | rspec + factory_bot + shoulda-matchers |
| Node.js | vitest + @testing-library | jest + @testing-library |
| Next.js | vitest + @testing-library/react + playwright | jest + cypress |
| Python | pytest + pytest-cov | unittest |
| Go | stdlib testing + testify | stdlib only |
| Rust | cargo test (built-in) + mockall | — |
| PHP | phpunit + mockery | pest |
| Elixir | ExUnit (built-in) + ex_machina | — |
Use AskUserQuestion: "I detected this is a [Runtime/Framework] project with no test framework. I researched current best practices. Here are the options: A) [Primary] — [rationale]. Includes: [packages]. Supports: unit, integration, smoke, e2e B) [Alternative] — [rationale]. Includes: [packages] C) Skip — don't set up testing right now RECOMMENDATION: Choose A because [reason based on project context]"
If user picks C → write .vibestack/no-test-bootstrap. Tell user: "If you change your mind later, delete .vibestack/no-test-bootstrap and re-run." Continue without tests.
If multiple runtimes detected (monorepo) → ask which runtime to set up first, with option to do both sequentially.
If package installation fails → debug once. If still failing → revert with git checkout -- package.json package-lock.json (or equivalent for the runtime). Warn user and continue without tests.
Generate 3-5 real tests for existing code:
git log --since=30.days --name-only --format="" | sort | uniq -c | sort -rn | head -10expect(x).toBeDefined() — test what the code DOES.Never import secrets, API keys, or credentials in test files. Use environment variables or test fixtures.
# Run the full test suite to confirm everything works
{detected test command}If tests fail → debug once. If still failing → revert all bootstrap changes and warn user.
# Check CI provider
ls -d .github/ 2>/dev/null && echo "CI:github"
ls .gitlab-ci.yml .circleci/ bitrise.yml 2>/dev/nullIf .github/ exists (or no CI detected — default to GitHub Actions): Create .github/workflows/test.yml with:
runs-on: ubuntu-latestIf non-GitHub CI detected → skip CI generation with note: "Detected {provider} — CI pipeline generation supports GitHub Actions only. Add test step to your existing pipeline manually."
First check: If TESTING.md already exists → read it and update/append rather than overwriting. Never destroy existing content.
Write TESTING.md with:
First check: If CLAUDE.md already has a ## Testing section → skip. Don't duplicate.
Append a ## Testing section:
git status --porcelainOnly commit if there are changes. Stage all bootstrap files (config, test directory, TESTING.md, CLAUDE.md, .github/workflows/test.yml if created): git commit -m "chore: bootstrap test framework ({framework name})"
Find the vibestack designer (optional — enables target mockup generation):
# Bind $D to vibe-design (OpenAI image backend) when a key is configured.
D=~/.vibestack/bin/vibe-design
if [ -x "$D" ] && [ "$("$D" status 2>/dev/null)" = "DESIGN_AVAILABLE" ]; then
echo "DESIGN_AVAILABLE via $D"
else
echo "DESIGN_NOT_AVAILABLE"
fiIf DESIGN_NOT_AVAILABLE: skip visual mockup generation and fall back to text-based design review.
{{include lib/snippets/prior-learnings.md}}
These principles govern how real humans interact with interfaces. They are observed behavior, not preferences. Apply them before, during, and after every design decision.
to think "What do I click?" or "What does this mean?", the design has failed. Self-evident > self-explanatory > requires explanation.
beat one click that requires thought. Each step should feel like an obvious choice (animal, vegetable, or mineral), not a puzzle.
rid of half of what's left. Happy talk (self-congratulatory text) must die. Instructions must die. If they need reading, the design has failed.
(prominence = importance), clearly defined areas, headings and bullet lists, highlighted key terms. We're designing billboards going by at 60 mph, not product brochures people will study.
Make the right choice the most visible choice.
it. If they accomplish their goal by accident, they won't seek the "right" way. Once they find something that works, no matter how badly, they stick to it.
timely, and unavoidable, or it won't be seen.
Don't innovate on navigation to be clever. Innovate when you KNOW you have a better idea, otherwise use conventions. Even across languages and cultures, web conventions let people identify the logo, nav, search, and main content.
things are visually contained. More important = more prominent. If everything shouts, nothing is heard. Start with the assumption everything is visual noise, guilty until proven innocent.
discoverability, especially on mobile where hover doesn't exist. Shape, location, and formatting (color, underlining) must signal clickability without interaction.
(shouting), things not organized logically (disorganization), and too much stuff (clutter). Fix noise by removal, not addition.
requires making it slightly inconsistent, choose clarity every time.
Users on the web have no sense of scale, direction, or location. Navigation must always answer: What site is this? What page am I on? What are the major sections? What are my options at this level? Where am I? How can I search?
Persistent navigation on every page. Breadcrumbs for deep hierarchies. Current section visually indicated. The "trunk test": cover everything except the navigation. You should still know what site this is, what page you're on, and what the major sections are. If not, the navigation has failed.
Users start with a reservoir of goodwill. Every friction point depletes it.
Deplete faster: Hiding info users want (pricing, contact, shipping). Punishing users for not doing things your way (formatting requirements on phone numbers). Asking for unnecessary information. Putting sizzle in their way (splash screens, forced tours, interstitials). Unprofessional or sloppy appearance.
Replenish: Know what users want to do and make it obvious. Tell them what they want to know upfront. Save them steps wherever possible. Make it easy to recover from errors. When in doubt, apologize.
All the above applies on mobile, just more so. Real estate is scarce, but never sacrifice usability for space savings. Affordances must be VISIBLE: no cursor means no hover-to-discover. Touch targets must be big enough (44px minimum). Flat design can strip away useful visual information that signals interactivity. Prioritize ruthlessly: things needed in a hurry go close at hand, everything else a few taps away with an obvious path to get there.
Systematic review of all pages reachable from homepage. Visit 5-8 pages. Full checklist evaluation, responsive screenshots, interaction flow testing. Produces complete design audit report with letter grades.
--quick)Homepage + 2 key pages only. First Impression + Design System Extraction + abbreviated checklist. Fastest path to a design score.
--deep)Comprehensive review: 10-15 pages, every interaction flow, exhaustive checklist. For pre-launch audits or major redesigns.
When on a feature branch, scope to pages affected by the branch changes:
git diff main...HEAD --name-only--regression or previous design-baseline.json found)Run full audit, then load previous design-baseline.json. Compare: per-category grade deltas, new findings, resolved findings. Output regression table in report.
The most uniquely designer-like output. Form a gut reaction before analyzing anything.
$B screenshot "$REPORT_DIR/screenshots/first-impression.png"Narration mode: Write this section in first person, as if you are a user scanning the page for the first time. "I'm looking at this page... my eye goes to the logo, then a wall of text I skip entirely, then... wait, is that a button?" Name the specific element, its position, its visual weight. If you can't name it specifically, you're not actually scanning, you're generating platitudes.
Page Area Test: Point at each clearly defined area of the page. Can you instantly name its purpose? ("Things I can buy," "Today's deals," "How to search.") Areas you can't name in 2 seconds are poorly defined. List them.
This is the section users read first. Be opinionated. A designer doesn't hedge — they react.
Extract the actual design system the site uses (not what a DESIGN.md says, but what's rendered):
# Fonts in use (capped at 500 elements to avoid timeout)
$B js "JSON.stringify([...new Set([...document.querySelectorAll('*')].slice(0,500).map(e => getComputedStyle(e).fontFamily))])"
# Color palette in use
$B js "JSON.stringify([...new Set([...document.querySelectorAll('*')].slice(0,500).flatMap(e => [getComputedStyle(e).color, getComputedStyle(e).backgroundColor]).filter(c => c !== 'rgba(0, 0, 0, 0)'))])"
# Heading hierarchy
$B js "JSON.stringify([...document.querySelectorAll('h1,h2,h3,h4,h5,h6')].map(h => ({tag:h.tagName, text:h.textContent.trim().slice(0,50), size:getComputedStyle(h).fontSize, weight:getComputedStyle(h).fontWeight})))"
# Touch target audit (find undersized interactive elements)
$B js "JSON.stringify([...document.querySelectorAll('a,button,input,[role=button]')].filter(e => {const r=e.getBoundingClientRect(); return r.width>0 && (r.width<44||r.height<44)}).map(e => ({tag:e.tagName, text:(e.textContent||'').trim().slice(0,30), w:Math.round(e.getBoundingClientRect().width), h:Math.round(e.getBoundingClientRect().height)})).slice(0,20))"
# Performance baseline
$B perfStructure findings as an Inferred Design System:
After extraction, offer: "Want me to save this as your DESIGN.md? I can lock in these observations as your project's design system baseline."
For each page in scope:
$B goto <url>
$B snapshot -i -a -o "$REPORT_DIR/screenshots/{page}-annotated.png"
$B responsive "$REPORT_DIR/screenshots/{page}"
$B console --errors
$B perfAfter the first navigation, check if the URL changed to a login-like path:
$B urlIf URL contains /login, /signin, /auth, or /sso: the site requires authentication. AskUserQuestion: "This site requires authentication. Want to import cookies from your browser? Run /setup-browser-cookies first if needed."
Imagine being dropped on this page with no context. Can you immediately answer:
Score: PASS (all 6 clear) / PARTIAL (4-5 clear) / FAIL (3 or fewer clear). A FAIL on the trunk test is a HIGH-impact finding regardless of how polished the visual design is.
Apply these at each page. Each finding gets an impact rating (high/medium/polish) and category.
1. Visual Hierarchy & Composition (8 items)
2. Typography (15 items)
text-wrap: balance or text-pretty on headings (check via $B css <heading> text-wrap)…) not three dots (...)font-variant-numeric: tabular-nums on number columns3. Color & Contrast (10 items)
color-scheme: dark on html element (if dark mode present)4. Spacing & Layout (12 items)
env(safe-area-inset-*) for notch devices5. Interaction States (10 items)
focus-visible ring present (never outline: none without replacement)cursor: not-allowedcursor: pointer on all clickable elements6. Responsive Design (8 items)
user-scalable=no or maximum-scale=1 in viewport meta7. Motion & Animation (6 items)
prefers-reduced-motion respected (check: $B js "matchMedia('(prefers-reduced-motion: reduce)').matches")transition: all — properties listed explicitlytransform and opacity animated (not layout properties like width, height, top, left)8. Content & Microcopy (8 items)
text-overflow: ellipsis, line-clamp, or break-words)… ("Saving…" not "Saving...")9. AI Slop Detection (10 anti-patterns — the blacklist)
The test: would a human designer at a respected studio ever ship this?
text-align: center on all headings, descriptions, cards)border-left: 3px solid <accent>)-apple-system as the PRIMARY display/body font — the "I gave up on typography" signal. Pick a real typeface.10. Performance as Design (6 items)
loading="lazy", width/height dimensions set, WebP/AVIF formatfont-display: swap, preconnect to CDN originsWalk 2-3 key user flows and evaluate the feel, not just the function:
$B snapshot -i
$B click @e3 # perform action
$B snapshot -D # diff to see what changedEvaluate:
Narration mode: Narrate the flow in first person. "I click 'Sign Up'... spinner appears... 3 seconds pass... still spinning... I'm getting nervous. Finally the dashboard loads, but where am I? The nav doesn't highlight anything." Name the specific element, its position, its visual weight. If you can't name it specifically, you're not actually experiencing the flow, you're generating platitudes.
As you walk the user flow, maintain a mental goodwill meter (starts at 70/100). These scores are heuristic, not measured. The value is in identifying specific drains and fills, not in the final number.
Subtract points for:
Add points for:
Report the final goodwill score with a visual dashboard:
Goodwill: 70 ████████████████████░░░░░░░░░░
Step 1: Login page 70 → 75 (+5 obvious primary action)
Step 2: Dashboard 75 → 60 (-15 interstitial tour popup)
Step 3: Settings 60 → 50 (-10 format punishment on phone)
Step 4: Billing 50 → 35 (-15 hidden pricing info)
FINAL: 35/100 ⚠️ CRITICAL UX DEBTBelow 30 = critical UX debt. 30-60 = needs work. Above 60 = healthy. Include the biggest drains and fills as specific findings.
Compare screenshots and observations across pages for:
Local: .vibestack/design-reports/design-audit-{domain}-{YYYY-MM-DD}.md
Project-scoped:
eval "$(~/.vibestack/bin/vibe-slug 2>/dev/null)" && mkdir -p ~/.vibestack/projects/$SLUGWrite to: ~/.vibestack/projects/{slug}/{user}-{branch}-design-audit-{datetime}.md
Baseline: Write design-baseline.json for regression mode:
{
"date": "YYYY-MM-DD",
"url": "<target>",
"designScore": "B",
"aiSlopScore": "C",
"categoryGrades": { "hierarchy": "A", "typography": "B", ... },
"findings": [{ "id": "FINDING-001", "title": "...", "impact": "high", "category": "typography" }]
}Dual headline scores:
Per-category grades:
Grade computation: Each category starts at A. Each High-impact finding drops one letter grade. Each Medium-impact finding drops half a letter grade. Polish findings are noted but do not affect grade. Minimum is F.
Category weights for Design Score:
| Category | Weight |
|---|---|
| Visual Hierarchy | 15% |
| Typography | 15% |
| Spacing & Layout | 15% |
| Color & Contrast | 10% |
| Interaction States | 10% |
| Responsive | 10% |
| Content Quality | 10% |
| AI Slop | 5% |
| Motion | 5% |
| Performance Feel | 5% |
AI Slop is 5% of Design Score but also graded independently as a headline metric.
When previous design-baseline.json exists or --regression flag is used:
Use structured feedback, not opinions:
Tie everything to user goals and product objectives. Always suggest specific improvements alongside problems.
snapshot -a) to highlight elements.$B screenshot, $B snapshot -a -o, or $B responsive command, use the Read tool on the output file(s) so the user can see them inline. For responsive (3 files), Read all three. This is critical — without it, screenshots are invisible to the user.Classifier — determine rule set before evaluating:
Hard rejection criteria (instant-fail patterns — flag if ANY apply):
Litmus checks (answer YES/NO for each — used for cross-model consensus scoring):
Landing page rules (apply when classifier = MARKETING/LANDING):
App UI rules (apply when classifier = APP UI):
Universal rules (apply to ALL types):
AI Slop blacklist (the 10 patterns that scream "AI-generated"):
text-align: center on all headings, descriptions, cards)border-left: 3px solid <accent>)-apple-system as the PRIMARY display/body font — the "I gave up on typography" signal. Pick a real typeface.Source: OpenAI "Designing Delightful Frontends with GPT-5.4" (Mar 2026) + vibestack design methodology.
Record baseline design score and AI slop score at end of Phase 6.
~/.vibestack/projects/$SLUG/designs/design-audit-{YYYYMMDD}/
├── design-audit-{domain}.md # Structured report
├── screenshots/
│ ├── first-impression.png # Phase 1
│ ├── {page}-annotated.png # Per-page annotated
│ ├── {page}-mobile.png # Responsive
│ ├── {page}-tablet.png
│ ├── {page}-desktop.png
│ ├── finding-001-before.png # Before fix
│ ├── finding-001-target.png # Target mockup (if generated)
│ ├── finding-001-after.png # After fix
│ └── ...
└── design-baseline.json # For regression modeAutomatic: Outside voices run automatically when Codex is available. No opt-in needed.
Check Codex availability:
command -v codex >/dev/null 2>&1 && echo "CODEX_AVAILABLE" || echo "CODEX_NOT_AVAILABLE"If Codex is available, launch both voices simultaneously:
TMPERR_DESIGN=$(mktemp /tmp/codex-design-XXXXXXXX)
_REPO_ROOT=$(git rev-parse --show-toplevel) || { echo "ERROR: not in a git repo" >&2; exit 1; }
command -v codex >/dev/null 2>&1 && codex exec "Review the frontend source code in this repo. Evaluate against these design hard rules:
- Spacing: systematic (design tokens / CSS variables) or magic numbers?
- Typography: expressive purposeful fonts or default stacks?
- Color: CSS variables with defined system, or hardcoded hex scattered?
- Responsive: breakpoints defined? calc(100svh - header) for heroes? Mobile tested?
- A11y: ARIA landmarks, alt text, contrast ratios, 44px touch targets?
- Motion: 2-3 intentional animations, or zero / ornamental only?
- Cards: used only when card IS the interaction? No decorative card grids?
First classify as MARKETING/LANDING PAGE vs APP UI vs HYBRID, then apply matching rules.
LITMUS CHECKS — answer YES/NO:
1. Brand/product unmistakable in first screen?
2. One strong visual anchor present?
3. Page understandable by scanning headlines only?
4. Each section has one job?
5. Are cards actually necessary?
6. Does motion improve hierarchy or atmosphere?
7. Would design feel premium with all decorative shadows removed?
HARD REJECTION — flag if ANY apply:
1. Generic SaaS card grid as first impression
2. Beautiful image with weak brand
3. Strong headline with no clear action
4. Busy imagery behind text
5. Sections repeating same mood statement
6. Carousel with no narrative purpose
7. App UI made of stacked cards instead of layout
Be specific. Reference file:line for every finding." -C "$_REPO_ROOT" -s read-only -c 'model_reasoning_effort="high"' --enable web_search_cached < /dev/null 2>"$TMPERR_DESIGN"Use a 5-minute timeout (timeout: 300000). After the command completes, read stderr:
cat "$TMPERR_DESIGN" && rm -f "$TMPERR_DESIGN"Dispatch a subagent with this prompt: "Review the frontend source code in this repo. You are an independent senior product designer doing a source-code design audit. Focus on CONSISTENCY PATTERNS across files rather than individual violations:
For each finding: what's wrong, severity (critical/high/medium), and the file:line."
Error handling (all non-blocking):
codex login to authenticate."[single-model].Present Codex output under a CODEX SAYS (design source audit): header. Present subagent output under a CLAUDE SUBAGENT (design consistency): header.
Synthesis — Litmus scorecard:
Use the same scorecard format as /plan-design-review (shown above). Fill in from both outputs. Merge findings into the triage with [codex] / [subagent] / [cross-model] tags.
Log the result:
true # vibe-review-log '{"skill":"design-outside-voices","timestamp":"'"$(date -u +%Y-%m-%dT%H:%M:%SZ)"'","status":"STATUS","source":"SOURCE","commit":"'"$(git rev-parse --short HEAD)"'"}'Replace STATUS with "clean" or "issues_found", SOURCE with "codex+subagent", "codex-only", "subagent-only", or "unavailable".
Sort all discovered findings by impact, then decide which to fix:
Mark findings that cannot be fixed from source code (e.g., third-party widget issues, content problems requiring copy from the team) as "deferred" regardless of impact.
For each fixable finding, in impact order:
# Search for CSS classes, component names, style files
# Glob for file patterns matching the affected pageIf the vibestack designer is available and the finding involves visual layout, hierarchy, or spacing (not just a CSS value fix like wrong color or font-size), generate a target mockup showing what the corrected version should look like:
$D generate --brief "<description of the page/component with the finding fixed, referencing DESIGN.md constraints>" --output "$REPORT_DIR/screenshots/finding-NNN-target.png"Show the user: "Here's the current state (screenshot) and here's what it should look like (mockup). Now I'll fix the source to match."
This step is optional — skip for trivial CSS fixes (wrong hex color, missing padding value). Use it for findings where the intended design isn't obvious from the description alone.
git add <only-changed-files>
git commit -m "style(design): FINDING-NNN — short description"style(design): FINDING-NNN — short descriptionNavigate back to the affected page and verify the fix:
$B goto <affected-url>
$B screenshot "$REPORT_DIR/screenshots/finding-NNN-after.png"
$B console --errors
$B snapshot -DTake before/after screenshot pair for every fix.
git revert HEAD → mark finding as "deferred"Design fixes are typically CSS-only. Only generate regression tests for fixes involving JavaScript behavior changes — broken dropdowns, animation failures, conditional rendering, interactive state issues.
For CSS-only fixes: skip entirely. CSS regressions are caught by re-running /design-review.
If the fix involved JS behavior: follow the same procedure as /qa Phase 8e.5 (study existing test patterns, write a regression test encoding the exact bug condition, run it, commit if passes or defer if fails). Commit format: test(design): regression test for FINDING-NNN.
Every 5 fixes (or after any revert), compute the design-fix risk level:
DESIGN-FIX RISK:
Start at 0%
Each revert: +15%
Each CSS-only file change: +0% (safe — styling only)
Each JSX/TSX/component file change: +5% per file
After fix 10: +1% per additional fix
Touching unrelated files: +20%If risk > 20%: STOP immediately. Show the user what you've done so far. Ask whether to continue.
Hard cap: 30 fixes. After 30 fixes, stop regardless of remaining findings.
After all fixes are applied:
DESIGN_READY: run $D verify --mockup "$REPORT_DIR/screenshots/finding-NNN-target.png" --screenshot "$REPORT_DIR/screenshots/finding-NNN-after.png" to compare the fix result against the target. Include pass/fail in the report.Write the report to $REPORT_DIR (already set up in the setup phase):
Primary: $REPORT_DIR/design-audit-{domain}.md
Also write a summary to the project index:
eval "$(~/.vibestack/bin/vibe-slug 2>/dev/null)" && mkdir -p ~/.vibestack/projects/$SLUGWrite a one-line summary to ~/.vibestack/projects/{slug}/{user}-{branch}-design-audit-{datetime}.md with a pointer to the full report in $REPORT_DIR.
Per-finding additions (beyond standard design audit report):
Summary section:
PR Summary: Include a one-line summary suitable for PR descriptions:
"Design review found N issues, fixed M. Design score X → Y, AI slop score X → Y."
If the repo has a TODOS.md:
{{include lib/snippets/capture-learnings.md}}
git revert HEAD immediately.~30 seconds. Free. No account. Every finding cites a rule and a line of evidence.