mcpField
Q
qualityforge

qualityforge

本地服务
github.com/ninelegsdog开发工具06 天前更新

关于 qualityforge

QualityForge 是基于 Playwright 的浏览器 QA 框架,面向需要统一测试证据和质量门禁的团队。其只读 MCP 服务让 AI Agent 检查失败记录和运行历史,但不能操作应用。

主要功能

  1. 01捕获 trace、截图和失败视频
  2. 02将失败整理为标准缺陷产物
  3. 03按明确阈值设置质量门禁
  4. 04收集并脱敏控制台与网络信号
  5. 05跟踪运行历史和质量趋势
  6. 06提供 MCP 工具、资源与分诊提示词

适用场景

  1. 01根据保存的证据诊断浏览器测试失败
  2. 02判断故障是否间歇出现或反复发生
  3. 03检查控制台、网络和页面错误
  4. 04查看无障碍审计结果

MCP 相关

提供基于 stdio 的只读 MCP 服务,包含运行摘要、失败、缺陷、趋势和无障碍审计工具,并提供资源及 `triage_failure` 提示词。它向 Agent 提供已收集的 QA 证据,但不授予操作应用的能力。

配置

本地服务的配置在各客户端中通用,复制后粘贴到客户端的 MCP 配置文件即可。

mcp.json · 通用配置
{
"mcpServers": {
"ninelegsdog-qualityforge": {
"command": "npx",
"args": [
"-y",
"qualityforge"
]
}
}
}
启动命令npx -y qualityforge

本地服务需要在你的电脑上安装运行环境(如 Node.js 18+)。各客户端的配置文件位置不同,请参考客户端文档。

安装包
npmqualityforge0.2.3

工具

还没有获取到工具列表

本地服务需要在你的电脑上运行后才能读取工具,维护者暂未提供工具列表。

详细介绍

QualityForge

面向现代 Web 应用、以证据为先的浏览器质量自动化。

QualityForge 是构建在 Playwright 之上的开源基础框架,可将失败的运行转化为机器可读的证据:包含跟踪记录、屏幕截图和视频的规范化缺陷产物;具有明确阈值的质量门禁;对控制台、网络和页面错误信号的捕获;以及一个只读 MCP 服务,可将所有信息交给 AI 助手,同时不赋予其执行操作的能力。

CI npm Node >= 22 MCP protocol 2026-07-28 License

状态 — 稳定,已发布。 [email protected] 自 2026-10-21 起已发布到 npm(0.1.0 于 2026-10-15 发布,是首个稳定版本),缺陷契约为 1.6.0 版的 defect.v1。0.x 系列仍允许在次版本中进行破坏性变更,因此请固定安装的版本。

目录

存在的原因

大多数团队最终都会为每个项目积累大量一次性的 UI 测试:选择器重复、没有共享的失败证据,也无法跨项目查看质量。QualityForge 提供了可复用的核心方案:使用一份配置、一种证据格式和一套质量门禁,适用于任意 Web 应用。

它的差异化之处不在于“AI 编写测试”。Playwright 已经内置了相关 Agent。它的核心是失败的运行与任意 Agent 之间的证据层:将缺陷产物规范化为统一的架构,让读取者无需获得执行操作的能力也能读取。

你将获得什么

  • 证据流水线。 在首次重试时记录跟踪信息,失败时截取屏幕截图并录制视频,支持 Chromium、Firefox 和 WebKit。即使运行失败,也会发布其产物。
  • 统一的规范化缺陷格式。 defect.v1,契约 1.4.0:每次失败都会生成一个带版本、经过验证的产物,它扩展了 Playwright 的 error-context.md,而不是重复其中的内容。
  • 质量门禁。 收集器按 spec × project 拆分,拒绝重复 ID,将中止的套件视为一次服务中断,而非每项测试各算一个缺陷;当阈值被违反时,以非零状态退出。
  • 信号捕获。 捕获控制台错误、未捕获的页面错误、失败的请求以及状态码高于 400 的 HTTP 错误;在源头进行脱敏,按类别限制数量,并提供 signals.dropped 计数,确保截断后的捕获结果不会被误认为完整。
  • 只读 MCP 服务。 使用协议 2026-07-28,提供十三个工具、资源和一个 triage_failure 提示词;已通过真实 stdio 与 OpenCode v2.0.16 验证。
  • 运行历史。 每次运行生成一个精简文件,回答“这是回归问题,还是一直如此”。
  • 会自检的 CI。 六个任务:lint 和类型检查、在 Node 22 和 24 上运行单元测试、在三个浏览器上运行套件;另有一个任务会安装真实的 OpenCode 客户端,并验证通过线路传输的帧。

