Skip to main content
Glama

claude-preview-mcp

Dev-server lifecycle + Chrome browser automation, as an MCP server. The preview_* tool family that any MCP-compatible agent can use.

This is the Anthropic Claude_Preview plugin re-implemented as a standalone MCP server so it works in Claude Code, OpenCode, Kilo Code, and any other MCP-compatible agent — with one canonical launch.json per project.

The repo ships the patched-upstream source (TypeScript) + pre-built JS, so installs don't need a build step. A single install.sh handles all three target agents.


What you get

mcp__Claude_Preview__preview_* tools (14 total):

Tool

What it does

Browser?

preview_start

Spawn a dev server from .claude/launch.json (PID, ready detection, port inference)

preview_stop

SIGTERM / SIGKILL a running server

preview_list

List configured + currently-running servers

preview_logs

Last N lines of combined stdout+stderr (default 80, max 500)

preview_navigate

Open a URL in a headless Chrome

yes

preview_screenshot

PNG/JPEG screenshot, base64 inline or saved to disk

yes

preview_snapshot

A11y tree (tag, role, name, value, focusable)

yes

preview_inspect

DOM element by CSS selector (rect, attrs, text, display)

yes

preview_click

Click an element by CSS selector

yes

preview_fill

Fill an input/textarea/select by CSS selector

yes

preview_eval

Run JavaScript in the page, return JSON-serializable result

yes

preview_console_logs

Captured console messages (filter by substring or type)

yes

preview_network

List captured requests, or fetch one response body by URL

yes

preview_resize

Resize the preview viewport

yes

Browser-required tools use the system's Chrome (/Applications/Google Chrome.app on macOS, google-chrome / chromium on Linux).


Related MCP server: @nimbus21.ai/chrome-devtools-mcp

# 1. Clone
git clone https://github.com/MichaelTendoSsemwanga/claude-preview-mcp
cd claude-preview-mcp

# 2. Pick your agent
./scripts/install.sh claude-code   # one-line: plugin cache, plugin.json, done
./scripts/install.sh opencode      # ~/tools + ~/.config/opencode/opencode.jsonc
./scripts/install.sh kilo          # ~/tools + ~/.kilocode/mcp_settings.json
./scripts/install.sh all           # all three

install.sh:

  • Copies the committed build/ into the right agent location

  • Provisions node_modules/ (just @modelcontextprotocol/sdk + puppeteer-core, ~25MB) into the same location via a temp scratch dir — so the repo itself stays light

  • Writes / merges the MCP config (uses jq for an atomic JSON merge that preserves any existing config)

  • Restores .claude-plugin/plugin.json for Claude Code

Per-agent activate

Agent

Activate

Claude Code

restart; tools appear as mcp__Claude_Preview__preview_*

OpenCode

opencode mcp list → should show ✓ Claude_Preview connected

Kilo Code

VS Code: Cmd-Shift-P → "Developer: Reload Window"

  • One-line setup (drop the plugin into the cache, no MCP config to touch)

  • Plugin lifecycle is managed by Claude Code — auto-spawned on launch, auto-killed on exit

  • The plugin.json uses ${CLAUDE_PLUGIN_ROOT} so the install path is stable across moves/upgrades

  • Same launch.json file works in Claude Code's built-in preview (which uses the configurations format) AND this MCP

Why other agents

OpenCode and Kilo don't have a plugin system. They register MCP servers by hand-rolling a config file, and they don't ship a configurations preview concept. This MCP bridges that gap: they get the same dev-server workflow, using the same launch.json, just with the extra hop of an MCP server entry in their config.


.claude/launch.json (the only project-side file)

The MCP server reads dev-server definitions from <project>/.claude/launch.json, walking upward from the agent's process.cwd() until it finds one. Two formats supported, picked in priority order:

Claude Code format (preferred)

{
  "version": "0.0.0",
  "configurations": [
    {
      "name": "back-office",
      "runtimeExecutable": "npm",
      "runtimeArgs": ["run", "dev"],
      "port": 5173
    },
    {
      "name": "tkt-backend",
      "runtimeExecutable": "bash",
      "runtimeArgs": ["-c", "cd /Users/loft/tkt-backend && bun run --hot src/index.ts"],
      "port": 3001
    }
  ]
}

