From rvst
Reference for every RVST CLI mode and test-harness command. Use whenever you need to validate layout, drive a user interaction, or investigate a render bug without a visible window.
How this skill is triggered — by the user, by Claude, or both
Slash command
/rvst:rvst-cliThe summary Claude sees in its skill listing — used to decide when to auto-load this skill
RVST hosts (typeaway, rvst-app, any downstream app) ship four headless
RVST hosts (typeaway, rvst-app, any downstream app) ship four headless modes. Every one is a way to see what the user sees without opening a window. Prefer them over manual launches.
--dump · DOM + layout treetarget/blitz/release/<bin> --dump path/to/app.js path/to/app.css
Prints every Blitz DOM node: id, tag, class/id attributes, computed width/height/position, display mode, bg/fg colors, padding. Text nodes show their content preview.
Use when:
WxH @ (x,y))Viewport is fixed at 640×400 in dump mode. That's fine for layout
sanity; use --ascii for realistic viewports.
--snapshot · structured JSONtarget/blitz/release/<bin> --snapshot app.js app.css
Prints a SceneSnapshot as JSON. Same info as --dump but machine-readable —
the shape is rvst_snapshot::SceneSnapshot. Pipe through jq to extract:
... --snapshot | jq '.nodes[] | select(.attrs.id=="typeaway-editor")'
Use for automated tests and diffing.
--ascii · rendered layout visualizationtarget/blitz/release/<bin> --ascii app.js app.css
target/blitz/release/<bin> --ascii --view=a11y app.js app.css
Runs the resolver at 1280×800 and prints a 120×40 ASCII art rendering of
the node boxes, plus a compact tree. --view= options include semantic
(default), a11y, tag, text.
Use when:
--test · interactive JSON protocolecho '{"cmd":"snapshot"}' | target/blitz/release/<bin> --test app.js app.css
This is the workhorse. Reads one JSON command per line from stdin, prints
one JSON result per line on stdout. Starts with {"ready":true,"node_count":N}.
Handles everything interactive.
All commands take cmd (name) + params (object). Listed by category.
| cmd | params | returns |
|---|---|---|
snapshot | — | {node_count, viewport_w, viewport_h, diagnostics_count, nodes} |
find | {text?, role?, class?} | matching nodes |
query | {selector} | nodes matching CSS selector |
explain | {id} | computed style + layout box |
computed_styles | {id} | just the styles |
input_state | {id} | value, selection, cursor for form fields |
| cmd | params |
|---|---|
click | {id, x?, y?} |
scroll | {id, dx?, dy?} |
hover | {id, x?, y?} |
type | {id, text} — fires keypress events |
focus | {id} |
navigate | {url} |
| cmd | params |
|---|---|
dispatch_event | {type, extra?} — fires a synthetic document-level event |
eval | {script} — executes JS in the QuickJS runtime; set globalThis.__rvst_test_result to return data |
| cmd | params |
|---|---|
ascii | {view?, width?, height?} |
screenshot | {path} — renders to PNG |
compare_pixels | {a, b, tolerance?} |
| cmd | params |
|---|---|
analyze | — runs visual-audit + spacing-audit bundle |
suggest_fixes | — heuristic fixes for common issues |
visual_audit | — contrast, alignment, overflow |
spacing_audit | — margin/padding consistency |
stacking_order | {id} |
compare_layout | {mark} |
| cmd | params |
|---|---|
assert_visible | {id} |
assert_clickable | {id} |
why_not_visible | {id} — explains why a node is hidden |
hit_test | {x, y} — what node is at these coords |
list_handlers | {id} — what events does this node listen to |
| cmd | params |
|---|---|
snapshot_mark | {name} — save current state under a label |
diff | {mark} — compare current to a saved mark |
| cmd | params |
|---|---|
wait | {ms} |
close | — |
| cmd | params |
|---|---|
__test_panic | — deliberately panics; used to exercise the panic overlay |
# Snapshot the baseline
target/blitz/release/<bin> --snapshot app.js app.css > /tmp/before.json
# Change the CSS, rebuild
npm run build
target/blitz/release/<bin> --snapshot app.js app.css > /tmp/after.json
# Diff (jq is the easy approach)
diff <(jq -S '.nodes[] | {id,tag,layout}' /tmp/before.json) \
<(jq -S '.nodes[] | {id,tag,layout}' /tmp/after.json)
(
cat <<'CMD'
{"cmd":"eval","params":{"script":"globalThis.__clicked=0;document.addEventListener('click',()=>{globalThis.__clicked++})"}}
CMD
cat <<'CMD'
{"cmd":"click","params":{"id":<rvst-id>}}
CMD
cat <<'CMD'
{"cmd":"eval","params":{"script":"globalThis.__rvst_test_result=String(globalThis.__clicked)"}}
CMD
echo '{"cmd":"close"}'
) | target/blitz/release/<bin> --test app.js app.css
Expect "result":"1" — otherwise the handler is not wired.
echo '{"cmd":"why_not_visible","params":{"id":<rvst-id>}}' \
| target/blitz/release/<bin> --test app.js app.css
(
echo '{"cmd":"snapshot_mark","params":{"name":"pre"}}'
echo '{"cmd":"dispatch_event","params":{"type":"rvst:hmr-message","extra":{"data":"{\"type\":\"update\",\"updates\":[]}"}}}'
echo '{"cmd":"diff","params":{"mark":"pre"}}'
echo '{"cmd":"close"}'
) | target/blitz/release/<bin> --test app.js app.css
--ascii or
--test would answer the same question in 200ms. You can't see the
window. The validation tools are how you see it.~/Library/Caches/typeaway/last-panic.log.
A silent abort is not a passing test.--dump
(640×400) and --ascii (1280×800) both. Responsive bugs hide in the gap.Guides creation, editing, and verification of skills for AI coding agents using test-driven development with subagent scenarios. Use when authoring or debugging skills.
npx claudepluginhub shinyobjectz-sh/rvst --plugin rvst