Skip to main content
Glama
Brandon-35
by Brandon-35

webshot-mcp

Give your agent eyes — without giving it a browser or your network. An MCP server with two tools, screenshot and page_text, that connects to a Chrome you already have running (over CDP) and captures full pages or single elements. No browser is ever launched or downloaded; private-network targets are blocked by an SSRF-aware URL policy.

Why this exists

Two lessons from running visual check → fix loops with coding agents:

  1. Launching a browser per screenshot is the slow, flaky way. A persistent headless Chromium (Docker sidecar, CI service, your desktop Chrome with --remote-debugging-port) is warm, shared, and reliable. The missing piece is a disciplined client: connect over CDP, open a fresh context per shot, close only what you opened, never kill the shared browser. That discipline is this repo.

  2. A screenshot tool inside your network is an SSRF proxy with a camera. An agent that can be talked into "screenshot http://169.254.169.254/…" or http://redis.internal:6379/ will happily photograph your cloud metadata endpoint. So the URL policy blocks loopback, RFC-1918, link-local, CGNAT, and v6-local targets — including hostnames that resolve to them — unless you allowlist the hostname explicitly. Local dev servers are the legitimate exception, and you name them one by one.

Quick start

npm install
npm test        # URL-policy test suite — no browser needed
npm run demo    # policy walkthrough + a real screenshot if a CDP Chrome is reachable

Get a CDP-enabled Chrome (any one of):

# your installed Chrome, headless
chrome --headless --remote-debugging-port=9222 --remote-debugging-address=127.0.0.1 about:blank

# or a Docker sidecar you keep running
docker run -d -p 127.0.0.1:9222:9222 chromedp/headless-shell

Wire into Claude Code:

claude mcp add webshot \
  -e WEBSHOT_CDP_URL=http://127.0.0.1:9222 \
  -e WEBSHOT_ALLOW_HOSTS=localhost,127.0.0.1 \
  -- npx tsx src/server.ts

Then ask the agent things like "screenshot the hero section of localhost:5173 — just .hero — and tell me what's off": selector crops to one element, which keeps the agent's attention (and your tokens) on the part under discussion instead of a 4,000-px page.

Tools

Tool

Contract

screenshot

url, optional selector (element crop), fullPage, viewport width/height, settleMs. Returns the PNG as MCP image content + {finalUrl, title, httpStatus}. Refuses to capture HTTP ≥ 400 — a screenshot of an error page silently poisons whatever the agent does next.

page_text

Body innerText — the cheap check when the agent needs to read, not see. Same URL policy.

Design notes

  • Fresh context per shot, shared browser for life. Contexts are cheap and isolated (cookies, cache, viewport); the browser is expensive and shared. browser.close() on a CDP connection disconnects without killing the remote browser — the server can restart all day without touching Chrome.

  • DNS is checked, rebinding is documented. Non-IP hostnames are resolved and every returned address re-verified against the private ranges. A malicious DNS server that answers differently on the browser's own second resolution (classic rebinding) is out of scope for a screenshot tool — noted here rather than hand-waved.

  • deviceScaleFactor: 2 — retina captures, because agents (and humans) misread blurry text in screenshots more often than you'd think.

  • Policy is fail-closed and testable. evaluateUrl is a pure function with the entire threat table in its test file; the server never calls the browser before the policy says yes.

Stack

TypeScript · @modelcontextprotocol/sdk (stdio) · playwright-core (CDP client only — no bundled browsers) · zod · vitest.

License

MIT © Brandon Ta

-
license - not tested
-
quality - not tested
C
maintenance

Maintenance

Maintainers
Response time
Release cycle
Releases (12mo)
Commit activity

Resources

Unclaimed servers have limited discoverability.

Looking for Admin?

If you are the server author, to access and configure the admin panel.

Related MCP Connectors

  • Read a URL as clean markdown, screenshot a website, url to PDF. Web access for agents, no signup.

  • Generate images, GIFs, and PDFs from HTML, URLs, or templates — from your AI agent.

  • Screenshots, PDFs and Markdown from any URL or HTML for AI agents, via the SnapForge API

View all MCP Connectors

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/Brandon-35/webshot-mcp'

If you have feedback or need assistance with the MCP directory API, please join our Discord server