mcpField
P
Playwright E2E MCP

Playwright E2E MCP

Local
github.comDeveloper Tools0Updated today

About Playwright E2E MCP

Playwright E2E MCP is an MCP server and agent skill for diagnosing and fixing Playwright tests. It analyzes failure evidence, verifies proposed fixes by rerunning tests, and also handles CI reports, test history, and flaky-test investigations.

Key features

  1. 01Run Playwright tests and diagnose failures
  2. 02Read CI reports, traces, and failure snapshots
  3. 03Verify fixes by rerunning and revert failures
  4. 04Analyze flaky tests and run history
  5. 05Audit tests and find breaking commits
  6. 06Check accessibility and Web Vitals

Use cases

  1. 01Diagnose test failures and app errors from traces
  2. 02Fix locators and rerun tests to verify changes
  3. 03Investigate CI failures or find a regression commit
  4. 04Identify flaky tests and review test changes

MCP support

As an MCP server and agent skill, it provides compatible clients with tools for running, diagnosing, fixing, and auditing Playwright tests. It can be configured locally for multiple MCP clients; the README also describes a Streamable HTTP bridge for remote-only clients.

Configuration

Local server config is the same for every client. Copy it into your client’s MCP config file.

mcp.json · Universal config
{
"mcpServers": {
"xsignon-secure-e2e": {
"command": "npx",
"args": [
"-y",
"playwright-e2e-mcp"
]
}
}
}
Run commandnpx -y playwright-e2e-mcp

Local servers need a runtime on your machine (e.g. Node.js 18+). Config file locations differ by client; see your client’s docs.

Packages
npmplaywright-e2e-mcp0.7.0

Tools

No tool list yet

Local servers expose tools only once running on your machine, and the maintainer has not provided a tool list.

Details

From the project README

playwright-e2e-mcp logo: a heartbeat line that ends in a green check

playwright-e2e-mcp

The test doctor for AI agents.
Your Playwright test fails. Your AI finds out why, fixes it, and proves the fix works.

npm npm downloads CI MCP Registry License: MIT

Install in Cursor Install in VS Code Add to Claude Desktop

An agent runs the failing checkout test, suggest-fix proposes a locator proven on the page at failure, and the applied fix is re-run and verified green

⭐ If it saves you a debugging session, a star helps other Playwright users find it.

Getting started · Tools · Tool reference · GitHub Action · Configuration · Changelog · Contributing

An MCP server and agent skill that gives your AI assistant (Claude, Cursor, VS Code Copilot, Gemini, Codex) a full Playwright toolkit: a test runner, a failure detective and a fixer that checks its own work. Other tools let an AI click around a browser. This one lets it keep your test suite green.

❌ Without it / ✅ With it

Without it, your agent sees Timeout 5000ms exceeded waiting for getByTestId('checkout'), guesses a new selector, edits the test and hopes. Or it "fixes" the test around a real bug.

With it, your agent reads the page as it was when the test failed, swaps in a locator proven unique on that page, re-runs the test, and keeps the edit only if it passes. When the button is really gone, it tells you it's an app bug.

run-test ──────┐
load-report ───┴─▶ get-failure ──▶ suggest-fix (apply + re-run) ──▶ green
 (CI job report)        │                 └─ refuses when the element is really gone (app bug)
                        └─ DOM at failure, failed requests, console errors
every run ──▶ analyze-history (flaky / broken / slow / which commit broke it)
test code ──▶ audit-tests (flake risks, ranked by history, verified rewrites)
red at HEAD ─▶ bisect-failure (runs it across git history, names the breaking commit)

Key features

  • Fixes are proven, not guessed. Every fix is re-run before it's kept, and undone if the test is still red.
  • Honest. It won't paper over a real bug to make a test pass.
  • Works on CI failures too. Load a CI job's report and traces and get the same diagnosis and fixes.
  • Flakiness with evidence. Names the flaky test, whether it's a race, shared state or test order, and the seed that reproduces it.
  • Lean. With the core tool set, finding and fixing a broken locator took about 5,500 tokens versus about 7,900 with Playwright MCP plus a shell. All 19 tools add about 16k tokens of definitions to every request, so load only the profiles you use (benchmark).
  • Free and open source. MIT, no account, no API key, no telemetry. Every tool is free; an optional paid Pro only adds hosted CI history.