快速开始

开发需要 Node.js 22 或更高版本——Node 20 已于 2026 年 3 月结束生命周期,而且 "engines": ">=22.0.0" 明确说明了这一点,而不是承诺对安装过程网开一面。CI 使用 Node 22 和 24,最低版本取两者中较低的那个。.nvmrc 为贡献者指定了 22:在这台机器上,某个 Node 24.21.0 构建版本会导致 tsc 以段错误退出,而且可以稳定复现。如果你使用版本管理器,请先运行 nvm use。

平台。 CI 在 Linux 上运行,因此 Linux 是经过验证的平台。核心代码采用跨平台编写方式——全程使用 path.sep 和 path.relative,不调用仅适用于 POSIX 的接口——所以 Windows 和 macOS 应该也能运行,但_尚未经过测试_。请将它们视为未经验证的平台,而不是受支持的平台。

git clone https://github.com/ninelegsdog/qualityforge.git
cd qualityforge
npm ci
npx playwright install --with-deps chromium
npm test

npm test 会自动启动随附的演示应用,因此全新克隆后无需配置,也不依赖第三方网络即可顺利运行。运行 npm run report 打开 HTML 报告。有关逐步操作指南——查看带有证据的真实故障、收集缺陷产物、连接 Agent、让套件测试你自己的应用——请参阅 docs/quick-start.md,或 docs/quick-start.ru.md。

演示应用

fixtures/ 是一个小型多页面应用,旨在为套件提供实际测试对象。它不是模拟应用:它会渲染、验证并获取数据。

路由功能
/概览页面,包含标题、状态读数,以及从 /api/items 获取的实体列表
/docs包含证据策略的文档页面
/contact包含客户端验证和无障碍错误报告的表单
/api/items为实体列表提供数据的 JSON 载荷
/boom故意返回 500,用于测试证据流水线

每个控件都有标签,每条消息都有角色,每个测试所需的元素都有稳定的标识——套件断言的是用户能感知到的内容,而不是标记结构。

证据流水线

项目的核心承诺是:故障发生时会留下足够的证据用于诊断,而且这一承诺经过了测试,而非仅仅宣称:

QUALITYFORGE_EVIDENCE_CHECK=1 npx playwright test tests/smoke/evidence-pipeline.spec.ts

这会运行两个故意失败的测试,并以非零状态码退出。之后,test-results/ 中会为每次故障包含以下内容:

产物生成原因
test-failed-1.pngscreenshot: "only-on-failure"
video.webmvideo: "retain-on-failure"
trace.ziptrace: "on-first-retry"——本地运行不会重试,因此请在本地添加 --trace on
error-context.md结构化故障摘要:测试名称、位置、错误、预期值、实际值

error-context.md 最值得关注:它以给助手的指令形式写成——“说明原因、简洁作答、遵守最佳实践”——随后列出测试名称、文件位置、错误和预期值差异。这是 Agent 所需的原始素材,而且无需额外成本。

在 CI 上调试时,优先使用追踪查看器,而不是截图和视频:它能提供每个操作对应的 DOM 快照,以及完整的网络日志。

缺陷产物

只有在无需重新运行任何内容、稍后仍能读取失败信息时,失败的测试才有用。QualityForge 会将每次失败转换为一个标准化、带版本的产物:

npm test                    # writes artifacts/json/playwright-results.json
npm run defects:collect     # writes artifacts/defects/<runId>/
{
  "id": "form-validation-smoke-shows-an-error-when-email-is-empty",
  "status": "failed",
  "test": { "file": "tests/smoke/form-validation.smoke.spec.ts", "line": 15 },
  "failure": {
    "message": "Error: expect(locator).toHaveText(expected) failed\n\nExpected: \"Email is required\"",
    "errorContextRef": "test-results/.../error-context.md",
  },
  "evidence": { "screenshot": "test-results/.../test-failed-1.png" },
  "context": { "commit": "43c761f", "baseUrl": "http://127.0.0.1:4311" },
  "flakiness": { "verdict": "unknown", "attempts": 1 },
}

