给 Agent 做版本回归测试,先固定任务集、验收规则和可控制的环境,让新旧配置逐题对照。先看修好了什么、退步在哪里,再看耗时、费用和人工投入是否符合预先约定的采用条件。总通过率提高,是打开结果清单的起点。
改了一段提示词,原来漏掉的筛选条件终于被执行;换了一个模型,总通过率也提高了。现在要回答的是:这套新配置能不能替换旧版?
下面以“读取订单文件,汇总已付款金额并生成结果文件”为例,给出一套可以照着准备的回归检查流程。本文全部任务、编号、数字和结果均为构造示例,不对应 EvalDock 或任何产品的实测。
1. 先写清采用条件,再开始运行
订单任务除了金额算对,还要求金额缺失时列出异常、原始输入文件保留。假设这次修改是为了修复“把未付款订单也计入总额”。运行前先填一张约定表:
| 项目 | 本例的检查要求 |
|---|---|
| 目标改善 | 混有未付款订单时,只汇总已付款金额 |
| 原有能力 | 普通汇总仍正确,金额缺失仍按约定列出异常 |
| 关键要求 | 原文件不能被覆盖;确认出现即暂停替换并排查 |
| 可接受代价 | 提前填写耗时、调用费用、人工协助的上限 |
| 改动范围 | 记录模型、提示词、工具、权限、重试策略的全部差异 |
如果同时换模型、改提示词,结论只针对这套新配置。要归因到其中一项,需要拆开再做对照。
资源上限应来自实际工作需要。例如,交互查询关心等待时间,定期批量汇总可能更关心总费用。不要看完结果后才为新版调整上限。
2. 固定测试集:修复题、原有能力、留出题都要跑
只重跑刚刚修好的那道题,无法发现其他能力退步。建议把任务分成三组,并让两版都执行:
| 任务组 | 订单例子 | 本组要回答的问题 |
|---|---|---|
| 修复目标 | 已付款与未付款混合、付款状态顺序变化 | 目标错误是否得到改善? |
| 原有能力 | 普通订单、金额缺失、原文件保留 | 原来能做好的事情是否仍可用? |
| 未用于调试的留出题 | 事先留出的新订单文件、独立设计的边界输入 | 改善能否延伸到没反复调试过的材料? |
Anthropic 的 Agent 评测方法文章区分了能力评测与回归评测:前者观察能否完成更难的任务,后者检查过去能完成的任务是否仍然可用。本篇关注的是新旧配置比较和回归。
“固定”至少要留住以下信息:输入文件及校验值、任务要求、预期输出、必需检查项、环境快照、配置记录、超时和重试规则。某次任务只有全部必需检查通过,才计为通过。
两版每次都从干净环境开始,不能让新版读到旧版的产物。数据库用相同起始快照,外部服务记录执行时间与不可还原条件;两版无法对齐的条件单列说明。发现验收规则有错时,要用修正后的同一规则重新检查两版受影响的结果。
留出题一旦参与反复调提示词,就成为调试材料,应记录用途变化并补充新的留出输入。三组结果分别报告,不能把刻意收集的易错题通过率当成日常使用成功率。
3. 逐题对照:把新增失败单独列出来
以下是构造的一轮结果:20 个不同任务,每版各执行一次,两版共 40 次。任务编号仅用于说明对照方法。
| 同一任务的新旧结果 | 数量 | 对照后要检查什么 |
|---|---|---|
| 旧版通过,新版通过 | 12 | 完成质量和代价是否变化 |
| 旧版失败,新版通过 | 5 | 是否命中目标问题,有哪些证据 |
| 旧版通过,新版失败 | 2 | 退步的具体要求、产物及影响 |
| 旧版失败,新版失败 | 1 | 尚未解决的问题是否影响采用范围 |
旧版通过 14/20=70%,新版通过 17/20=85%,提升15 个百分点,净增加 3 个通过。这不等于“只改善了 3 道题”:实际有 5 个新增通过,同时有 2 个新增失败。
构造示例:20 个任务两版各执行一次;总通过率上升时,仍需逐项检查 2 个新增失败,不能由净增数量直接决定替换。
进一步展开两条退步记录:
| 任务 | 旧版 | 新版 | 新增失败及证据检查 |
|---|---|---|---|
| T18:原文件保留 | 通过 | 失败 | 输入文件被覆盖;对照运行前后校验值与写入记录 |
| T19:缺失金额处理 | 通过 | 失败 | 异常清单漏项;核对预期异常行与实际输出 |
这两条也是构造示例。校验值变化提示输入发生改变,仍需结合文件内容和写入记录确认是否违反任务要求;金额异常则要回到对应输入行核对。先确认失败判定,再分析新配置的原因。
按第 1 节的关键要求,出现原文件被覆盖就应暂停替换。筛选错误得到修复的收益可以保留记录,但不能抵消关键违规。
4. 用短脚本汇总,保留逐题证据
下面的 Python 3 脚本只使用标准库,可以直接保存为compare.py,执行python3 compare.py。它用构造的布尔结果重现上表;脚本不调用 Agent,也不负责自动验收文件。实际使用时,应把old、new替换为经过同一检查规则确认的逐题结果。
fromcollectionsimportCounter# 构造示例:每个任务两版各执行一次,不是产品实测。# T01—T12 共同通过;T13—T17 新增通过;T18—T19 新增失败。old={f"T{i:02d}":i<=12oriin(18,19)foriinrange(1,21)}new={f"T{i:02d}":i<=17foriinrange(1,21)}ifnotoldorold.keys()!=new.keys():raiseValueError("需要非空、完全相同的任务集合")ifany(type(v)isnotboolforvin[*old.values(),*new.values()]):raiseValueError("结果必须是布尔值;缺失、设施异常请先单列处理")counts=Counter((old[k],new[k])forkinold)labels={(True,True):"共同通过",(False,True):"新增通过",(True,False):"新增失败",(False,False):"共同失败"}forpair,labelinlabels.items():ids=[kforkinoldif(old[k],new[k])==pair]print(f"{label}:{counts[pair]},任务:{', '.join(ids)or'无'}")n=len(old)a,b=sum(old.values()),sum(new.values())print(f"旧版:{a}/{n}={a/n:.0%},新版:{b}/{n}={b/n:.0%}")print(f"变化:{(b-a)/n*100:.0f}个百分点")# 费用也是构造数据,包含本轮所有成功和失败调用。forlabel,cost,passedin[("旧版",20,a),("新版",34,b)]:unit=f"{cost/passed:.2f}元"ifpassedelse"不适用(零次通过)"print(f"{label}调用总费用:{cost}元,每次通过分摊费用:{unit}")预期输出包含:共同通过 12、新增通过 5、新增失败 2、共同失败 1;旧版 70%、新版 85%、变化 15 个百分点;每次通过分摊调用费用分别为 1.43 元和 2.00 元。
缺失结果不能默认为失败或通过;设施异常要与 Agent 任务失败区分。Agent 超时若按约定属于失败,应计入结果并保留原因。需要排除或重跑时,两版规则一致,明确数量、理由与成本归属;不能静默删掉坏结果。
汇总表之外,每次执行还应保留:任务编号、配置、检查项及判定、产物位置、失败原因、耗时、费用、人工补充与返工记录。数字异常时可以回到原始证据,而不是只剩一个通过率。
5. 耗时、费用、人工投入使用同一口径
先比较全部计划任务的投入,再拆开成功、失败和超时。只看成功运行,会漏掉失败尝试已经消耗的资源。
| 记录项 | 对照口径 | 本构造示例 |
|---|---|---|
| 耗时 | 同一计时起止,记录每次耗时、累计执行时间;并行时批次墙钟时间另列 | 未设定数值,实际测试需补齐 |
| 调用费用 | 两版相同计费范围,纳入失败和约定重试;外部服务费用单列 | 旧版 20 元,新版 34 元,各执行 20 次 |
| 人工投入 | 补充说明、结果检查、返工分别记录分钟数,采用相同计时规则 | 未设定数值,不能记成零投入 |
| 每次通过分摊调用费用 | 全部调用费用 ÷ 通过次数;零次通过时不计算 | 旧版约 1.43 元,新版 2.00 元 |
这里的费用仍是构造数据,不是产品报价。新版多完成任务,但每次通过分摊的调用费用增加;该指标也没有包含人工成本。缺少耗时和人工记录时,就不能宣称“整体更省”。
需要按真实使用频率加权时,在看结果前确定任务组权重并说明依据。公开报告中的维度均分与本文按必需检查计算的任务通过率,是不同指标,不混成一个结果。
6. 按采用条件决定下一步
每题只跑一次适合发现差异,还不足以证明改善稳定。可以事先为两版安排相同次数的独立运行,交错执行,保留全部尝试。这里的补测用于验证新旧差异是否持续;不要把同一任务的多次运行当成多个不同任务,也不要把临时专项补测混入原来的 20 题总表。
如果实际产品允许重试,两版使用相同重试规则,同时报告首次执行与允许重试后的完成情况,耗时费用包含全部尝试。结果接近或波动明显时继续补测;要声称稳定提升,还需报告不确定性并考虑同一任务多次运行的关联。
| 观察结果 | 采用动作 |
|---|---|
| 目标问题改善,关键要求守住,代价达标 | 在已测范围内扩大试用,继续观察真实使用表现 |
| 改善集中在特定任务,且能可靠识别和隔离 | 限定范围试用,保留旧配置作为恢复选项 |
| 总通过率提高,但出现关键违规或重要退步 | 暂停替换,修复后检查受影响任务及相关能力 |
| 差异不清楚,或环境、资源数据不完整 | 保留“尚不足以决定”,补齐证据 |
对本文构造案例,可写成:“新版修复了部分筛选问题,但原文件保留要求发生退步,且耗时与人工投入尚未补齐;暂不替换,先修复退步,再按相同任务和规则回归。”
下面的模板可以直接放进一次版本采用记录:
目标问题与预期改善: 旧配置 / 新配置 / 全部改动: 固定测试集版本、输入校验值与环境快照: 修复目标 / 原有能力 / 留出题的数量: 必需检查、关键要求、资源上限、超时与重试规则: 每题计划运行次数及实际完成次数: 共同通过 / 新增通过 / 新增失败 / 共同失败: 新增失败对应的任务要求、产物及检查证据: 全部计划任务的耗时、调用费用、人工投入及缺失项: 设施异常、排除、重跑和专项补测记录: 采用 / 限定试用 / 暂停 / 继续补测的理由: 适用范围、后续观察与恢复安排:EvalDock 的评测方法强调让任务、运行条件和证据对应,优化后在相同任务、环境与评分标准下复测。
EvalDock 是面向各类 Agent 的跨生态评测与选型平台,结合任务过程、工具调用和交付结果,为开发者提供针对性的优化方案。版本比较时,把目标收益、具体退步与采用条件放在同一份记录中,下一步要修什么、补测什么就更清楚。
本文由 EvalDock 团队撰写。