🚀 What only this MCP does

Most testing MCPs let an AI drive a browser: Microsoft's Playwright MCP, Chrome DevTools MCP, ExecuteAutomation's mcp-playwright and the Selenium MCP. They're great for clicking through a page. None of them, as of October 2026, does the following. This one does:

CapabilityWhat you get
🛡️ A guard against "fixes" that check lesscheck-test-change compares a changed test with its old self and blocks a fix that went green by deleting an assertion, skipping the test or adding .only; it warns on weaker matchers, hard waits, forced clicks and swallowed errors. The same check runs in CI as guard
🧊 Quarantine with an owner and an expiryquarantine keeps a flaky test running and reported while its failure stops blocking the build, with who fixes it, why, and the date it blocks again
🎯 Find the commit that broke a testbisect-failure runs the test across your git history, in a temporary worktree that leaves your checkout alone, and names the first bad commit with its diff and the failure
🧪 Flake-risk audit of your test codeaudit-tests finds hard waits, one-shot assertions, missing awaits and fragile selectors. It ranks them by how flaky those tests really were, then applies the safe rewrites and re-runs them to prove them
✅ Fixes that prove themselvessuggest-fix swaps in a locator proven unique on the DOM at failure, re-runs the test and reverts if it's still red. It refuses to patch over a real app bug
🔬 Flaky-test verdicts with evidencediagnose-flaky repeats tests with retries off and tells a race from shared state from test order, naming the test it depends on and the seed that reproduces it
📈 Memory of every runanalyze-history ranks flaky, regressed and broken tests, groups failures by cause, tracks slow tests and names the commit where each one went bad
🏗️ Diagnose CI failures locallyload-report loads a CI job's report and traces (sharded too), so the same diagnosis and verified fixes work on failures from CI
💬 One-click fixes on pull requestsThe GitHub Action verifies each fix in CI and posts it as a suggested change reviewers apply with one click
♿⚡ Audits that hand back testsAccessibility (axe-core) and Web Vitals audits return verified locators for each problem plus a ready regression or budget test

It works alongside a browser MCP rather than replacing it: that one drives the page, and this one keeps your suite green.

What you can ask

You ask your AI…It does this
🏃"Run my tests"Runs the suite and reports every failure with its file, line, cause and a fix hint. One root cause breaking 30 tests shows up as one problem.
🔍"Why did this fail?"Reads Playwright's trace: the page at the moment of failure, the broken request, the console error. No guessing.
🛠️"Fix it"Swaps in a locator proven unique on the page, re-runs the test, and undoes the edit if it's still red. If the button is really gone, it tells you it's an app bug instead of hiding it.
🎲"Is this test flaky?"Re-runs it many ways (repeated, alone, in random order) and names the exact test and seed that cause the flake.
📈"What's been breaking lately?"Keeps a local run history and separates flaky, newly broken and always-broken tests; shows the slowest tests, stability by day and the commit where each test went bad.
☁️"Why did CI fail?"Loads the CI job's report (or merges sharded blob reports), maps its paths onto your checkout and finds the traces in the downloaded artifact, so the same diagnosis and fixes work on CI failures.
✍️"Write a test for this flow"Walks the steps on the live page first, writes a spec that replays them with assertions on where the flow landed (URL and accessibility snapshot), and runs it once to prove it passes.
♿"Check this page for accessibility"Runs axe-core (WCAG 2.2 AA) and returns each problem with a ready-to-paste locator and regression test.
⚡"Why is this page slow?"Measures Web Vitals (LCP, CLS, INP, TBT) on desktop or a throttled phone, names the slow element and the elements that jump, and hands back a budget test.
🧪"Show me the error state"Mocks API responses (500s, empty lists, slow calls) so the AI can inspect, audit or measure states that are hard to reach.
🔑"Log in and save the session"Logs in once (password from an environment variable, authenticator code generated from the TOTP secret), checks the session works and saves it for tests and page tools; reuses it until it expires. The password never passes through the chat.
🛡️"Did that fix cheat?"Compares the changed tests with git and blocks a fix that passes by deleting assertions or skipping tests.
🧊"Quarantine this flaky test"Keeps it running and reported, stops it failing the build, with an owner and an expiry date.
🔐"Test the page after login"Works behind sign-in with saved sessions, headers and click/fill steps, in Chromium, Firefox or WebKit, and can record or replay network traffic from a HAR file.
🤖"Do it in CI"A GitHub Action and ci command post the diagnosis, flaky verdict and fix diffs on your PR.