该产物有意扩展 Playwright 的 error-context.md,而不是重复其中的内容:它会记录该文件的路径,并添加稳定标识、运行关联信息、VCS 上下文、证据指针和不稳定性判定。signals 块——控制台错误、未捕获的页面错误、失败的请求、状态码高于 400 的 HTTP 错误——由捆绑的 fixture 实时收集,因为“找不到元素”是症状,而“页面抛出了 TypeError”才是原因。完整规范请参阅 docs/defect-schema.md。

无障碍性是一项独立的第二种测量,而不是该产物中的一个字段:npm run a11y:audit 会对页面运行 axe-core,并写入 a11y-audit.v1——每条规则最多保留十个节点,并注明丢弃的数量;将 html 精简为结构,因为它包含页面内容;保留 target,因为没有它就无法区分各个节点。请参阅 docs/a11y-schema.md。

npm run defects:collect 也可作为 CI 质量门禁:门禁通过时退出码为 0,违反阈值时为 1,完全无法运行收集时为 2。

安装软件包
npm i [email protected]

latest 指向此版本。无论如何,都应固定到所需版本,而不是信任标签名称:npm 不允许移除 latest,因此标签只能向前移动;裸命令 npm i qualityforge 会安装标签当前指向的版本,而不是你测试过的版本。

使用该软件包的项目会从构建产物导入 fixture——Playwright 拒绝转译 node_modules 下的 TypeScript,因此该 fixture 通过 exports 中的子路径发布:

import { expect, test } from "qualityforge/fixtures/quality-context.js";

只需更改这一处导入即可完成全部集成:控制台、页面错误和网络捕获都会自动启用。所有捕获的数据都会在源头进行脱敏——URL 保留协议、主机和路径,并移除查询字符串和凭据;控制台文本中的令牌和 JWT 会被替换;敏感标头值会被遮盖,但标头名称会保留——并且每个类别最多捕获 40 条记录。

@playwright/test 是一个对等依赖:使用该软件包的项目需自行提供;如果缺少该依赖,npm 7+ 会自动安装,因为没有它 fixture 就无法运行。声明的版本范围是 ^1.63.0;CI 验证的版本是 1.63.0,并在 devDependencies 中精确固定;如果软件包不再声明该对等依赖,或 npm 不再为使用方安装它,npm run package:check 就会失败。

bin 条目会发布使用该软件包的项目要运行的两个命令——始终通过 npx --no-install 运行,因为它可以确保不会为了获取别人的代码而访问注册表:

npx --no-install qualityforge [flags]                          # the collector
npx --no-install qualityforge-mcp [--root <dir>] [--history <dir>]

MCP 服务

npm run mcp 会通过 stdio 启动只读 MCP 服务,使用协议 2026-07-28。它向 Agent 提供证据层:出了什么问题、问题出在哪里,以及页面在出问题时的状态。 已在 Linux 上连接并通过 OpenCode v2.0.16 验证,配置如下;根据决策,Kilo 和 MiMo 不在范围内——详见本节末尾。

{
  "$schema": "https://opencode.ai/config.json",
  "mcp": {
    "qualityforge": {
      "enabled": true,
      "type": "local",
      "command": ["node", "/absolute/path/to/qualityforge/dist/mcp/index.js"],
    },
  },
}

安装了此软件包的项目无需提供路径: ["npx", "--no-install", "qualityforge-mcp"] 会从 node_modules/.bin 启动同一服务。该命令指向 dist/,而 npm ci 会构建此目录 (prepare 会运行 tsc);如果安装时使用了 --ignore-scripts,则运行 npm run build。随后,opencode mcp list 会报告连接状态; 请多运行几次再作判断——该状态只是对仍在建立中的连接的采样,并非最终结论。

