| name | vera-browser |
| description | Render pages with headless Chromium: screenshot, mobile/responsive layout review, viewport sweep, post-JS DOM, eval JS. Use for any visual/design/frontend QA task — see how a page actually looks rather than read its source. Triggers on: screenshot, render, mobile layout, responsive, viewport, breakpoint, design review, visual review, frontend QA, what does X look like, see the page, hydrated DOM, SPA, headless browser. |
vera-browser
A headless-Chromium CLI on PATH. Use it whenever the task needs to see or render a page rather than just read its source.
When to use
- Screenshotting a URL at a specific viewport (mobile / desktop / responsive sweep)
- Reviewing mobile layout, responsive breakpoints, design changes
- Visually verifying a frontend fix landed correctly
- Extracting the post-JS-execution DOM of a SPA (React, Vue, Next, etc.)
- Probing page state with
document.title, computed styles, element counts, etc.
When NOT to use
- Just need raw HTML / readable content →
web_fetch is faster and lighter.
- Pure CSS reasoning from source → read the stylesheet directly.
- Anything that needs interactive auth, form submission, or multi-step flows — deferred, not yet supported.
Subcommands
vera-browser screenshot <url> [--viewport <preset>] [--out <path>] [--wait-for <sel>] [--no-full-page] [--timeout <ms>]
vera-browser dom <url> [--viewport <preset>] [--wait-for <sel>] [--timeout <ms>]
vera-browser eval <url> --script <js> [--viewport <preset>] [--wait-for <sel>] [--timeout <ms>]
Run vera-browser --help for the full reference.
Viewport presets
Default: desktop-1280. Mobile presets set isMobile, hasTouch, and a real iOS/Android UA.
| preset | css size | notes |
|---|
iphone-se | 375 × 667 | small modern phone |
iphone-14-pro | 393 × 852 | mid modern phone |
pixel-7 | 412 × 915 | large android |
desktop-1280 | 1280 × 800 | laptop default |
desktop-1920 | 1920 × 1080 | full HD desktop |
PNG dimensions will be css × DPR (e.g. iphone-se → 750 × 1334 @ 2× DPR). That's correct.
The read-back pattern (most common flow)
vera-browser prints the screenshot path on stdout. Pipe it straight into read to actually see the rendered page:
vera-browser screenshot https://example.com --viewport iphone-se --out /tmp/shot.png
Then:
read /tmp/shot.png
The PNG comes back as an image attachment in your context. Reason about what you see, then act.
Pattern: mobile-layout audit
Loop the four most-useful viewports, read each shot, then write up findings:
URL=https://agent-vera.com
for vp in iphone-se iphone-14-pro pixel-7 desktop-1280; do
vera-browser screenshot "$URL" --viewport $vp --out /tmp/audit-$vp.png
done
Then read /tmp/audit-iphone-se.png, read /tmp/audit-iphone-14-pro.png, etc., and produce a per-viewport finding list. Never caveat with "I can't actually render the page" — you can. Use this pattern.
Pattern: SPA post-hydration DOM
For React/Vue/Next sites, web_fetch only sees the empty shell. Use dom to get the hydrated tree:
vera-browser dom https://react.dev --wait-for main --timeout 20000
The HTML printed to stdout is what the user actually sees in their browser, not the SSR skeleton.
Pattern: probing page state
For one-off questions ("what's the page title?", "how many product cards rendered?"):
vera-browser eval https://shop.example.com --script "document.querySelectorAll('.product-card').length"
vera-browser eval https://example.com --script "document.title"
The result is JSON-stringified. Strings come back quoted, numbers/booleans/objects as-is.
Local dev servers
Anything reachable from inside the agent container works, including localhost:
python3 -m http.server 8000 &
vera-browser screenshot http://localhost:8000 --out /tmp/local.png
Wait strategies
- Default (no
--wait-for): navigates with networkidle. Best for static-ish pages.
--wait-for <css-selector>: navigates with domcontentloaded, then waits for the selector. Use this for SPAs — many never go fully networkidle and the default wait will burn the timeout.
Defaults & gotchas
- Timeout: 30 s per op. Override with
--timeout <ms>. Unreachable hosts fail fast (net::ERR_NAME_NOT_RESOLVED, exit 1).
- Screenshots are full-page by default. Use
--no-full-page if you only want the fold (above-the-scroll viewport area).
- Default output path:
/tmp/vera-browser/<ts>-<slug>.png. Always read it back from the printed stdout path — don't guess.
- Eval is subject to page CSP. Strict CSP pages may block
new Function(). Falls back gracefully — you'll see an error from the page, not a hang.
PLAYWRIGHT_BROWSERS_PATH=/opt/ms-playwright is set in the image — you don't need to export it.
- Exit codes: 0 success, 1 runtime error (timeout, navigation failure, CSP block, etc.), 2 CLI usage error. Always check.
Anti-patterns
- ❌ Captioning a screenshot you didn't actually
read. Take it, read it, then describe what's in it.
- ❌ Using
eval for things dom already gives you (selectors, text content of large regions).
- ❌ Screenshotting one viewport when the task says "mobile audit" — always sweep at least 3 mobile presets.
- ❌ Reaching for
web_fetch first on a known SPA. Use dom directly.