Requirements

  • Node.js 22 or newer
  • A project that uses @playwright/test, with a browser installed (npx playwright install chromium)
  • Claude Code, Claude Desktop, Cursor, VS Code, Windsurf, Codex, Gemini CLI or any other MCP client

Getting started

Fastest: run this in your project root. It adds the server to every client config it finds (Claude Code, Cursor, VS Code, Gemini CLI, Codex) and installs the agent skill, leaving your other servers alone:

npx -y playwright-e2e-mcp init            # --client all | cursor,vscode … · --dry-run
npx -y playwright-e2e-mcp doctor          # checks Node, Playwright, browsers and client setup

Or let your agent do it. Paste this into any coding agent:

Install the playwright-e2e-mcp server and skill by following https://raw.githubusercontent.com/xsignon-secure/E2E/main/llms-install.md

Standard config works in most clients:

{
  "mcpServers": {
    "playwright-e2e": {
      "command": "npx",
      "args": ["-y", "playwright-e2e-mcp"]
    }
  }
}

The server uses its working directory as the project root. If your client starts it somewhere else (such as your home directory), add "env": { "PW_MCP_PROJECT_ROOT": "/path/to/your/project" }.

Claude Code

Server and skill, as a plugin:

/plugin marketplace add xsignon-secure/E2E
/plugin install playwright-e2e-mcp@xsignon-secure

Or the server only:

claude mcp add playwright-e2e -- npx -y playwright-e2e-mcp
Claude Desktop

Download the .mcpb extension from the latest release and double-click it. It ships its own dependencies, so no Node setup is needed. On install it asks for your project root: choose the project folder, not your home directory.

You can also add the standard config to claude_desktop_config.json.

Cursor

Click Install in Cursor, or go to Settings → MCP → Add new MCP server and paste the standard config. For one project only, put it in .cursor/mcp.json.

VS Code / GitHub Copilot

Click the Install in VS Code button above, or run:

code --add-mcp '{"name":"playwright-e2e","command":"npx","args":["-y","playwright-e2e-mcp"]}'
Codex
codex mcp add playwright-e2e -- npx -y playwright-e2e-mcp

A Playwright run with retries can take longer than Codex's default 60 s tool timeout. Raise the timeouts in ~/.codex/config.toml:

[mcp_servers.playwright-e2e]
command = "npx"
args = ["-y", "playwright-e2e-mcp"]
startup_timeout_sec = 60
tool_timeout_sec = 600
Gemini CLI / Qwen Code

Server and skill, as an extension:

gemini extensions install https://github.com/xsignon-secure/E2E

Or paste the standard config into .gemini/settings.json (Qwen Code: .qwen/settings.json).

Windsurf, Cline, Zed and other clients

Add the standard config to the client's MCP config file (Cline: MCP Servers → Configure). Clients that take a command, such as Zed, run npx with the arguments -y playwright-e2e-mcp.

Freebuff / Codebuff

Drop an mcp.json with the standard config into your project's .agents/ folder. This repo ships one in .agents/mcp.json, so opening the checkout attaches the server workspace-wide. Freebuff asks you to trust a repository's .agents/ on first run.

ChatGPT and other remote-only clients

Some clients only accept a remote HTTPS server. This repo ships a Streamable HTTP bridge you can host for free on Vercel, with OAuth sign-in for claude.ai connectors. See Hosted endpoint. On Vercel the page tools (inspect a page, check selectors, accessibility and Web Vitals audits) run on a bundled Chromium against public URLs. Running and fixing your own tests needs your project, so use the local install for that.

