概述
多数接口测试只断言几个字段:状态码、一个 id、也许一条错误信息。于是把 created_at 改名成 createdAt、删掉一个嵌套对象、把数字变成字符串,测试全都通过,客户端却在上线后崩溃。黄金文件比较完整的规范化响应,任何变化都会以 diff 形式出现,迫使作者与评审明确判断这是不是有意的接口变更。
步骤
- 编写黄金文件辅助函数,只有显式设置环境变量时才写入:
export async function assertGolden(name, payload) {
const actual = JSON.stringify(sortKeys(payload), null, 2) + '\n';
if (process.env.UPDATE_GOLDEN === '1') {
await writeFile(file(name), actual);
}
assert.equal(await readFile(file(name), 'utf8'), actual);
}
- 消除不确定性:注入固定时钟、把数据库 id 映射为稳定占位符、对键排序、只保留契约字段。
- 为成功、校验失败、空列表分别建立一个小文件,文件名体现行为。
- 更新时使用
UPDATE_GOLDEN=1,并像审查源码一样审查生成的 diff 后再提交。 - 在 CI 中禁止该变量,例如检测到
CI=true且UPDATE_GOLDEN=1时直接抛错。
验证
连续运行两次,黄金文件应逐字节一致;若不一致,说明仍有时间戳、随机 id 或键顺序泄漏。故意重命名字段后,测试应失败并指出具体文件名。CI 中带上 UPDATE_GOLDEN=1 应直接报错,确保快照无法在流水线里被自动接受。
注意事项
- 精确字节比较对纯格式变化很敏感,规范化是设计的一部分。
- 黄金文件不校验类型与必填字段,应与 JSON Schema 或 OpenAPI 响应校验配合使用。
- 快照可能包含密钥或个人数据,必须脱敏,禁止直接保存生产响应。
- 一个大文件覆盖整个 API 难以阅读且经常冲突,应拆分为每个接口每个场景一个文件。
- 行尾差异会让 CI 误报,建议对黄金目录设置
text eol=lf。