工具说明
quality_get_latest_run计数、门禁、每个维度的判定、策略链、历史判定
quality_list_failures精简记录:ID、状态、测试位置、偶发性
quality_get_defect单个缺陷的完整信息,包括控制台、网络和页面错误信号
quality_flaky_tests各次运行中失败的测试规格:偶发失败、持续失败、新增或已消失
quality_get_trend每次运行的通过率、趋势方向、持续时间、不同的失败测试规格
quality_list_audits已记录的无障碍审计,按时间从新到旧排列,并标明是否全部通过
quality_get_audit单次审计的完整信息,包含每条规则针对真实节点保留的计数

此外还有最新运行摘要和任意缺陷的资源,以及一个会先询问事实再提出假设的 triage_failure 提示词。

连接前须知
  • 先生成产物。 找不到产物根目录时,服务会以状态码 1 退出,而提示信息会写入 stderr,客户端会将其丢弃——因此你只能看到 failed: Connection closed。请先运行测试套件和 npm run defects:collect,或传入 --root <dir>。
  • 使用绝对路径。 客户端会从_你的_项目目录启动服务,而不是从此检出目录启动,因此相对路径的根目录会解析到不存在的位置。
  • 明确指定运行器。 配置指向 dist/,因此连接时不会进行转译:此处 initialize 的响应时间约为 0.24 秒,而 ["npx", "tsx", …, "src/mcp/index.ts"] 约为 2.4 秒;OpenCode 文档记载的默认 MCP 超时为 5000 ms。
  • 两种配置形式都能连接。 上文展示的扁平形式 mcp.<name> 和 V2 文档记载的 mcp.servers.<name> 均已在 v2.0.16 上连接成功。区别在于写入的是哪个文件,而不是能否正常工作。
从结构上确保只读

服务中不存在写入路径:没有任何工具会修改数据,存储层也不提供任何修改方法。只读是结构上的保证,而非承诺。

客户端提供的每个路径都被视为不可信,因为客户端侧的路径允许列表只是便利措施,并非安全边界。绝对路径、百分号解码前后的 .. 路径遍历、NUL 字节,以及解析后指向根目录之外的符号链接,都会被拒绝;拒绝消息也绝不会回显文件系统布局,因为它可能出现在对话记录中。

为何手写协议。 我们对官方 @modelcontextprotocol/sdk 进行了核查,而非想当然地假定其支持:版本 1.32.0 声明了 LATEST_PROTOCOL_VERSION = "2025-11-25",但不包含 server/discover、resultType、ttlMs/cacheScope 或 subscriptions/listen——它并未实现 2026-07-28。仍接受 2025-11-25 握手,因为即使客户端从未发送 initialize,仍应能获取 tools/list。

Kilo 和 MiMo 经决定不予支持,这不只是未经测试。所有者于 2026-10-03 决定不再跟进:第三个客户端所需的服务端工作,最好投入到唯一实际存在的客户端上。如果你使用它们,本文档并未说明上方的阻止措施是否会被接受。

配置

config/project.json 声明项目名称、被测来源、证据策略、门槛阈值以及产物的写入位置。加载时会对其进行验证,并一次性报告所有问题及其确切路径:

Configuration error: Invalid configuration in /…/config/project.json
  - thresholds.maxFailureRate must be a number between 0 and 1, got "high"
  - baseUrl must not contain credentials, a query string or a fragment
运行历史

可选的 history 区块会为每次运行保存一个精简文件,从而回答“这是回归问题,还是一直如此”:

"history": { "directory": "quality-history", "keep": 200 }

有意将其提交到仓库中,与 artifacts/ 不同:每条历史记录只有几百字节的计数和结果,而它是让一次运行值得进行的唯一依据。每条记录都会记录哪些规格未通过,并由两个 MCP 工具读取:quality_flaky_tests 会区分后来恢复的规格和始终未恢复的规格;quality_get_trend 会报告一段时间内的趋势,并在运行次数少于四次时返回 unknown。若不设置,历史记录功能将关闭,不会额外写入任何内容。

命令