Other ways to install
RouteHow
Skill only, any agentnpx skills add xsignon-secure/E2E
MCP Registryio.github.xsignon-secure/E2E (listing); registry-aware clients find it there
Straight from GitHub, no npmnpx -y github:xsignon-secure/E2E#v0.7.0 (pin a release tag)
Release tarballnpm install -D https://github.com/xsignon-secure/E2E/releases/download/v0.7.0/playwright-e2e-mcp-0.7.0.tgz
Dockerdocker run -i --rm -v "$PWD:/work" ghcr.io/xsignon-secure/playwright-e2e-mcp (published on each release; see Development)
Local checkout"command": "node", "args": ["/path/to/E2E/dist/index.js"]
Your first prompt

Restart your client, then ask:

Run my Playwright tests and fix whatever fails.

Your agent should run the suite, read the failure, and propose a fix it has re-run. To check the setup without your own tests, ask it to run examples/sample-test.spec.ts from this repo.

What's new in 0.7

  • Log in once, safely: save-login signs in (2FA codes included) with secrets read from the environment, checks the session and saves it as a storageState file; it reuses the session until it stops working.
  • Heal guard: check-test-change and playwright-e2e-mcp guard block a test "fix" that passes by checking less (deleted assertions, skipped tests, .only).
  • Flaky-test quarantine: quarantine stops a known flaky test from failing the build for a set time, with an owner and a reason, while it keeps running and being reported.

What's new in 0.6

  • Find the commit that broke a test: bisect-failure runs the test across git history in a temporary worktree and names the first bad commit, its changes and the failure there.
  • Flake-risk audit: audit-tests finds hard waits, one-shot assertions, missing awaits and fragile selectors, ranked by real flakiness, and applies the safe rewrites with a verifying run.
  • One-click fixes on pull requests: the GitHub Action proves each fix in CI and posts it as a suggested change.
  • doctor: npx playwright-e2e-mcp doctor checks Node, Playwright, browsers and client setup.
  • Structured results: every tool returns JSON next to its Markdown, with output schemas.
  • Phones, tablets, Chrome and Edge: device presets and channel for every page tool, and a Docker image on ghcr.io.
  • Node 22 or newer is now required, and the hosted endpoint limits guessing of its key.

All release notes

Tools

ToolPurpose
run-testRun Playwright tests and return stats, failures, diagnostics and hints; reports progress, and background: true returns a run id for long suites
get-run-statusProgress or final result of a background run; can wait for it or cancel it
get-failureDeep analysis of one failure: stack, expected/actual, DOM snapshot at failure (from the Playwright trace), failed requests, console errors, next steps
load-reportLoad a run from CI: a JSON report or a folder of sharded blob reports; CI paths are mapped onto the checkout and traces found in the unpacked artifact, so get-failure, suggest-fix and diagnose-flaky work on it, and the run joins the history with its commit
suggest-fixPatch a failure: a drifted locator is replaced with one proven unique on the DOM at failure, an ambiguous one (strict mode violation) gets the unique locator of the intended match, changed copy gets the new expected text; apply: true writes it, re-runs the test and reverts if still red
inspect-pageOpen a URL headlessly (optionally signed in, after steps) and return elements with verified Playwright locators, CSS selectors, visibility, text and console output, or the accessibility snapshot with a ready toMatchAriaSnapshot assertion
list-testsList available tests (file, line, full title, projects) with filtering
validate-selectorCheck a CSS selector, Playwright selector or locator expression against a live page: validity, match count, and a sturdier verified locator for each match
generate-e2e-testScaffold a Playwright test from a description using the project's real selectors and verified locators from the live page, or walk a flow step by step on the live page and write a spec that is run once to prove it passes
compare-visual-stateVisual regression: screenshot before/after a change and report what moved and how colors shifted
audit-accessibilityRun axe-core (WCAG 2.2 AA by default) on a page, signed in or after steps, and return violations worst first with verified locators for the offending elements and a regression check
audit-performanceMeasure lab Web Vitals (LCP, CLS, TBT, FCP, TTFB, INP during steps), optionally as a throttled phone and the median of several runs; rate them or check budgets, name the LCP and shifting elements as verified locators, list heavy and render-blocking requests, and return a budget test
diagnose-flakyRun a failing test 2–10 times with retries disabled and return an evidence verdict: CONSISTENTLY FAILING, FLAKY or NOT REPRODUCING; tells parallelism and test-order bugs from races
analyze-historyRank flaky, regressed and broken tests from the local run history, group failures by cause, list the slowest tests, show stability by day, name the commit where each test went bad, or show one test's timeline
audit-testsAudit the test code for flake risks (hard waits, one-shot assertions instead of web-first ones, missing awaits, .only, force clicks, networkidle, element handles, layout selectors), ranked by how flaky those tests have been in the run history; fix: true rewrites the mechanical ones, re-runs the files and reverts if they fail
save-loginLog in once and save the session (storageState): steps with {{env:E2E_PASSWORD}} and {{totp}} (authenticator code from a secret in the environment), a check that the session works, and reuse until it expires; secrets never pass through the chat
check-test-changeHeal guard: compare changed tests with git (or a proposed fix with the file) and BLOCK deleted assertions, skipped or removed tests and .only; WARN on weaker matchers, hard waits, force: true, swallowed errors and raised timeouts or retries
quarantineQuarantine a flaky test with an owner, a reason and an expiry (default 14 days): it keeps running and being reported, but its failure no longer fails run-test or ci until the entry expires. Stored in playwright-quarantine.json
bisect-failureFind the commit that broke a test: binary-search git history between a good and a bad commit, running the test at each step in a temporary worktree (your checkout is untouched), and report the first bad commit, what it changed and how the test failed