Fields: name, runtimeExecutable, runtimeArgs (array), port, autoPort (advisory), env (object), url (optional — overrides the synthesized http://localhost:{port}).

The MCP translates internally: runtimeExecutablecommand, runtimeArgsargs, porturl.

Legacy servers format (still supported)

{
  "servers": [
    {
      "name": "web",
      "command": "npm",
      "args": ["run", "dev"],
      "url": "http://localhost:3000",
      "readyPattern": "Local:"
    }
  ]
}

Use this if you have a project that already used it. Don't mix the two formats in the same file (only configurations is read when both are present).


Repo layout

claude-preview-mcp/
├── .claude-plugin/
│   └── plugin.json          # Claude Code plugin manifest
├── src/                     # TypeScript source (patches live here)
│   ├── index.ts             #   MCP server entry, tool definitions, handlers
│   ├── process-manager.ts   #   launch.json parser + dev-server spawn
│   ├── browser-manager.ts   #   headless Chrome session
│   └── schemas.ts           #   zod input schemas
├── build/                   # Pre-compiled JS (committed; don't need to build)
│   └── *.js, *.js.map
├── scripts/
│   └── install.sh           # Universal installer (claude-code | opencode | kilo | all)
├── docs/
│   └── ARCHITECTURE.md      # Claude Code plugin internals + MCP protocol details
├── package.json             # Name, deps, build script
├── package-lock.json        # Locked dep versions
├── tsconfig.json            # TS compiler config (Node16 ESM, strict)
├── .gitignore
├── LICENSE                  # MIT
└── README.md                # this file

Develop / rebuild

# Edit src/*.ts
npm install            # one time, fetches dev deps
npm run build          # tsc → build/
git add build/ src/    # commit both

The install script will use the freshly-built build/ on the next run.


Smoke test (any agent)

In the agent's session:

  1. mcp__Claude_Preview__preview_list → returns {configured: [...], running: []}

  2. mcp__Claude_Preview__preview_start {"name": "<one-of-your-configurations>"} → starts it

  3. mcp__Claude_Preview__preview_list → now shows it in running[]

  4. (browser) preview_navigate {"url": "http://localhost:5173"} then preview_snapshot

  5. preview_logs {"name": "<name>", "tail": 50} → see the dev-server output

  6. preview_stop {"name": "<name>"} → SIGTERM

Or from the shell, no agent needed:

node ./build/index.js &
sleep 1
# Talk JSON-RPC to stdin/stdout (use the test script in /tmp, or any MCP client)
kill %1

What's patched vs upstream

The Anthropic Claude_Preview plugin (this repo's source) ships with four bugs that surface under modern MCP clients (Claude Code, OpenCode 1.17+ — both use protocol 2025-11-25). All four are fixed in src/:

#

Symptom

Fix location

4a

preview_network schema malformed (anyOf at top level) → whole tool list rejected

src/index.ts

4b

Only reads legacy servers format, ignores Claude Code's configurations

src/process-manager.ts

4c

preview_eval "() => ({foo:1})" returns undefined → result validation fails

src/index.ts

4d

preview_screenshot returns invalid Base64 (Uint8Array.toString pitfall)

src/index.ts

4e

preview_fill "Illegal invocation" on non-input elements

src/index.ts

Each patch has an inline comment explaining the original cause. See docs/ARCHITECTURE.md for the long version with the diagnostic traces.


Caveats

  • One Chrome per MCP server. If you have this AND chrome-devtools-mcp registered, each spawns its own Chrome instance. Don't run both pointing at the same page.

  • One dev server per port. Two preview systems (Claude Code's built-in + this MCP) can't both bind the same port. Use one per project.

  • Process state isn't shared. Servers started via this MCP die when the MCP process exits. Claude Code's built-in preview is more durable.

  • launch.json walks up. If you run an agent from ~/ expecting project launch files, it won't — cd into the project root first.

  • Per-agent permissions. Most agents prompt on first tool use. Allowlist Claude_Preview (or each individual tool) to stop the prompts. The Kilo Code install includes an alwaysAllow block by default.

  • macOS Chrome path is hard-coded in browser-manager.ts (looks for /Applications/Google Chrome.app/Contents/MacOS/Google Chrome first, then google-chrome on PATH). Override with CHROME_PATH env var.


License

MIT — see LICENSE. Bundled dependencies (@modelcontextprotocol/sdk, puppeteer-core) retain their own licenses.

A
license - permissive license
-
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.

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/MichaelTendoSsemwanga/claude-preview-mcp'

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