tsaol/awesome-claude/ui-test-guard

Claude Code and agent skill by tsaol/awesome-claude

Trust tier 3
  • community
Source check pending

Checking that the SKILL.md file is still in the repository.

A Stop hook that catches Claude when it claims a UI change is "done", "deployed", or "verified" without showing evidence that a real-browser UI test actually passed. Stops the curl + grep illusion of testing.

Install

npx vskill@latest install tsaol/awesome-claude/ui-test-guard

SKILL.md

ui-test-guard — Stop Hook for Honest UI Testing

A Claude Code Stop hook that intercepts replies claiming a UI change is complete and asks: did you actually run a real-browser test? If not, it injects a system-reminder so Claude has to either run the test or admit it skipped.

The problem

Claude will happily report a UI change as "deployed and verified" after running only curl | grep "expected text". Curl can confirm the server returns a 200 with the right string in its body, but it cannot catch:

  • CSS layout breakage
  • React hydration errors
  • RSC flight payloads served as raw text instead of rendered HTML
  • Blank screens caused by JS runtime errors
  • Visual regressions
  • Missing fonts, broken images, overflow, mobile-only bugs

A user can spend hours trusting "verified" reports that were never actually verified.

The fix

A Stop hook scans Claude's last reply. If it contains:

  • A claim word: deployed, verified, done, shipped, live, tested, complete, works, ALL PASSED
  • AND a URL or known web route: https://..., /login, /dashboard, /portfolio, etc.
  • AND no evidence of a real-browser test: ui-test, run_tests.py, ALL PASSED, playwright, cypress

…the hook returns exit 2 with a reminder. Claude sees the reminder on the next turn and has to either run the test or explicitly say it skipped.

How it works

PhaseWhat happens
Stop event firesAfter every Claude reply is composed
Hook reads transcriptPulls the last assistant message text via jq
Three regexes evaluatedCLAIM_RE AND URL_RE AND NOT EVIDENCE_RE
If all trueexit 2 + system-reminder via stderr
Otherwiseexit 0, silent pass

Fail-open by design: if jq is missing, the transcript is unreadable, or anything else goes wrong, the hook exits 0. No false positives blocking real work.

Install

1. Copy the hook
bash
mkdir -p ~/.claude/hooks/ui-test-guard
cp skills/ui-test-guard/hooks/ui-test-guard.sh ~/.claude/hooks/ui-test-guard/
chmod +x ~/.claude/hooks/ui-test-guard/ui-test-guard.sh
2. Register in settings.json

Add this to ~/.claude/settings.json under hooks:

json
{
"hooks": {
"Stop": [
{
"hooks": [
{
"type": "command",
"command": "/home/<you>/.claude/hooks/ui-test-guard/ui-test-guard.sh",
"timeout": 5
}
]
}
]
}
}

See settings.example.json for the project-relative path version.

3. Verify
bash
# Synthetic transcript that should trigger
mkdir -p /tmp/guard-test
cat > /tmp/guard-test/bad.jsonl <<'EOF'
{"type":"assistant","message":{"content":[{"type":"text","text":"I deployed the fix to /dashboard and verified it works."}]}}
EOF
echo '{"transcript_path":"/tmp/guard-test/bad.jsonl"}' | bash ~/.claude/hooks/ui-test-guard/ui-test-guard.sh
echo "exit=$?"
# Expected: prints reminder to stderr, exit=2

Customize the regexes

Override any regex via environment variables before the hook runs. Useful when you want to scope to a specific project URL:

Env varDefaultExample override
UI_TEST_GUARD_CLAIM_RE`(deployedverified...)``(deployedshipped)` for stricter
UI_TEST_GUARD_URL_REgeneric web routes + http URLs(myapp\.example\.com) for project scope
UI_TEST_GUARD_EVIDENCE_RE`(ui-testrun_tests\.pyALL PASSED...)`add your team's test harness name
UI_TEST_GUARD_LOG/tmp/ui-test-guard.log/var/log/...

Wrap the hook in a wrapper script to apply the env, e.g.:

bash
#!/bin/bash
export UI_TEST_GUARD_URL_RE='(myapp\.example\.com|/dashboard|/admin)'
exec ~/.claude/hooks/ui-test-guard/ui-test-guard.sh

Pair this with a real-browser test runner

This hook only nags. It does not run the test. You still need a test harness. Pairs well with:

  • ui-test skill (AWS AgentCore Browser, in this repo)
  • Playwright
  • Cypress
  • Selenium

The EVIDENCE_RE matches the names of the most common harnesses, so it stays quiet when any of them are mentioned in the reply.

Why a Stop hook, not PreToolUse

Two design choices were considered:

Stop hook (this skill): soft, advisory. Reminds Claude after the fact. Does not block any tool. Lets Claude finish a thought, then nudges. Best for repeated education.

PreToolUse hook (alternative): hard block. Refuses git commit or aws ssm send-command if recent test results don't show pass. Stronger, but risks blocking legitimate non-UI work and frustrating the user.

This skill picks the soft path. Upgrade to PreToolUse only if Stop reminders aren't enough.

File layout

ui-test-guard/
├── SKILL.md # this file
├── settings.example.json # hooks block to merge into settings.json
└── hooks/
└── ui-test-guard.sh # the hook itself (one Bash script)

Limitations

  • Only as good as the regexes. If Claude phrases its claim creatively, the hook won't fire.
  • Reads the JSONL transcript — sensitive to changes in Claude Code's transcript schema. Tested on Claude Code 2.x.
  • One hook per Stop event. If you have other Stop hooks, register them all in the same array.

Security

  • Security scanPassed, 90 of 100Pattern checks on the skill's files.
  • Model reviewPassed

Quality evaluation

  • Task evaluationNot runNo evaluation yet. Run one in Skill Studio.

Source

Popularity

Repository stars
62
Repository forks
4
7-day trend score
21

Stars and forks are for the whole GitHub repository, not this skill alone. Not refreshed yet.

Works with

Any agent vskill installs to: 56 targets in all. These 39 have a page on this site.

  • Claude Code
  • Cursor
  • GitHub Copilot
  • Windsurf
  • Codex
  • Gemini CLI
  • Cline
  • Amp
  • Roo Code
  • Goose
  • Continue
  • Kilo Code
  • Junie
  • Trae
  • OpenHands
  • Qwen Code
  • AI Agent
  • Tabnine Chat
  • Sourcegraph Cody
  • Amazon Q
  • Firebase Genkit
  • Sweep
  • Devin
  • Phind
  • Mentat
  • Claude Desktop
  • Aider
  • GPT Pilot
  • Plandex
  • bolt.new
  • v0
  • Replit Agent
  • Anse
  • TypingMind
  • BetterChatGPT
  • LibreChat
  • Warp AI
  • Pieces
  • Fig AI
Embed badge
vskill VERIFIED badge
[![vskill VERIFIED](https://verified-skill.com/api/v1/skills/tsaol/awesome-claude/ui-test-guard/badge)](https://verified-skill.com/skills/tsaol/awesome-claude/ui-test-guard)

Something wrong with this skill or its page? Tell us.