Two prompts package the main workflows for clients that show them as slash commands: fix-failing-test and triage-flaky-tests.

Every argument and example output is in the tool reference. All tools carry MCP tool annotations (readOnlyHint, destructiveHint, …), so clients can show accurate safety prompts.

Only need the fix loop? --tools=core (or PW_MCP_TOOLS=core) exposes seven tools and cuts the tool-definition context by about three quarters. Other profiles: triage, inspect, author.

Typical workflow
  1. run-test { "testFiles": ["tests/checkout.spec.ts"] }, or { "background": true } for a long suite and get-run-status { "waitSeconds": 30 } until it finishes. For a failure from CI, download the job's artifacts and call load-report { "report": "ci-artifacts/results.json" } instead.
  2. get-failure { "index": 1 } to read the code frame, expected/actual, the DOM snapshot at failure, the failed network requests and the page's console errors.
  3. suggest-fix { "index": 1 } for a locator or copy change: review the diff, then { "index": 1, "apply": true } to write it and verify with a re-run. If it reports the element is missing, fix the app, not the test.
  4. For anything it cannot patch: inspect-page { "url": "…", "view": "locators" } (add storageState or actions to reach the right screen), then validate-selector to prove the new locator before editing.
  5. If a failure looks intermittent: diagnose-flaky { "runs": 3 } for fresh evidence, and analyze-history to see how the test behaved across earlier runs ({ "view": "commits" } names the commit where it went bad).
  6. After changing CSS or components: compare-visual-state { "url": "…", "name": "checkout" }.
  7. Re-run only what failed with run-test { "lastFailed": true } until green.

To write a new test, find the locators with inspect-page { "view": "locators" }, then call generate-e2e-test with a description and the steps of the flow; it walks them on the live page, writes the spec and runs it once. To check a page's speed or accessibility, use audit-performance and audit-accessibility.

CI: GitHub Action and ci command

The same diagnosis runs without an agent. playwright-e2e-mcp ci runs the suite (auto-retry once, so flaky tests are reported as flaky, not failed), optionally drafts suggest-fix diffs and a flaky verdict for the failures, and writes one Markdown report to stdout, to --output, and to the GitHub job summary when GITHUB_STEP_SUMMARY is set. Exit code 0 passed, 1 tests failed, 2 the run itself failed.

npx -y playwright-e2e-mcp ci --flaky-runs 3 --suggest 2 --output report.md
npx -y playwright-e2e-mcp ci --help

As a GitHub Action, it adds the report to the job summary and keeps one PR comment up to date when the run fails. On a pull request it also re-runs each failing test with its suggested fix and posts the fixes that pass as suggested changes on the failing lines, so a reviewer applies one with the Commit suggestion button (only on lines the PR changed; the rest stay in the report):