npm test                    # full suite
npm run test:smoke          # Chromium only
npm run test:unit           # unit tests, no browser launched
npm run test:debug          # Playwright Inspector, step through a test
npm run report              # open the HTML report
npm run report:clean        # remove generated output
npm run build               # compile src/ to dist/ (an install runs this for you)
npm run defects:collect     # build defect artifacts from the last run
npm run defects:check       # prove two report-shape rules on a real Playwright run
npm run a11y:audit          # audit a page for accessibility, into artifacts/a11y/<runId>/
npm run mcp                 # start the read-only MCP server on stdio
npm run mcp:check:all       # drive the server over real stdio and check it
npm run mcp:schema          # cross-check capabilities against the client's binary
npm run mcp:live            # connect the real opencode client and assert the wire
npm run verify              # lint + typecheck + build + format check (CI runs this first)

基于 Python 的检查项——mcp:check*、mcp:schema、mcp:live、defects:check、docs:numbers、docs:support、docs:tools 和 ci:validate——分别放在独立脚本中,因此只安装了 Node 也能运行 verify。mcp:live 还需要 opencode 二进制文件;若缺少该文件,检查会失败而不是跳过——没有客户端却悄悄通过的实时客户端检查,只是摆设。

CI 中强制执行的规则

  • lint 规则禁止使用 page.waitForTimeout()。它是导致测试不稳定的主要原因;应等待真实条件。
  • 禁止使用 test.only() 和 describe.only()。在 CI 中,它们会悄悄跳过套件的其余部分。
  • @typescript-eslint/no-floating-promises 属于错误。Playwright 调用漏写 await 会导致测试悄悄地什么也没断言。
  • 选择器策略由 lint 强制执行,并非建议:在字面量 locator() 参数中使用 CSS、XPath 和 text= 简写都会导致 npm run lint 失败。选择器层级——先角色,再标签,再文本,最后才是 data-testid——见 docs/selectors-and-testid.md。
  • 格式检查和类型检查必须通过。

本仓库中的一切都遵循同一条规则:只有在真实环境中运行,并观察到它因正确的原因而失败后,才算完成。 关于报告、协议帧和运行器判定的说法,都会对照真实生成方进行核验,绝不依赖手写的测试样例。

文档

如果你想基于此项目启动项目,而不是阅读文档:模板 https://github.com/ninelegsdog/qualityforge-template 会从 git 安装此软件包, 在全新克隆后即可成功运行,并且已写好 MCP 配置块。

参与贡献

参见 CONTRIBUTING.md — 环境搭建、拉取请求规则、测试要求, 以及 AI 辅助贡献的要求。使用问题模板提交缺陷报告或 功能请求;提交拉取请求时,请使用 PULL_REQUEST_TEMPLATE.md。

安全问题:请先阅读 SECURITY.md — 不要为此公开提交问题。

许可证

Apache-2.0 — 参见 LICENSE。坦诚行事,并假定他人出于善意: 社区准则见 CODE_OF_CONDUCT.md。

为什么优先收集证据?

普通测试运行器只会说“失败”。QualityForge 会告诉你“为什么失败”——收集证据,便于 Agent 或人工快速分析。

失败时收集的证据

  • Screenshot — 失败时页面状态的截图
  • Trace/Video — 用于重现问题的 Playwright 跟踪记录
  • Logs — 控制台日志和网络事件
  • HAR — 网络流量(可选)
  • Context — URL、视口、步骤、预期结果

与 Agent 集成

附带只读 MCP 服务。Agent 可以读取失败证据、了解上下文,并提出有针对性的修复方案,无需猜测。

已用于生产环境

QualityForge 用于验证 BotKit 生态系统中的 9 个生产级 Telegram 机器人,验证工作通过 botkit-farm 进行。MCP 服务使 AI Agent 能够利用完整证据(跟踪记录、截图、网络日志)分析测试失败,而无需直接访问代码或修改代码。

专注于 Agent 基础设施

作为更广泛的 Agent 开发基础设施的一部分构建——为 AI 编码 Agent 提供工具链、质量门禁和验证优先的工作流。

评论

支持 Markdown

第一次接触 MCP?

从协议是什么,到在客户端里装上第一个服务,这几条回答覆盖了大多数入门问题。

一个开放协议,规定了 AI 应用如何以统一方式连接外部工具与数据源。客户端负责与模型对话,MCP 服务负责提供工具、资源和提示模板,两者通过标准消息通信,同一个服务可以被不同客户端复用。