关于 qe-browser
qe-browser 是面向 QE 与 CI 浏览器测试的 Vibium 封装,提供类型化断言、批量执行、视觉差异和页面提示注入扫描等专用能力。它也支持基于语义意图的元素查找。
主要功能
- 0116 类页面状态断言
- 02批量执行并在失败时停止
- 03与基线进行像素差异比较
- 04扫描页面中的提示注入
- 05按语义意图查找元素
适用场景
- 01验证登录流程及页面状态
- 02在 CI 中运行视觉回归测试
- 03检查不可信页面的提示注入
- 04通过批处理运行端到端步骤
MCP 相关
底层 Vibium 提供 MCP 服务,可供 MCP 客户端执行导航、页面映射和交互。QE 专用断言、批处理、视觉差异、注入扫描和意图评分仍通过本 Skill 的脚本使用。
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ proffesor-for-testing/ agentic-qe --skill qe-browser安装后在 Claude Code 中输入/qe-browser确认已加载。
包含的文件
除 SKILL.md 外,安装时一起下载的参考资料和脚本。
evals/qe-browser.yamlfixtures/package.jsonserve-skills.jsreferences/assertion-kinds.mdmigration-from-playwright.mdschemas/output.jsonscripts/assert.jsbatch.jscheck-injection.jsintent-score.jspackage.jsonsmoke-test.shvalidate-config.jsonvisual-diff.jsscripts/lib/vibium.js详细介绍
QE Browser
由 AQE 维护的轻量级 Vibium 封装,增加了 QE 专用原语:类型化断言、批量执行、与基线进行视觉差异比较、提示词注入扫描和语义意图评分。
引擎: Vibium——单个约 10MB 的 Go 二进制文件,基于 WebDriver BiDi(W3C 标准)构建,采用 Apache-2.0 许可证,并发布于 npm/PyPI/Maven Central。首次使用时会自动启动后台守护进程,并自动下载 Chrome for Testing。
为什么选 Vibium,而不是 Playwright?
- 10MB 二进制文件,而 Playwright 安装约为 300MB
- WebDriver BiDi 标准(而非 CDP)——面向 Firefox/Safari,具备前瞻性
- 每条命令都支持
--json模式(符合 AQE 的结构化输出规则) - 内置 MCP 服务:
npx -y vibium mcp - 一流的语义定位器:
find text|label|placeholder|testid|role|xpath|alt|title
平台支持(已于 2026-04-09 针对 Vibium v26.3.18 验证)
| 平台 | npm install -g vibium | vibium go <url> | smoke-test.sh |
|---|---|---|---|
| macOS arm64(Apple Silicon 原生) | ✅ | ✅ | ✅ |
| macOS x64(Intel) | ✅ | ✅ | ✅ |
| Linux x86_64 | ✅ | ✅ | ✅ |
| Windows x64 | ✅ | ✅ | 尚未测试 |
| Linux ARM64(aarch64) | ✅ 二进制文件本身 | ⚠️ 需要变通方案 | ✅ 使用变通方案后 |
Linux ARM64 变通方案
Google Chrome for Testing 不提供 linux-arm64 版本。Vibium 在 aarch64 主机上会回退到 chrome-linux64(x86_64),在 Rosetta 下运行时会因 failed to open elf at /lib64/ld-linux-x86-64.so.2 而失败。要在 Linux ARM64 codespace 或容器中运行 qe-browser:
# 1. Install Vibium normally — the vibium binary itself IS native ARM64
npm install -g vibium
# 2. Install Debian's native ARM64 chromium + chromedriver
sudo apt-get update
sudo apt-get install -y chromium chromium-driver
# 3. Symlink Vibium's broken cached binaries to the native system ones.
# Run after `vibium install` (auto-runs on first `vibium go`).
for dir in ~/.cache/vibium/chrome-for-testing/*/; do
# Newer Vibium layout (v26.3.x): chromedriver and chrome at the root
if [ -e "$dir/chromedriver" ]; then
rm -f "$dir/chromedriver" "$dir/chrome"
ln -s /usr/bin/chromedriver "$dir/chromedriver"
ln -s /usr/bin/chromium "$dir/chrome"
fi
# Older Vibium layout: chromedriver-linux64/ and chrome-linux64/ subdirs
if [ -e "$dir/chromedriver-linux64/chromedriver" ]; then
rm -f "$dir/chromedriver-linux64/chromedriver" "$dir/chrome-linux64/chrome"
ln -s /usr/bin/chromedriver "$dir/chromedriver-linux64/chromedriver"
ln -s /usr/bin/chromium "$dir/chrome-linux64/chrome"
fi
done
# 4. Verify
vibium --headless go https://httpbin.org/html
vibium --headless title # → "Herman Melville - Moby-Dick"
此变通方案已在运行 chromium 146.0.7680.177-1~deb12u1 的 Debian bookworm aarch64 上验证可用。请关注上游进展——当 Vibium 添加 --browser-path 标志,或 Google 发布 linux-arm64 版 Chrome for Testing 后,本节内容便不再适用。
无头模式
辅助脚本(assert.js、batch.js、visual-diff.js、check-injection.js、intent-score.js)会自动为每次 vibium 调用注入 --headless,因为 qe-browser 技能面向 QE/CI 使用场景,通常没有显示服务器。Vibium 本身默认“显示界面”——在无头容器中不带 --headless 运行 vibium go 会因 Missing X server or $DISPLAY 而失败。
交互式调试时可选择不启用无头模式:
QE_BROWSER_HEADED=1 node .claude/skills/qe-browser/scripts/assert.js --checks '...'
直接调用 vibium(而非通过辅助脚本调用)时,如果你在容器中运行,请自行传入 --headless:
vibium --headless go https://example.com
vibium --headless title
激活条件
- QE 技能需要导航到网页、读取网页、与网页交互或捕获网页时
- 针对已存储的基线运行视觉回归测试时
- 断言页面状态(URL、文本可见性、控制台错误、网络故障)时
- 验证安全问题的可利用性(渗透测试)时
- 扫描不可信网页中的提示词注入时
- 使用明确的通过/失败门槛运行批量自动化时
核心工作流
每项由浏览器驱动的 QE 任务都遵循相同流程:
- 导航 —
vibium go <url> - 映射 — 使用
vibium map获取元素引用(@e1、@e2、…) - 交互 —
vibium click @e1、vibium fill @e2 "text" - 验证 — 使用此技能的
assert.js运行类型化检查,或使用vibium diff map查看变化 - 如果 DOM 发生变化,则重新映射
# Typical login flow verification
vibium go https://app.example.com/login
vibium map --json > /tmp/refs.json
vibium fill @e1 "$USERNAME"
vibium fill @e2 "$PASSWORD"
vibium click @e3
vibium wait url "/dashboard"
node .claude/skills/qe-browser/scripts/assert.js --checks '[
{"kind": "url_contains", "text": "/dashboard"},
{"kind": "no_console_errors"},
{"kind": "no_failed_requests"}
]'
引用生命周期——使用 diff map
DOM 发生变化时,Vibium 引用会失效。Vibium 提供了 vibium diff map,可以显示自上次调用 map 后新增、移除或重新定位的内容,无需手动为引用进行版本管理。在任何会改变 DOM 的交互之后:
vibium click @e3
vibium diff map --json # shows added/removed/moved refs
这种方式比跟踪版本号更简洁——你会得到结构化差异,可以直接将其传递给下一步操作。
QE 原语(此技能的附加价值)
所有脚本都位于 .claude/skills/qe-browser/scripts/,并通过 shell 调用 vibium。这些脚本要求 vibium 位于 PATH 中(由 aqe init 安装)。
assert.js — 支持 16 种检查类型的类型化断言
node scripts/assert.js --checks '[
{"kind": "url_contains", "text": "/dashboard"},
{"kind": "text_visible", "text": "Welcome"},
{"kind": "selector_visible", "selector": "#user-menu"},
{"kind": "value_equals", "selector": "input[name=email]", "value": "[email protected]"},
{"kind": "no_console_errors"},
{"kind": "no_failed_requests"},
{"kind": "response_status", "url": "/api/user", "status": 200},
{"kind": "element_count", "selector": ".result", "op": ">=", "count": 5}
]'
全部 16 种类型:url_contains、url_equals、text_visible、text_hidden、selector_visible、selector_hidden、value_equals、attribute_equals、no_console_errors、no_failed_requests、response_status、request_url_seen、console_message_matches、element_count、title_matches、page_source_contains。
完整参考:references/assertion-kinds.md。
如果有任何检查失败,退出代码为非零。输出为 JSON:{ "passed": N, "failed": M, "results": [...] }。
batch.js — 多步骤执行,失败时停止
node scripts/batch.js --steps '[
{"action": "go", "url": "https://example.com/login"},
{"action": "fill", "ref": "@e1", "text": "[email protected]"},
{"action": "fill", "ref": "@e2", "text": "secret"},
{"action": "click", "ref": "@e3"},
{"action": "wait_url", "pattern": "/dashboard"},
{"action": "assert", "checks": [{"kind": "no_console_errors"}]}
]' --summary-only
与每一步都调用一次 vibium 相比,可减少往返次数。支持 --stop-on-failure(默认为 true)和 --summary-only。
visual-diff.js — 与存储的基准图像进行像素差异比较
# First run — creates baseline
node scripts/visual-diff.js --name "homepage"
# Subsequent runs — compare
node scripts/visual-diff.js --name "homepage" --threshold 0.05
# Scope to an element
node scripts/visual-diff.js --name "hero" --selector "#hero"
# Reset baseline after intentional change
node scripts/visual-diff.js --name "homepage" --update-baseline
基准图像存储在 .aqe/visual-baselines/ 中(项目本地,默认由 git 忽略)。使用 pixelmatch 进行像素比较;返回相似度百分比和差异图像路径。
check-injection.js — 提示词注入扫描器
扫描当前页面内容,查找已知的提示词注入模式(忽略先前指令、隐藏文本中的系统提示词等)。移植自 gsd-browser 的启发式扫描器(MIT/Apache)。
vibium go https://untrusted-page.com
node scripts/check-injection.js --include-hidden --json
返回按严重程度排序的发现结果。适用于 pentest-validation、injection-analyst 和 aidefence-guardian。
intent-score.js — 15 种语义意图
基于启发式评分发现元素,无需与大模型往返交互。移植自 gsd-browser 的 intent.rs:59-385(MIT/Apache)。
node scripts/intent-score.js --intent accept_cookies
node scripts/intent-score.js --intent submit_form --scope "#login-form"
node scripts/intent-score.js --intent primary_cta
意图:submit_form、close_dialog、primary_cta、search_field、next_step、dismiss、auth_action、back_navigation、fill_email、fill_password、fill_username、accept_cookies、main_content、pagination_next、pagination_prev。
返回评分和选择器排名前 5 的候选项。可用于关闭 Cookie 横幅、查找登录表单,以及在无需映射整个页面的情况下浏览向导。
常见 QE 模式
模式 1 — CI 中的视觉回归
vibium go "$STAGING_URL"
vibium wait load
node scripts/visual-diff.js --name "homepage-$(uname -m)" --threshold 0.02
# Non-zero exit if diff exceeds threshold
模式 2 — 带显式断言的 E2E 流程
node scripts/batch.js --steps @flows/login-flow.json
node scripts/assert.js --checks @assertions/post-login.json
模式 3 — 无需与 axe 往返交互的无障碍审计
vibium go "$URL"
vibium a11y-tree --json > a11y.json
# Analyze a11y.json with axe-core or in-skill rules
模式 4 — 重用身份验证状态
# Once: log in and save state
vibium go https://app.example.com/login
vibium fill "input[name=email]" "$USERNAME"
vibium fill "input[name=password]" "$PASSWORD"
vibium click "button[type=submit]"
vibium wait url "/dashboard"
vibium storage -o .aqe/auth/myapp.json
# Every subsequent run
vibium storage restore .aqe/auth/myapp.json
vibium go https://app.example.com/dashboard
模式 5 — 渗透测试漏洞利用验证
vibium go "$TARGET"
node scripts/check-injection.js --include-hidden > injection-report.json
vibium record start --name "exploit-$(date +%s)"
# Perform exploit steps via vibium commands
vibium record stop -o evidence.zip
模式 6 — 语义化关闭 Cookie 横幅
vibium go "$URL"
# Heuristic scoring — no LLM needed
ACCEPT=$(node scripts/intent-score.js --intent accept_cookies --json | jq -r '.candidates[0].selector // empty')
[ -n "$ACCEPT" ] && vibium click "$ACCEPT"
MCP 集成
Vibium 自带 MCP 服务。使用方法:
claude mcp add vibium -- npx -y vibium mcp
当 Vibium MCP 工具可用(mcp__vibium__*)时,核心的导航、映射、点击和填充操作优先使用这些工具,而不是通过 Shell 调用。继续使用此技能的 scripts/ 处理 QE 专用原语(断言、批处理、视觉差异、注入、意图)——这些功能不属于 Vibium。
回退策略
如果未安装 vibium(例如尚未运行 aqe init,或用户选择不安装),qe-browser 辅助脚本会自动实现相应契约。**无需搜索错误字符串。**每个脚本都会:
- 捕获
lib/vibium.js在二进制文件不在 PATH 中时抛出的VibiumUnavailableError - 输出结构化的
skipped封装(见下方输出契约),在顶层设置vibiumUnavailable: true,并将output.reason设为"browser-engine-unavailable" - 以退出代码 2 退出(已跳过,与 0=成功和 1=失败不同)
- 绝不会静默回退到 Playwright 或 puppeteer-extra
通过 Shell 调用这些辅助脚本的下游技能可以根据结构化字段进行分支:
node .claude/skills/qe-browser/scripts/assert.js --checks "$CHECKS"
EXIT=$?
case $EXIT in
0) echo "passed" ;;
1) echo "failed" ; cat last-output.json ;;
2) echo "skipped — vibium not installed; run \`aqe init\` or \`npm install -g vibium\`" ;;
esac
也可以在 Node 中:
const result = JSON.parse(stdout);
if (result.vibiumUnavailable) {
// Surface skipped status to the caller; do NOT mark as failed
return { status: 'skipped', reason: result.output.reason };
}
从 Playwright 迁移
如果你有现成的 Playwright 测试:
// Playwright
await page.goto('https://example.com');
await page.fill('input[name=email]', '[email protected]');
await page.click('button[type=submit]');
await expect(page).toHaveURL(/dashboard/);
可改为:
# qe-browser
vibium go https://example.com
vibium fill "input[name=email]" "[email protected]"
vibium click "button[type=submit]"
vibium wait url "/dashboard"
node .claude/skills/qe-browser/scripts/assert.js --checks '[
{"kind": "url_contains", "text": "/dashboard"}
]'
完整迁移指南:references/migration-from-playwright.md。
输出契约
所有脚本都会输出结构化 JSON 封装。status 有三种有效值:
success(退出代码 0)
{
"skillName": "qe-browser",
"version": "1.0.0",
"timestamp": "2026-04-09T12:00:00Z",
"status": "success",
"trustTier": 3,
"output": {
"operation": "assert",
"summary": "All 6 assertions passed",
"assert": { ... }
},
"metadata": { "executionTimeMs": 142 }
}
failed(退出代码 1)
结构相同;status: "failed" 表示真实的断言失败或操作错误。output.* 块包含各项检查的详细信息。
已跳过(退出代码 2)— F1 契约
当 vibium 未安装在 PATH 中时发出。顶层的 vibiumUnavailable: true 是下游技能的规范信号。
{
"skillName": "qe-browser",
"version": "1.0.0",
"timestamp": "2026-04-09T12:00:00Z",
"status": "skipped",
"trustTier": 3,
"vibiumUnavailable": true,
"output": {
"operation": "assert",
"summary": "vibium binary not found on PATH. Install via `npm install -g vibium` or run `aqe init`.",
"reason": "browser-engine-unavailable",
"error": "vibium binary not found on PATH...",
"remediation": [
"Install vibium globally: `npm install -g vibium`",
"Or re-run `aqe init` to install via the AQE bootstrap",
"Set QE_BROWSER_HEADED=1 only for interactive debugging (not the cause here)"
]
},
"metadata": { "executionTimeMs": 0 }
}
退出代码摘要
| 退出代码 | 状态 | 含义 |
|---|---|---|
| 0 | success | 所有断言均通过/操作已完成 |
| 1 | failed | 确实发生断言失败或操作错误 |
| 2 | skipped | vibium 不可用;属于环境问题,而非测试结果 |
CI 工具可使用退出代码区分“测试确实失败”(阻止构建)和“由于未安装浏览器引擎,我们无法运行测试”(发出警告,但不阻止构建)。
使用 scripts/validate-config.json 和 schemas/output.json 进行验证。
致谢
- 提示词注入扫描器和意图评分逻辑移植自 gsd-browser(MIT/Apache-2.0)。
- 引擎:Vibium(Apache-2.0)。