permissions:
  contents: read
  pull-requests: write   # for the PR comment and the suggested fixes
steps:
  - uses: actions/checkout@v6
  - uses: actions/setup-node@v6
    with: { node-version: 24 }
  - run: npm ci && npx playwright install --with-deps chromium
  - uses: xsignon-secure/[email protected]
    with:
      flaky-runs: 3      # 0 skips the flaky verdict
      suggest: 2         # suggest-fix diffs for the first 2 failures
      # args: --browser chromium tests/checkout

A complete, ready-to-copy workflow is available in examples/github-actions/playwright-e2e.yml, including artifact upload and commented options for guard: true and Pro Cloud.

Inputs: project-root, args, flaky-runs, suggest, comment, review, verify-fixes, guard, pro-key, pro-url, fail-on-failure, version, github-token. Outputs: exit-code, report, guard.

Quarantined tests (playwright-quarantine.json, see quarantine) are honoured here too: when every failure is quarantined and unexpired, ci exits 0 and the report lists them.

Heal guard in CI. guard: true checks the PR's changed tests against the base branch first and fails the job if a test was made to pass by checking less. Without the Action:

npx -y playwright-e2e-mcp guard --base origin/main   # exit 1 on BLOCK; --strict fails on warnings too

Configuration

Environment variables
Environment variableDefaultPurpose
PW_MCP_PROJECT_ROOTserver cwdDefault project root for every tool
PW_MCP_TOOLSallWhich tools to expose, as tool names and/or profiles, comma separated (same as the --tools= flag). Profiles: core (run, status, failure, fix, flaky, heal guard, list), triage (run, status, failure, CI report, flaky, history, test audit, bisect, quarantine, heal guard, list), inspect (page, selector, accessibility, performance, visual, login), author (list, page, selector, generate, run, login, heal guard). All nineteen tool definitions cost about 16k tokens of context per request; core costs about 5k (12k and 2.6k with PW_MCP_OUTPUT_SCHEMAS=0)
PW_MCP_OUTPUT_SCHEMASon0 leaves the output schemas out of the tool list to save context. Results still carry structuredContent (see Structured results)
PW_MCP_STORAGE_STATE—Default storageState file (inside the project) for the page tools
PW_MCP_SHUFFLE_SEEDSrandomComma-separated seeds for diagnose-flaky's order pass, to replay the orders a diagnosis reported
PW_MCP_LOGIN_ENV—Extra environment variables save-login may type through {{env:NAME}}, comma separated. Without it only E2E_*, TEST_*, PW_*, PLAYWRIGHT_* and LOGIN_* are allowed
PW_MCP_PRO_KEY / PW_MCP_PRO_URL—Optional, paid: Pro key and Pro Cloud address. CI runs are uploaded with playwright-e2e-mcp upload (or the Action's pro-key / pro-url inputs) and analyze-history merges them with local runs. Unset (the default), nothing is ever sent anywhere
PW_MCP_HISTORYon0 stops recording runs to .playwright-e2e-mcp/history.jsonl
PW_MCP_ALLOWED_ROOTS—Extra directories a caller may pass as projectRoot (:-separated, ; on Windows). Anything outside these and the default root is rejected
PW_MCP_HTTP_TOKEN—HTTP bridge only: bearer token that unlocks all tools: 16+ characters, 32+ recommended (see Hosted endpoint)
PW_MCP_ALLOWED_HOSTSlocalhost + Vercel hostnames when there is no tokenHTTP bridge only: comma-separated Host allowlist; * accepts any
PW_MCP_MAX_FAILED_AUTH20HTTP bridge only: wrong tokens or access keys one client address may send in 15 minutes before it gets 429
PW_MCP_OAUTH_REDIRECT_HOSTSany https hostHTTP bridge only: comma-separated hosts OAuth apps may return to, e.g. claude.ai,chatgpt.com; .example.com covers subdomains; localhost always works
PW_MCP_TRUST_PROXYoff (on for Vercel)HTTP bridge only: 1 trusts X-Real-IP / X-Forwarded-For from a reverse proxy in front, so the sign-in limit counts per client, not per proxy
PW_MCP_PASSTHROUGH_ENV—HTTP bridge only: comma-separated extra variables passed to test runs (e.g. BASE_URL)
PW_MCP_MAX_CHILDREN4HTTP bridge only: how many test runs and browser probes may run at once
PW_MCP_BLOCK_PRIVATE_URLSoff (on for the HTTP bridge)1 makes the URL tools refuse loopback, private-network and cloud-metadata addresses, including redirects and subresources
PW_MCP_SERVERLESS_CHROMIUMon for VercelLaunch the page tools on the bundled serverless Chromium (@sparticuz/chromium, Linux x64, Node 22+); 0 turns it off, 1 turns it on elsewhere
LOG_LEVEL / MCP_LOG_LEVELinfodebug | info | warn | error | silent; LOG_LEVEL wins when both are set
LOG_FORMAT / MCP_LOG_FORMATtexttext, or json (also ndjson) for one structured JSON object per line — ready for a log ingester

Logs always go to stderr — stdout is reserved for the MCP protocol. Unrecognized values fall back to the default, so a typo in LOG_LEVEL logs at info and one in LOG_FORMAT logs as text rather than silencing the server. With LOG_FORMAT=json each line is a single object (time, level, message plus context):

{"time":"2026-10-07T08:00:00.000Z","level":"info","message":"server ready","name":"playwright-e2e-mcp"}

Benchmark

bench/token-benchmark.mjs breaks a checkout button's test id on a storefront page and fixes it two ways: with this server (run-test → suggest-fix → apply) and with Playwright MCP plus a shell (playwright test, browser_navigate + browser_snapshot, edit, re-run). Latest result (full output):

Stepplaywright-e2e-mcp (core tools)playwright-e2e-mcp (all tools)Playwright MCP + shell
Tool definitions (sent with every request)4,82616,1215,225
Run the failing test244244323
Find the element / propose the fix2322322,286
Apply + verify (re-run)23023034
Total for one fix5,53216,8277,868

Tokens are characters ÷ 4. The work itself (run, diagnose, fix, verify) takes about 700 tokens here versus about 2,600 with Playwright MCP, but tool definitions are sent with every request: with all 19 tools loaded they outweigh that saving, so set PW_MCP_TOOLS=core (or another profile) when you only fix failing tests. The Playwright MCP route is a lower bound: it assumes the agent picks the right locator from the snapshot on the first try, which the server does for it here. Run 2026-10-28 with 0.7.0 and Playwright 1.64.1; re-run with npm run build && node bench/token-benchmark.mjs.

Demo

A real run-test call served over stdio by npx -y playwright-e2e-mcp against the bundled examples/sample-test.spec.ts (actual output, unedited):

run-test result: 4 passed, 0 failed, 5.1s

Free and open source

  • MIT licensed. Use it, change it, ship it in commercial work; no fees, no feature held back. The optional Pro plan adds a hosted service (CI run history across machines), not tools; nothing here needs it.
  • No account, no API key, no sign-up. npx -y playwright-e2e-mcp init is the whole setup.
  • No telemetry. It never phones home; your tests, traces and run history stay on your machine unless you set a Pro key and upload them.
  • Free dependencies only: the MCP SDK (Apache-2.0), zod (MIT), axe-core (MPL-2.0) and the Playwright your project already has (Apache-2.0).
  • Free to host yourself, too: the HTTP bridge deploys to a free Vercel account (see Hosted endpoint).

What it does not do: it doesn't drive an exploratory browsing session step by step, and it doesn't replace Playwright's own Test Agents inside VS Code. Use Playwright MCP for interactive browsing and this server for running, diagnosing and fixing the suite. They work side by side.

More documentation

License

MIT. If this saves you a debugging session, a ⭐ on the repo helps other Playwright users find it.

Comments

Markdown supported

New to MCP?

From what the protocol is to installing your first server, these answers cover most first questions.

An open protocol that defines how AI applications connect to external tools and data in a uniform way. Clients talk to the model; MCP servers provide tools, resources and prompt templates. They exchange standard messages, so one server can be reused by many clients.