camofox-browser截图与快照组合拳:base64 PNG+可访问性树
【免费下载链接】camofox-browserStealth headless browser for AI agents — bypass Cloudflare, bot detection, and anti-scraping. Drop-in Puppeteer/Playwright replacement.项目地址: https://gitcode.com/GitHub_Trending/ca/camofox-browser
camofox-browser 是一款面向 AI 代理的隐身无头浏览器服务,它把"截图"与"快照"做成了黄金搭档:一次 API 调用,既能拿到 base64 编码的 PNG 截图,又能拿到带元素引用的可访问性树(ARIA 快照)。图像负责"看见",快照负责"理解",两者组合让 AI 代理像人一样浏览网页——既能感知视觉布局,又能精确点击任意元素。本文带你快速掌握这套组合拳的正确打开方式 🎯
为什么 AI 代理需要"截图 + 快照"双通道?
很多无头浏览器方案只给 AI 一种视角,而 camofox-browser 认为两者缺一不可:
| 通道 | 输出形式 | 擅长场景 | 短板 |
|---|---|---|---|
| 截图(Screenshot) | base64 PNG 图像 | 视觉布局、验证码、品牌配色、"看起来对不对" | 纯图像 Token 消耗大,无法精确定位元素 |
| 快照(Snapshot) | 可访问性树 + 元素引用 | 结构化语义、元素定位、点击/输入 | 丢失视觉信息(颜色、位置、图片内容) |
camofox-browser 的可访问性快照比原始 HTML小约 90%,Token 效率极高;而 base64 PNG 截图则补齐了视觉维度。两者一次调用同时返回,正是"组合拳"的核心价值。
快照端点:把网页变成"可点击"的可访问性树
调用快照端点后,服务端会用 Camoufox(C++ 层反指纹的 Firefox 分支)提取页面的可访问性树,并为每个交互元素标注稳定引用e1、e2……:
# 获取带元素引用的可访问性快照 curl "http://localhost:9377/tabs/TAB_ID/snapshot?userId=agent1" # -> { "url": "...", "snapshot": "- button \"Submit\" [e1] - link \"Learn more\" [e2]", "refsCount": 2, ... }拿到引用后,后续交互直接用ref操作,无需脆弱的 CSS 选择器:
# 按引用点击元素 curl -X POST http://localhost:9377/tabs/TAB_ID/click \ -H 'Content-Type: application/json' \ -d '{"userId": "agent1", "ref": "e1"}'元素引用的标注逻辑位于 server.js:服务端的refreshTabRefs为按钮、链接、输入框等交互角色生成引用,再逐行注入 YAML 快照。
一键组合拳:includeScreenshot=true 附带 base64 PNG
在快照请求上多加一个查询参数,即可在同一次响应里拿到截图 📸
curl "http://localhost:9377/tabs/TAB_ID/snapshot?userId=agent1&includeScreenshot=true"响应中会多出一个screenshot对象:
{ "url": "https://example.com", "snapshot": "- heading \"Welcome\" - button \"Submit\" [e1]", "refsCount": 1, "screenshot": { "data": "iVBORw0KGgo...", "mimeType": "image/png" } }data字段就是标准 base64 编码的 PNG,解码后前 4 字节为 PNG 魔数(0x89 P N G),可直接写入文件交给多模态模型。该逻辑实现在 server.js:服务端调用page.screenshot({ type: 'png' })后将 Buffer 转 base64 附加到响应。
💡 注意:开启截图不会改变快照内容本身——带不带
includeScreenshot,返回的可访问性树完全一致(e2e 测试 snapshotScreenshot.test.js 专门验证了这一点)。
独立截图端点:支持 fullPage 整页长图
除了"顺路"截图,还有专门的截图端点GET /tabs/:tabId/screenshot,直接返回image/png二进制流,并支持fullPage=true截取整页:
# 视口截图,直接得到 PNG 文件 curl "http://localhost:9377/tabs/TAB_ID/screenshot?userId=agent1" -o shot.png # 整页长截图 curl "http://localhost:9377/tabs/TAB_ID/screenshot?userId=agent1&fullPage=true" -o full.png该端点位于 server.js,截图时还会触发tab:screenshot插件事件,方便插件体系扩展(例如 VNC 插件监听浏览器状态)。
大页面怎么办:快照分页与截断策略
超长页面(如搜索结果页)的可访问性树可能非常大,camofox-browser 内置了智能分页,避免一次性撑爆上下文:
| 响应字段 | 含义 |
|---|---|
truncated | 快照是否被截断 |
totalChars | 完整快照总字符数 |
hasMore/nextOffset | 是否还有下文 / 下次请求的 offset |
分页窗口逻辑见 lib/snapshot.js:单窗口上限80000 字符(约 2 万 Token),且永远保留尾部 5000 字符——因为分页导航链接往往在页面底部,保留尾部能让 AI 随时"翻页":
# 用返回的 nextOffset 继续读取下一段 curl "http://localhost:9377/tabs/TAB_ID/snapshot?userId=agent1&offset=74800&includeScreenshot=true"带 offset 的二次读取走缓存路径(见 server.js),不重新解析页面,响应更快。
组合拳实战:一次调用完成"看图 + 理解 + 操作"
一个典型的代理工作流长这样:
- 创建标签页:
POST /tabs打开目标 URL; - 组合拳取快照:
GET /tabs/:id/snapshot?includeScreenshot=true一次拿到可访问性树 + base64 PNG; - 多模态判断:把快照文本和截图一起喂给 AI——文字树负责定位元素,图像负责验证视觉状态(如"登录框是否真的渲染出来了");
- 按引用操作:
POST /tabs/:id/click传ref: "e1"精准点击; - 循环:操作后再次组合拳,持续感知页面变化。
在 OpenClaw 插件形态下,以上能力对应camofox_snapshot与camofox_screenshot两个工具(见 README.md),代理可直接调用。完整接口定义可在 docs/openapi.json 中查阅。
快速上手
git clone https://gitcode.com/GitHub_Trending/ca/camofox-browser && cd camofox-browser npm install && npm start # 服务启动于 http://localhost:9377也可以直接运行:npx @askjo/camofox-browser。首次运行会自动下载 Camoufox 引擎(约 300MB),空闲时内存仅约 40MB,树莓派和 $5 VPS 都能跑 ☕
相关文件导航
- 快照路由与引用标注:server.js
- 截图路由(fullPage 支持):server.js
- 快照窗口分页实现:lib/snapshot.js
- 组合拳 e2e 测试:tests/e2e/snapshotScreenshot.test.js
- OpenAPI 接口文档:openapi.json、docs/api.html
- 插件工具定义:plugin.js
总结:截图让 AI 代理"看得见",可访问性快照让它"读得懂、点得准"。camofox-browser 用一个includeScreenshot=true参数把两者打包成一次调用,配合智能分页,成为 AI 代理浏览器能力的标准姿势。
【免费下载链接】camofox-browserStealth headless browser for AI agents — bypass Cloudflare, bot detection, and anti-scraping. Drop-in Puppeteer/Playwright replacement.项目地址: https://gitcode.com/GitHub_Trending/ca/camofox-browser
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考