1. 为什么 AI 写完代码还得自己点浏览器:opencode 与 playwright 的自动化测试闭环到底解决什么问题
用 opencode 写代码这件事,爽是真的爽,但痛点也很真实。你描述一个功能,它哗哗生成一堆文件,然后呢?然后你就得自己npm run dev,打开浏览器,点按钮、填表单、看控制台有没有红字。一个功能来回改三五轮是常态,真正耗时间的不是写代码,而是「写完之后的人工验证」这一步。
这个环节卡住的本质是:AI 编程工具能生成代码,但它看不到运行结果。它不知道按钮点下去有没有反应,不知道接口返回的是 200 还是 500,不知道页面上是不是弹了个报错。它只能靠你贴日志、贴截图、贴报错信息,才能进入下一轮修改。这个「人肉回传」的过程,就是效率瓶颈。
playwright 的出现把这个瓶颈打通了。它是一个浏览器自动化框架,能启动真实浏览器、点击元素、填表单、抓网络请求、读控制台日志、截图。当 opencode 通过 MCP 或 skill 的方式接上 playwright 之后,它就能自己打开浏览器跑一遍,看到失败信息,然后自己改代码,再跑一遍,直到用例通过。这就是所谓的「AI 编程到测试的迭代闭环」。
适合谁?适合已经在用 opencode 或 Claude Code 做日常开发、但每次改完还要手动验证的前端/全栈同学。也适合想搭一套自动化回归流程、但不想写一堆测试脚本的团队。你不需要是测试专家,只要能把「打开浏览器点哪里、期望看到什么」描述清楚,剩下的交给 playwright 和模型。
我实测下来,这套组合最舒服的地方在于:模型通道统一走一个 Key,opencode 负责生成和修改,playwright 负责执行和回传,两边通过配置文件串起来,整个链路是可复制、可版本管理的。下面从配置入口开始,一步步把 settings 改到 TaoToken 通道,再跑通一次完整的闭环验证。
2. 把 opencode 的 settings 模型通道改到 TaoToken:统一 Key 与 API 入口的前置准备
opencode 的配置分两层:一层是全局配置,通常在~/.config/opencode/opencode.json;另一层是项目级配置,放在项目根目录的opencode.json或.opencode/config.json。模型通道、MCP 服务、skill 路径这些都在这里定义。我们要做的第一件事,就是把模型请求指向 TaoToken 的统一 API 通道,这样 opencode 生成代码时走的是同一个 Key,playwright 回传失败信息后触发的下一轮修改也走同一个通道,不会出现「生成用 A、修改用 B」的混乱。
TaoToken 的 API 入口是https://taotoken.net/api,官网是https://taotoken.net/?utm_source=taotoken_aicg_blog_end。你需要在控制台创建一个 API Key,然后把它写进 opencode 的配置里。注意,API 地址不要带 UTM 参数,只有官网链接才带。
先确认 opencode 版本和配置文件位置:
opencode --version ls ~/.config/opencode/如果目录不存在,手动创建:
mkdir -p ~/.config/opencode然后编辑~/.config/opencode/opencode.json。opencode 的模型配置支持自定义 provider,我们需要把 baseURL 指向 TaoToken 的 API 地址,apiKey 填你申请到的 Key,model 填你要用的模型 ID。不同模型的 ID 不一样,具体以 TaoToken 控制台或文档里列出的为准。
这里有个容易踩的坑:opencode 的配置 schema 对字段名比较敏感,baseURL和baseUrl在某些版本里行为不同,建议直接参考官方 schema 提示。如果你在编辑器里装了 JSON schema 插件,$schema指向https://opencode.ai/config.json时会自动补全。
配置写完后,用一条最简单的命令验证通道是否通:
opencode run "用一句话说明什么是端到端测试"如果返回正常文本,说明模型通道已经指向 TaoToken 并且 Key 有效。如果报 401,说明 Key 没填对或者没生效;如果报连接超时,检查 baseURL 是否写成了https://taotoken.net/api而不是别的路径。
这一步是整个闭环的地基。地基不稳,后面 playwright 回传的失败信息就没法触发模型修改,闭环就断了。所以务必先单独验证模型通道,再往下走。
3. 可复制的 settings 配置片段:opencode 接入 TaoToken 与 playwright MCP 的完整写法
这一节给你可以直接抄的配置。分三块:opencode 的模型通道配置、playwright MCP 配置、以及项目级 settings 覆盖。路径和原文保持一致,你按自己的实际路径替换即可。
第一块,全局模型通道。编辑~/.config/opencode/opencode.json:
{ "$schema": "https://opencode.ai/config.json", "provider": { "taotoken": { "npm": "@ai-sdk/openai-compatible", "name": "TaoToken", "options": { "baseURL": "https://taotoken.net/api", "apiKey": "sk-你的TaoTokenKey" }, "models": { "your-model-id": { "name": "Your Model" } } } }, "model": "taotoken/your-model-id" }把sk-你的TaoTokenKey换成你在 TaoToken 控制台创建的 Key,your-model-id换成你要用的模型 ID。npm字段指定用 OpenAI 兼容的适配器,TaoToken 的 API 是兼容 OpenAI 格式的,所以这样写能通。
第二块,playwright MCP 配置。在同一个文件的mcp字段下增加:
{ "$schema": "https://opencode.ai/config.json", "mcp": { "playwright": { "type": "local", "command": [ "npx", "@playwright/mcp@latest" ], "enabled": true } } }注意type是local,command是一个数组,第一项是npx,第二项是包名。这个配置让 opencode 在需要时启动 playwright MCP 服务,模型就能调用浏览器操作能力。
第三块,项目级 settings 覆盖。在项目根目录创建opencode.json:
{ "$schema": "https://opencode.ai/config.json", "model": "taotoken/your-model-id", "mcp": { "playwright": { "type": "local", "command": ["npx", "@playwright/mcp@latest"], "enabled": true } } }项目级配置会覆盖全局配置里的同名字段。这样你在不同项目里可以用不同的模型 ID,但都走同一个 TaoToken Key。
如果你用的是 Claude Code,配置路径不同,MCP 写在~/.claude.json的mcpServers下:
{ "mcpServers": { "playwright": { "command": "npx", "args": ["@playwright/mcp@latest"] } } }Claude Code 的模型通道配置在~/.claude/settings.json或项目级.claude/settings.json,字段名和 opencode 不一样,但思路一致:baseURL 指向 TaoToken API,apiKey 填同一个 Key。
三件套记牢:Base URL 是https://taotoken.net/api,Key 是你在控制台创建的,Model ID 是你要用的模型标识。这三样在 opencode、Claude Code、Cline 里都是核心,缺一不可。
配置改完后,重启 opencode,让它重新加载配置。可以用opencode mcp list查看 MCP 服务是否注册成功。
4. 跑一条 playwright 用例验证闭环:从失败回传到 opencode 触发下一轮修改
配置就绪后,我们来跑一次完整的闭环。目标是:让 opencode 生成一个简单页面,用 playwright 跑一条会失败的用例,确认失败信息能回流到 opencode,并触发它修改代码。
第一步,准备一个最小项目。在空目录里初始化:
mkdir ai-loop-demo && cd ai-loop-demo npm init -y npm install -D @playwright/test npx playwright install chromium第二步,让 opencode 生成一个带按钮的页面。在项目里运行:
opencode run "创建一个 index.html,里面有一个 id 为 submit 的按钮,点击后把页面标题改成 '已提交'。再写一个 playwright 测试文件 tests/submit.spec.js,测试点击按钮后标题是否变成 '已提交'。"opencode 会生成index.html和tests/submit.spec.js。假设它生成的测试用例里期望标题是「提交成功」,而页面实际改成的是「已提交」,这条用例就会失败。
第三步,手动跑一次 playwright 确认失败:
npx playwright test tests/submit.spec.js你会看到类似这样的输出:
Error: expect(received).toBe(expected) Expected: "提交成功" Received: "已提交"第四步,把失败信息交给 opencode,让它自己修。这里有两种方式:一种是你手动把报错贴给 opencode;另一种是让 opencode 通过 playwright MCP 自己跑测试、自己读结果。后者才是真正的闭环。在 opencode 里输入:
运行 playwright 测试 tests/submit.spec.js,如果失败,读取失败信息并修改代码直到通过。opencode 会调用 playwright MCP 启动浏览器,执行测试,拿到失败信息,然后修改index.html或测试文件,再次运行,直到通过。你可以在终端里看到它一轮一轮的操作记录。
第五步,确认最终结果。当 opencode 报告测试通过后,你再手动跑一次:
npx playwright test tests/submit.spec.js看到1 passed就说明闭环跑通了。整个过程你只做了一次描述,剩下的生成、测试、失败回传、修改、再测试,都是自动完成的。
这里的关键点是:playwright 的失败信息必须能被模型读到。MCP 模式下,模型能直接获取浏览器快照、控制台日志、网络请求;skill 模式下,模型通过命令行输出拿到结果。两种方式都能回传,区别在 token 消耗。
5. 本篇常见错排查:401、local proxy failed、reading choices、OAuth 报错怎么定位
配置和闭环跑起来的过程中,最容易撞上这几类报错。我按实际遇到的顺序列出来,你对照着排查。
第一类,401 Unauthorized。这个基本是 Key 的问题。检查三处:~/.config/opencode/opencode.json里的apiKey是否填了完整的 Key;Key 是否在 TaoToken 控制台被禁用或删除;baseURL 是否写成了https://taotoken.net/api而不是带别的路径。如果 Key 没问题,试试用 curl 直接请求验证:
curl https://taotoken.net/api/v1/models \ -H "Authorization: Bearer sk-你的Key"返回模型列表说明 Key 有效,问题在 opencode 配置;返回 401 说明 Key 本身有问题。
第二类,local proxy failed。这个报错通常出现在 MCP 服务启动阶段。playwright MCP 通过npx @playwright/mcp@latest启动,如果本地网络环境导致 npx 拉包失败,或者端口被占用,就会报这个。排查方法:先手动运行npx @playwright/mcp@latest --help,看能否正常启动;如果卡在下载,检查 npm 源;如果端口冲突,换一个端口或重启终端。
第三类,reading choices 相关报错。这个一般出现在模型返回格式不符合预期时,比如模型返回的内容里没有choices字段,或者返回了非 JSON 格式。原因可能是模型 ID 填错了,或者 baseURL 指向的接口不兼容 OpenAI 格式。确认你用的模型 ID 在 TaoToken 的兼容列表里,并且 baseURL 是/api而不是/api/v1之外的路径。
第四类,OAuth 报错。如果你在配置里误开了某些需要 OAuth 的 provider,或者 Claude Code 的登录态和 API Key 冲突,会报 OAuth 相关错误。解决方法是明确使用 API Key 模式,不要混用登录态。在 Claude Code 里,检查~/.claude.json是否同时存在oauthAccount和apiKey字段,如果有冲突,删掉 OAuth 相关字段,只保留 API Key 配置。
第五类,playwright 测试跑起来了但模型读不到结果。这个通常是 MCP 没注册成功。用opencode mcp list确认 playwright 在列表里且状态是 enabled。如果不在,检查mcp字段的 JSON 格式,特别是command数组的写法,少一个逗号都会导致解析失败。
排查顺序建议:先验证模型通道(curl 或 opencode run),再验证 MCP 注册(mcp list),最后验证 playwright 本身(手动跑测试)。一层一层来,不要跳步。
6. 把闭环用起来:TaoToken 通道下的模型对话、Coding Plan 与接入文档入口
闭环跑通之后,你可能会想:这套东西能不能用在更复杂的项目里?能。但有几个实践建议。
第一,模型通道统一走 TaoToken 之后,你可以在 opencode、Claude Code、Cline 之间共享同一个 Key,不用每个工具单独配。切换工具时只改配置文件路径,Key 和 baseURL 不变。想验证某个模型效果,可以直接用模型对话入口试:
https://taotoken.net/api配合控制台创建的 Key,在模型对话里贴一段代码或报错,快速对比不同模型的响应质量。
第二,如果你打算长期用这套闭环做日常开发,Coding Plan 比按量付费更划算。它适合高频调用、长时间跑 Agent 的场景。具体入口在控制台里能看到,结合你的实际用量选。
第三,接入文档里有各工具的详细配置示例,包括 opencode、Claude Code、Cline 的完整字段说明。遇到配置字段不确定的时候,直接查文档比猜快得多。API Key 管理也在控制台里,可以创建多个 Key 分配给不同项目,方便追踪用量。
第四,playwright 的 skill 模式和 MCP 模式按场景选。固定步骤的回归测试用 skill,token 省;需要分析页面结构、动态定位元素的场景用 MCP,信息全。两者可以同时配置,模型会根据任务自己选。
最后说一个实际经验:闭环刚跑通的时候,别急着上复杂项目。先用一个只有一两个按钮的页面跑通全流程,确认失败信息能回传、模型能修改、测试能通过。然后再逐步增加用例复杂度。这样出问题的时候,排查范围小,定位快。等这套流程稳定了,你会发现改完代码不用再手动点浏览器,是真的省时间。