MCP剧作家浏览器服务器
A生产级 模型上下文协议(MCP)服务器 通过Playwright,人工智能助手可以完全控制浏览器——使用DOM+可访问性树+可视化的混合方法。为真实世界的代理自动化而构建:作业应用程序、网络抓取、表单填写和复杂的多标签工作流。
v2.0是一个完整的重写。 服务器从680行和23个工具增长到近5000行和71个工具,具有模块化架构、令牌优化的捕获配置文件、硬负载预算和完整的测试套件。
______________________________________________________________________
目录
______________________________________________________________________
v2.0中的新增功能
问题v1
v1是一个有效的概念验证。它可以浏览页面并提取作业。但是,当与Gemini CLI一起用于实际任务时——填写应用程序表单、导航多标签流、处理下载——它遇到了严重的限制:
- 代币浪费:每个工具响应都会丢弃它发现的所有内容。一
browser.snapshot在一个复杂的页面上,一次调用就可以将50KB+的内存推入Gemini的上下文窗口,从而迅速耗尽预算。 - 不支持多标签:如果一个链接打开了一个新的标签页(在求职申请中很常见),双子座就无法切换到它。
- 无表单智能:填写表格需要手动点击说明。无法询问“哪些字段仍然为空?”或“填写所有必填字段”
- 易碎的仅DOM导航:影子DOM、iframe和混淆的元素ID导致了失败,没有回退。
- 无会话持久性:每次跑步都是从头开始。一次又一次登录浪费了时间,并触发了机器人检测。
- 无安全护栏:人工智能可以在磁盘上的任何地方写入文件,运行任意JS,或创建自己的自动化脚本——不受保护。
- 整体的:一个680行的文件,没有测试。
v2.0解决了什么问题
在v2.0中,每个问题都有一个特定的解决方案:
| 问题 | v2.0解决方案 |
|---|---|
| 令牌浪费 | 捕获配置文件系统(轻/平衡/满)+280KB硬有效载荷上限 |
| 多标签卡住 | 页面管理器具有稳定的页面ID, browser.list_pages, browser.select_page |
| 愚蠢的表单填写 | browser.form_audit + browser.fill_form +Google Forms专业工具 |
| 影子DOM/模糊ID | 通过CDP创建A11y树 Accessibility.getFullAXTree 与稳定 ax- UID |
| 会话丢失 | Cookie导出/导入, browser.export_storage_state / browser.import_storage_state |
| 无安全 | 路径满负荷运行 src/security/paths.js, MCP_ALLOW_EVALUATE 警卫 |
| 单片 | 10个聚焦模块 src/browser/ + src/security/ +18测试套件 |
______________________________________________________________________
v1与v2比较
| 维度 | v1.0 | v2.0 |
|---|---|---|
| MCP工具总数 | 23 | 71 |
| 服务器大小 | 680行,1个文件 | 4966行,11个模块 |
| 代币效率 | 不受控制的转储 | 捕获配置文件+280KB硬上限 |
| 多标签支持 | 仅限单个选项卡 | 整页管理器(列表、选择、关闭) |
| 表单自动化 | 手动点击 | form_audit + fill_form +谷歌表单专家 |
| A11y/阴影DOM | 仅DOM,脆弱 | CDP可访问性树,具有稳定的UID |
| 滚动处理 | 仅看到第一个视口 | 滚动感知+容器滚动 |
| 会话持续 | 无 | Cookie/存储导出导入 |
| 弹出窗口和对话框处理 | 无 | 对话框接受/关闭,弹出页面ID捕获 |
| 下载管理 | 无 | 等待下载,保存到路径 |
| 文件阅读(CV/PDF) | 没有 | files.read_text, files.read_pdf_text |
| 安全 | 无限制 | 允许列表强制读/写路径 |
| 可观测性 | 无 | 控制台日志捕获、网络请求日志 |
| 测试覆盖率 | 2次测试 | 18测试 |
| 档案 | 3 | 5(+持久变体) |
| 批处理脚本 | 5 .bat 发射器 | 7 .bat 发射器 |
| 错误处理 | 人工智能的原始异常 | 规范化、结构化、预算化 |
什么保持不变
- 确实,作业提取器(生产级、多选择器、重复数据删除)
- 谷歌搜索提取器(同意处理、URL去模糊)
- 隐身模式(隐藏Web驱动程序、用户代理欺骗)
- CDP连接到真正的Chrome
- 可视化快照+基于坐标的点击
______________________________________________________________________
运作原理
You / Gemini CLI
│
│ natural language prompt
▼
Gemini CLI ──── loads MCP config ────► playwrightBrowser MCP server
│
┌────────────────┤
│ │
71 MCP Tools Payload Budget
(browser.*) (280KB ceiling)
(forms.*) (capture profiles)
(files.*) (retryWith hints)
(jobs.*)
(search.*)
│
┌─────────┤──────────┐
│ │ │
Playwright CDP API Security
(browser) (A11y, (path
network, allowlist)
clicks)
│
Chrome / Chromium捕获阶梯
每个配置文件都指示Gemini按顺序尝试工具,首先是最便宜的:
1. browser.snapshot → plain text summary (cheapest, ~6KB in light mode)
2. browser.list → interactive elements (structured, ~8KB)
3. browser.query_dom → targeted selector query (focused, ~10KB)
4. browser.take_snapshot→ A11y tree with UIDs (rich, only when uid-clicking needed)
5. browser.visual_snapshot → screenshot + bbox map (most expensive, last resort)Gemini只会在更便宜的工具没有所需的东西时升级为更昂贵的工具。这就是为什么v2.0使用的令牌比v1.0少得多的核心。
有效载荷预算
每一个工具响应都会通过 enforcePayloadCeiling() 在发送给双子座之前:
- 以字节为单位测量响应大小
- 如果小于280KB→ 按原样发送
- 如果结束→ 渐进截断:数组收缩,字符串截断,字段删除
- 始终包括
retryWith提示Gemini下次要减少哪些参数 - 绝对楼层:
{truncated: true}--双子座永远不会得到上下文崩溃的回应
______________________________________________________________________
快速开始
# Clone
git clone https://github.com/Mhrnqaruni/mcp-playwright-browser.git
cd mcp-playwright-browser
# Install
npm install
npx playwright install chromium
# Run (interactive mode - chat with Gemini)
scripts\run-dom-headless.bat
# Run (one-shot automation)
scripts\run-dom-headless.bat -p "Go to https://example.com and extract the page title"
# Run with real Chrome (for logged-in sessions)
scripts\run-chrome-profile.bat --kill-chrome______________________________________________________________________
安装
先决条件
- Node.js 18+
- npm
- Gemini CLI:
npm install -g @google/gemini-cli然后gemini auth login - 谷歌浏览器 (适用于CDP和铬型材模式)
设置
1.安装依赖项
npm install
npx playwright install chromium2.配置MCP服务器路径
编辑 .gemini/settings.json 并设置 cwd 到您的仓库位置:
{
"mcpServers": {
"playwrightBrowser": {
"command": "node",
"args": ["src/mcp-browser-server.js"],
"cwd": "C:/path/to/mcp-playwright-browser"
}
}
}3.(可选)禁用Chrome后台应用程序
防止配置文件锁定:
Chrome Settings → Advanced → System →
☐ Continue running background apps when Google Chrome is closed4.验证
scripts\run-dom-headless.bat -p "Use MCP server playwrightBrowser. Launch browser. Go to https://example.com. Take a snapshot. Close."______________________________________________________________________
配置文件启动器
每 .bat 该文件预先配置了所有内容(浏览器类型、隐身、配置文件、环境变量),并使用正确的系统指令启动Gemini。您永远不需要手动配置Gemini。
可用配置文件
| 脚本 | 浏览器 | 模式 | 最适合 |
|---|---|---|---|
run-dom-headless.bat | 铬 | 无头 | ⚡ 批量刮擦,速度最快 |
run-visual-headful.bat | Chromium | 可见+截图 | 调试、视觉验证 |
run-chrome-profile.bat | Real Chrome | 您的个人资料 | 已登录会话、表单填写 |
run-cdp-profile.bat | 真正的Chrome | CDP | 最大隐形 |
run-cdp-profile-screen.bat | 真正的Chrome | CDP+可视化 | 带有屏幕截图分析的CDP |
run-cdp-profile-persist.bat | 真正的Chrome | CDP+持久性 | 长会话,多步骤流程 |
run-cdp-profile-screen-persist.bat | 真正的Chrome | CDP+视觉+持久 | 全功率模式 |
互动模式(聊天)
# Start Gemini and chat with it
scripts\run-chrome-profile.bat --kill-chrome
# Then just type:
# "Fill out the job application at [URL] using my CV"
# "Go to LinkedIn and apply to the first 5 jobs"
# "Extract all AI engineer jobs from Indeed and save them"单次模式(自动化)
# Run a task and get a log file
scripts\run-dom-headless.bat -p "Your full task here"
# With custom output
scripts\run-dom-headless.bat -p "Extract 50 jobs from Indeed" --output logs\jobs.log
# Chrome profile one-shot
scripts\run-chrome-profile.bat --kill-chrome -p "Submit application at [URL]" --output logs\apply.log日志会自动保存到 logs/ 带有时间戳。
个人资料详细信息
run-dom-headless.bat --最快
- Chromium无头(无GUI)
- 最适合:批量提取、抓取、后台任务
- 代币使用率:最低(无截图)
run-visual-headful.bat --调试
- 铬合金,带可见窗口
- 基于屏幕截图的导航可用
- 最适合:故障排除、目视验证
run-chrome-profile.bat --经过身份验证的会话
- 使用现有登录配置文件的真实Chrome
- 已登录Gmail、LinkedIn、求职网站
- 使用
--kill-chrome开始前释放配置文件 - 最适合:工作申请、经过身份验证的抓取
run-cdp-profile.bat --最大隐身能力
- 通过Chrome DevTools协议连接到真实的Chrome
- 网站最难检测到自动化
- 最适合:屏蔽Playwright/Chromium的网站
- 启动前自动关闭使用配置文件的任何现有Chrome
run-cdp-profile-persist.bat --长时间会议
- 具有持久浏览器的CDP模式(在任务之间不关闭)
- 最适合:浏览器状态必须存活的多步骤工作流
______________________________________________________________________
全部71个MCP工具
捕获配置文件控制
| 工具 | 说明 |
|---|---|
browser.set_capture_profile | 设置 light / balanced / full 轮廓。控制所有工具的令牌使用情况。先叫这个。 |
browser.get_capture_profile | 显示当前配置文件设置和有效负载预算。 |
浏览器生命周期
| 工具 | 说明 |
|---|---|
browser.launch | 使用以下选项启动Chromium:无头、隐形、userDataDir、profileDirectory、通道、slowMo、args |
browser.launch_chrome_cdp | 启动真正的Chrome浏览器,远程调试+一步连接 |
browser.connect_cdp | 使用以下方式连接到现有Chrome --remote-debugging-port |
browser.close | 关闭浏览器会话 |
browser.reload | 重新加载当前页面 |
多标签管理
| 工具 | 说明 |
|---|---|
browser.new_page | 打开新选项卡,由页面管理器跟踪 |
browser.list_pages | 列出所有打开的标签页,包括页面ID、url、标题、活动/关闭状态 |
browser.select_page | 按页面ID切换活动选项卡 |
browser.close_page | 按pageId关闭特定选项卡 |
browser.list_frames | 列出当前页面上的所有iframe |
导航
| 工具 | 说明 |
|---|---|
browser.goto | 使用可配置的waitUntil和timeout导航到URL |
browser.back | 回到历史 |
browser.forward | 在历史中前进 |
browser.wait | 等待选择器或固定毫秒 |
browser.wait_for | 智能等待:选择器、文本或uid(A11y) |
事件和对话处理
| 工具 | 说明 |
|---|---|
browser.list_dialogs | 列出待处理的JS对话框(警报、确认、提示) |
browser.handle_dialog | 接受或关闭对话框,可选地使用输入文本 |
browser.wait_for_download | 在下载开始之前进行阻止,返回downloadId |
browser.save_download | 将捕获的下载保存到特定路径 |
browser.wait_for_popup | 等待新选项卡/弹出窗口打开,返回其pageId |
browser.expect_event | 监听一次性事件:对话、下载、导航、请求、响应 |
会话和Cookie管理
| 工具 | 说明 |
|---|---|
browser.get_cookies | 列出Cookie,可选择按URL过滤 |
browser.set_cookies | 将Cookie注入浏览器会话 |
browser.clear_cookies | 清除所有或特定于URL的Cookie |
browser.export_storage_state | 将完整会话状态(Cookie+本地存储)导出到JSON文件 |
browser.import_storage_state | 从以前导出的JSON还原会话 |
滚动控制
| 工具 | 说明 |
|---|---|
browser.get_scroll_state | 返回scrollY、scrollHeight、atTop、atBottom、视口信息 |
browser.scroll_by | 按增量像素滚动页面(垂直+水平) |
browser.scroll_to | 滚动到绝对位置 |
browser.get_scrollables | 检测页面上的所有可滚动容器 |
browser.get_container_scroll_state | 滚动特定容器选择器的指标 |
browser.scroll_container | 按选择器滚动特定容器 |
页面阅读和快照
| 工具 | 说明 |
|---|---|
browser.snapshot | 纯文本页面摘要:标题、文本、链接、可选标题+表单摘要 |
browser.take_snapshot | 通过CDP的A11y树:角色、名称、UID(ax-{nodeId})、深度、状态 |
browser.query_dom | 灵活的选择器查询:文本、值、bbox、可见性、状态、标记名 |
browser.evaluate | 执行JavaScript(需要 MCP_ALLOW_EVALUATE=true,原点门控) |
元素交互
| 工具 | 说明 |
|---|---|
browser.list | 列出带有elementId、标签、文本和href的可见交互元素 |
browser.click | 按元素ID、uid、选择器或文本单击 |
browser.hover | 将鼠标悬停在元素上(触发下拉菜单、工具提示) |
browser.type | 通过按键打字模拟按键 |
browser.fill | 直接值填充(更快,无需按键模拟) |
browser.press | 按键盘键(Enter、Tab、Escape等) |
browser.set_input_files | 上传文件到输入\[type=file\] |
browser.scroll_to_uid | 将UID元素滚动到视图中 |
视觉导航
| 工具 | 说明 |
|---|---|
browser.screenshot | 将屏幕截图保存到路径 |
browser.visual_snapshot | 屏幕截图+带有边界框和ID的元素图 |
browser.click_at | 在视口相对X/Y坐标处单击 |
browser.click_at_page | 点击文档的绝对X/Y坐标 |
数据提取
| 工具 | 说明 |
|---|---|
browser.extract_text | 从CSS选择器中提取文本(单个或所有匹配项) |
browser.extract_html | 从选择器中提取outerHTML |
表单自动化
| 工具 | 说明 |
|---|---|
browser.form_audit | 扫描页面以查找所有未填写的必填字段:文本、选择、单选、复选框、内容可编辑 |
browser.fill_form | 填写列表 {label, selector, value, kind} 字段--标签驱动或选择器驱动 |
forms.google_audit | 谷歌表单专家:列出所有问题并检查 aria-checked 获取答案 |
forms.google_set_text | 逐个问题文本填写Google Forms文本问题 |
forms.google_set_dropdown | 在Google Forms下拉列表中选择选项 |
forms.google_set_checkbox | 选中/取消选中Google Forms复选框 |
forms.google_set_radio | 在Google Forms单选组中选择选项 |
forms.google_set_grid | 在Google Forms网格问题中选择选项 |
可观测性
| 工具 | 说明 |
|---|---|
browser.list_console_messages | 显示已捕获 console.log/warn/error 从页面 |
browser.list_network_requests | 显示所有网络请求(URL、方法、状态、时间) |
browser.get_network_request | 按ID获取特定请求的完整详细信息 |
文件操作
| 工具 | 说明 |
|---|---|
files.read_text | 读取文本文件(仅限于允许的路径) |
files.read_pdf_text | 从PDF中提取文本——用于阅读简历文件 |
files.list_dir | 列出目录内容 |
files.write_text | 将文本写入文件(仅限于 output/ 和 logs/) |
专业提取器(生产示例)
| 工具 | 说明 |
|---|---|
jobs.extract_indeed | 通过多选择器回退、重复数据删除和访问检测提取Indeed作业列表 |
jobs.indeed_next_page | 导航到下一个Indeed页面(直接URL、单击或自动模式) |
search.google | 打开谷歌搜索并提取同意处理结果 |
search.extract_google | 从当前谷歌搜索页面提取结果 |
______________________________________________________________________
建筑
模块结构
src/
├── mcp-browser-server.js # Main server: tool registration, env config, middleware
├── extractors.js # Indeed + Google specialized extractors
├── browser/
│ ├── pages.js # Multi-tab page manager (stable pageIds)
│ ├── snapshot.js # A11y tree via CDP Accessibility.getFullAXTree
│ ├── capture-profiles.js # light/balanced/full × low/high = 30 preset configs
│ ├── payload-budget.js # Hard 280KB response ceiling with graceful truncation
│ ├── cdp.js # CDP session, click/hover/scroll by backendNodeId
│ ├── dom-version.js # DOM mutation tracking, frame management
│ ├── forms.js # Form audit + intelligent form fill
│ ├── observability.js # Console + network request capture via CDP
│ └── wait.js # Smart wait: selector, text, uid
└── security/
└── paths.js # Read/write path allowlist enforcement工具注册中间件
每个工具都要经过一个在处理程序之前和之后运行的包装器:
AI calls tool
│
▼
assign requestId
│
▼
run handler
│
▼
normalize errors (structured, no stack traces)
│
▼
add envelope (ok, requestId, timestamp, url, domVersion)
│
▼
enforcePayloadCeiling (truncate if > 280KB)
│
▼
send to AI这意味着每个工具都会自动受益于错误安全和有效载荷预算,而无需为每个工具编写任何额外代码。
UID系统
A11y快照(browser.take_snapshot)以以下格式为每个节点分配一个稳定的UID ax-{nodeId},与CDP联系在一起 backendDOMNodeId。然后,此UID可以与以下对象一起使用:
browser.click({ uid: "ax-123" })--直接通过CDP在后端节点上单击browser.scroll_to_uid({ uid: "ax-123" })--先将其滚动到视图中browser.wait_for({ uid: "ax-123" })--等到它可见
CDP原生点击比基于选择器的点击更可靠,因为它们绕过CSS选择器解析,即使在Shadow DOM中也能工作。
______________________________________________________________________
令牌效率:捕获配置文件
这是现实世界中最重要的v2.0功能。
问题
AI上下文窗口是有限的。每个工具响应都会消耗令牌。一个天真的实施方式,每次通话都会迅速耗尽预算。
解决方案:三种配置文件
在会话开始时设置一次配置文件,随后的每次工具调用都会自动使用适当的限制:
browser.set_capture_profile({ profile: "light" })| 配置文件 | 快照字符 | 列表项 | A11y节点 | 最适合 |
|---|---|---|---|---|
| 光 | 6000–9000 | 120–180 | 220–320 | 作业抓取,批量任务 |
| 平衡的 | 12000–16000 | 240–320 | 440–700 | 表格填写、研究 |
| 满的 | 20000 | 500 | 1200-2000 | 仅深度调试 |
每个轮廓有两个细节级别
在每个配置文件中,工具都接受 detail: "low" 或 detail: "high":
browser.snapshot({ detail: "low" }) # minimal, fast
browser.snapshot({ detail: "high" }) # more text, links, headings, form summary实践中的捕获阶梯
配置文件系统说明教导Gemini仅在需要时升级:
✅ "I need to find the Apply button"
→ browser.snapshot (low) # did I find it in plain text? usually yes
→ browser.list (low) # still looking? check interactive elements
→ browser.take_snapshot (low) # need uid for reliable click? A11y tree
→ browser.visual_snapshot (low) # shadow DOM / can't find it at all? visual fallback在 light 在模式下,整个梯形图的令牌成本比v1.0的单转储方法低约8倍。
硬有效载荷预算
即使有捕获配置文件,有些页面也很庞大。有效载荷预算是一个安全网:
- 默认上限: 每个响应280KB
- 如果超过:逐步截断(数组→ 字符串→ 对象键)
- 包含
retryWith字段:{ detail: "low", maxItems: 80, limit: 20 } - Gemini读取此信息并使用较小的参数重试
- 绝对回退:
{ truncated: true, truncationReason: "..." }
预算是可配置的: MCP_MAX_RESPONSE_BYTES=150000 对于更严格的环境。
______________________________________________________________________
常见用例
工作申请(Chrome配置文件)
# Start with your real logged-in Chrome
scripts\run-chrome-profile.bat --kill-chrome双子座:
Set capture profile to light.
Go to [application URL].
Run form_audit to see all required fields.
Fill them using fill_form with my details from Applied Jobs/CODEX/maincv.md.
Before submitting, take a screenshot and ask me to confirm.批量作业报废(无头)
scripts\run-dom-headless.bat -p "Use playwrightBrowser. Launch browser headless. Go to https://ae.indeed.com/q-ai-engineer-l-dubai-jobs.html. Extract jobs with jobs.extract_indeed limit 20, save to output/indeed/page-1. Go to next page with jobs.indeed_next_page. Extract again, save to output/indeed/page-2. Close."会话持久性(登录一次,重用)
# First time: login manually and export session
scripts\run-cdp-profile.bat双子座:
Go to linkedin.com and wait for me to log in.
After I confirm logged in, run browser.export_storage_state to output/linkedin-session.json.下一次:
Run browser.import_storage_state from output/linkedin-session.json.
Go to linkedin.com — should be logged in already.谷歌表单自动化
scripts\run-dom-headless.bat双子座:
Go to [Google Form URL].
Run forms.google_audit to see all questions.
Fill each question using the appropriate forms.google_set_* tool.
Run forms.google_audit again to verify all answered.
Submit.PDF简历阅读
双子座可以直接阅读你的简历,而无需粘贴:
Read my CV from Applied Jobs/CODEX/maincv.md using files.read_text.
Or read the PDF version: files.read_pdf_text from Applied Jobs/CODEX/CV.pdf.
Use that information to fill the job application form.使用可视化模式进行调试
scripts\run-visual-headful.bat双子座:
Go to [URL].
Take a visual_snapshot and save to output/debug.png.
Tell me what you see and identify any unusual elements.______________________________________________________________________
环境变量
所有变量都有双重名称,以兼容Gemini CLI。发射器同时设置了以下两项:
| 变量 | 别名 | 描述 |
|---|---|---|
MCP_HEADLESS | GEMINI_CLI_MCP_HEADLESS | true/false--在没有GUI的情况下运行 |
MCP_STEALTH | GEMINI_CLI_MCP_STEALTH | true/false--启用反检测 |
MCP_CHANNEL | GEMINI_CLI_MCP_CHANNEL | chrome --使用真正的Chrome |
MCP_EXECUTABLE_PATH | GEMINI_CLI_MCP_EXECUTABLE_PATH | chrome.exe的绝对路径 |
MCP_USER_DATA_DIR | GEMINI_CLI_MCP_USER_DATA_DIR | Chrome配置文件目录 |
MCP_PROFILE | GEMINI_CLI_MCP_PROFILE | 配置文件名称: Default, Profile 3 |
MCP_CDP_ENDPOINT | GEMINI_CLI_MCP_CDP_ENDPOINT | CDP网址: http://127.0.0.1:9222 |
MCP_CDP_PORT | GEMINI_CLI_MCP_CDP_PORT | CDP端口号(默认9222) |
MCP_CDP_AUTO_CLOSE | GEMINI_CLI_MCP_CDP_AUTO_CLOSE | 退出服务器时关闭Chrome |
MCP_FORCE_CDP | GEMINI_CLI_MCP_FORCE_CDP | 禁用 browser.launch (仅CDP模式) |
MCP_REQUIRE_PROFILE | GEMINI_CLI_MCP_REQUIRE_PROFILE | 需要userDataDir(防止裸Chromium) |
MCP_ALLOW_EVALUATE | GEMINI_CLI_MCP_ALLOW_EVALUATE | 启用 browser.evaluate 工具 |
MCP_EVALUATE_ALLOW_ORIGINS | GEMINI_CLI_MCP_EVALUATE_ALLOW_ORIGINS | 逗号分隔的允许计算来源 |
MCP_CAPTURE_PROFILE | GEMINI_CLI_MCP_CAPTURE_PROFILE | 默认配置文件: light, balanced, full |
MCP_MAX_RESPONSE_BYTES | GEMINI_CLI_MCP_MAX_RESPONSE_BYTES | 覆盖280KB有效载荷上限 |
MCP_SLOWMO_MS | GEMINI_CLI_MCP_SLOWMO_MS | 将操作减慢N毫秒(调试) |
为什么有双重名字? Gemini CLI会清理环境变量,并可能进行剥离 MCP_* 前缀键。这 GEMINI_CLI_MCP_* 变量绕过此筛选。服务器读取这两个变量,并使用设置的变量。
______________________________________________________________________
项目结构
mcp-playwright-browser/
│
├── src/
│ ├── mcp-browser-server.js # Main server (71 tools, middleware, env config)
│ ├── extractors.js # Indeed + Google production extractors
│ ├── browser/
│ │ ├── pages.js # Multi-tab page manager
│ │ ├── snapshot.js # A11y tree (CDP Accessibility API)
│ │ ├── capture-profiles.js # Token budget profiles (light/balanced/full)
│ │ ├── payload-budget.js # Hard response size ceiling
│ │ ├── cdp.js # CDP primitives (click, hover, scroll by nodeId)
│ │ ├── dom-version.js # DOM mutation tracking + frame management
│ │ ├── forms.js # Form audit + intelligent fill
│ │ ├── observability.js # Console + network capture
│ │ └── wait.js # Smart wait (selector, text, uid)
│ ├── security/
│ │ └── paths.js # File read/write path allowlist
│ └── tests/
│ ├── page-manager-test.js
│ ├── security-paths-test.js
│ ├── snapshot-uid-test.js
│ ├── uid-click-fill-test.js
│ ├── elementid-no-stale-test.js
│ ├── wait-for-test.js
│ ├── form-audit-fill-test.js
│ ├── console-network-test.js
│ ├── visual-coords-test.js
│ ├── frame-domversion-test.js
│ ├── cdp-hover-test.js
│ ├── browser-events-test.js
│ ├── storage-state-test.js
│ ├── capture-profiles-test.js
│ ├── payload-budget-test.js
│ ├── google-form-test.js
│ ├── google-test.js
│ └── indeed-test.js
│
├── scripts/
│ ├── run-dom-headless.bat # Fastest: headless Chromium
│ ├── run-visual-headful.bat # Visual: Chromium + screenshots
│ ├── run-chrome-profile.bat # Auth: real Chrome with your profile
│ ├── run-cdp-profile.bat # Stealth: CDP mode
│ ├── run-cdp-profile-screen.bat # Stealth + visual
│ ├── run-cdp-profile-persist.bat # Stealth + persistent session
│ ├── run-cdp-profile-screen-persist.bat # Full power
│ ├── autoconnect.js # CDP auto-connect helper
│ └── .gemini/settings.json # Fallback MCP config
│
├── profiles/
│ ├── dom/
│ │ ├── system.md # Gemini system instructions (DOM mode)
│ │ └── oneshot.md # One-shot variant (closes browser at end)
│ ├── visual/
│ │ ├── system.md
│ │ └── oneshot.md
│ ├── cdp/
│ │ ├── system.md
│ │ ├── oneshot.md
│ │ └── persistent.md
│ └── cdp-visual/
│ ├── system.md
│ ├── oneshot.md
│ └── persistent.md
│
├── .gemini/settings.json # Main MCP config (set your cwd here)
├── GEMINI.md # Project-level Gemini instructions
├── LICENSE # ISC License
└── README.md运行测试
# All tests that don't need network
npm run test:local
# Live network tests (Indeed + Google)
npm run test:remote
# Everything
npm run test:all______________________________________________________________________
故障排除
“Chrome已在运行”/个人资料已锁定
# Use --kill-chrome
scripts\run-chrome-profile.bat --kill-chrome
# Or manually
taskkill /F /IM chrome.exeChrome 136+阻止默认用户数据目录上的自动化。始终使用专用配置文件或 ChromeForMCP 数据目录。
“Gmail说浏览器不安全”
你是通过Chromium连接的,而不是真正的Chrome。确保:
- 启动前Chrome已完全关闭(
--kill-chrome) - 发射响应显示
"persistent": true以及您的个人资料路径 - 如果没有,请重新启动Gemini并验证
.bat输出Using Chrome executable: ...
在Gemini中找不到MCP工具
- 运行任何
.bat从任何目录--它们会自动修复cwd - 验证
.gemini/settings.json有正确的cwd - 这
scripts/.gemini/settings.json如果双子座开始,这是一个退路scripts/
响应已截断/ retryWith 提示
这是正常工作的有效载荷预算。双子座会读 retryWith 提示并使用较低的参数重试。如果它继续发生,请切换到 light 轮廓:
browser.set_capture_profile({ profile: "light" })性能缓慢
- 使用
run-dom-headless.bat用于批量操作(无GUI=速度快3-4x) - 避免
browser.extract_html--它返回完整的HTML并浪费令牌 - 使用
detail: "low"在所有工具上,除非您特别需要更多
浏览器打开但忽略我的个人资料
检查 .bat 输出:
Using Chrome executable: C:\Program Files\Google\Chrome\Application\chrome.exe
Using Chrome profile: Profile 3如果您看到其他配置文件或“未找到”,请编辑 .bat 并设置 MCP_PROFILE 明确地。
______________________________________________________________________
安全与隐私
路径限制
browser.evaluate (任意JS执行)是 默认情况下禁用。仅明确启用它: MCP_ALLOW_EVALUATE=true
files.read_text 和 files.write_text 仅限于:
- 阅读:
Applied Jobs/,Auto/output/,Auto/logs/ - 写:
Auto/output/,Auto/logs/
任何在这些路径之外读取或写入的尝试都会立即抛出。检查前先解析符号链接(防止遍历攻击)。
存储什么
| 数据 | 位置 | Git被忽略 |
|---|---|---|
| 执行日志 | logs/ | ✅ 是的 |
| 提取的工作/数据 | output/ | ✅ 是的 |
| 会话状态导出 | output/ | ✅ 是的 |
| Gemini CLI状态 | scripts/.gemini/state.json | ✅ 是的 |
.gemini/ config | root .gemini/ | ✅ 是的 |
什么东西从不存储
- ❌ 密码或凭据
- ❌ 信用卡或付款信息
- ❌ 浏览器历史
- ❌ 超出允许路径的个人文档
______________________________________________________________________
道德使用
此工具用于:
- 学习浏览器自动化和MCP开发
- 测试您自己的web应用程序
- 在您有权访问的网站上自动执行任务
- 合法的求职和申请工作流程
您负责:
- 关于
robots.txt网站服务条款 - 遵守数据保护法规(GDPR、CCPA等)
- 限制您的请求速率以避免服务中断
- 未经授权,不得使用此功能绕过付费墙或访问控制
作者对误用不承担任何责任。负责任地使用。
______________________________________________________________________
这与微软官方有何不同 playwright-mcp
微软的 剧作家mcp 专注于 基于可访问性树的自动化 用于结构化环境中的测试开发。
| 功能 | 微软 playwright-mcp | 这个项目 |
|---|---|---|
| 导航 | 可访问性树 | 混合:DOM+A11y+可视化 |
| 哲学 | “盲目”自动化(快速、结构化) | 类人自动化(稳健、自适应) |
| 主要用例 | QA测试、定义的工作流 | 开放式web代理、抓取、复杂的UI |
| 令牌效率 | 未优化 | 捕获配置文件+硬负载预算 |
| 会话持久性 | 基本 | Cookie/存储导出导入 |
| 表单智能 | 手动 | form_audit + fill_form +谷歌表单专家 |
| 多选项卡 | 基本 | 具有稳定页面ID的完整页面管理器 |
| 设置 | 通用 | 包括电池(隐形、配置文件、发射器) |
使用Microsoft用于: CI/CD测试自动化,结构化可访问性驱动的工作流程 使用此功能: 在开放网络上运行的自主代理、作业申请自动化、反检测抓取
______________________________________________________________________
更新日志
v2.0.0(当前)
- 完整的架构重写:单片→ 11 模块化文件
- 71个MCP工具(23个)
- 捕获配置文件系统(轻/平衡/满),提高代币效率
- 硬280KB有效负载预算,具有优雅的截断和
retryWith提示 - 多标签页管理器(列表、选择、关闭页面)
- 通过CDP实现稳定的A11y树快照
ax-用户界面 - CDP原生点击/悬停/滚动后端DOMNodeId(处理Shadow DOM)
- 表单审核+智能填写+谷歌表单专家(6个工具)
- 会话导出/导入(cookie+本地存储持久性)
- 弹出、对话框、下载事件处理
- 滚动感知:获取状态、按增量滚动、滚动容器
- 通过CDP实现网络+控制台的可观察性
- 文件读取:文本文件+PDF提取
- 安全:路径允许强制执行,评估防护
- 18个测试套件(共2个)
- 7个配置文件启动器(原来是5个):为CDP添加了持久变体
- GEMINI_CLI_MCP\_\*双环境变量支持GEMINI净化
v1.1.0版本
- 配置文件启动器系统(.bat文件)
- Chrome配置文件集成
--kill-chrome旗帜- 单次模式,自动记录
- GEMINI_CLI_MCP\_\*环境变量别名
browser.visual_snapshot和browser.click_at
v1.0.0
- 初始版本
- 带Playwright的基本MCP服务器
- Indeed+谷歌提取器
- DOM和视觉导航
______________________________________________________________________
贡献
- 分叉存储库
- 创建要素分支(
git checkout -b feature/your-feature) - 跑
npm run test:local确认没有损坏 - 承诺(
git commit -m 'Add your feature') - 推送并打开拉取请求
______________________________________________________________________
许可证
ISC许可证--请参阅 许可证 文件。
______________________________________________________________________
致谢
______________________________________________________________________
支持
- 问题:
- 讨论:
