实验一:运行一份确定性 Eval¶
本篇要解决什么问题¶
第一次动手先不接模型 API,你要从 Dataset 一直跑到 Trial(试验)、Attempt、Artifact、Score、Metric 和 Gate,把整条路走通。这样哪一步出错,你都能在本地稳定复现,不会让网络、额度或模型漂移把问题盖住。先跑运费案例,然后打开报告,从结论倒着查回产生这次失败结论的整条证据链。
核心机制¶
配置先把两个 Target 和三个 Sample 定下来,Planner 再据此建出六个 Trial,本地脚本逐个算出 fee,最后由 Scorer(评分器)拿它和 expected 比较。Gate 要求所有样本都通过,而一次 Run 用到的根证据全部放在输出目录里,后面跑 inspect、score 或 gate 时都只读这份目录,所以你能沿同一条证据链把每个结论查回去。
完整流程¶
- 在仓库根目录确认 Python 3.12 与 uv 可用;
- 运行案例到新的输出目录,不复用旧 Run;
- 执行 inspect,记录 Trial、Bundle 与 Score 数量;
- 打开 evidence.json,找到
amount-100+buggyTrial; - 沿 canonical Attempt、Bundle、Score、Metric 到 Gate 写出链路;
- 对照 Dataset 和脚本手算 fee。
uv sync
uv run eval-harness-ref run reference/examples/shipping/eval.yaml --output output/lab-01
uv run eval-harness-ref inspect output/lab-01
关键数据与不变量¶
计划里必须有 6 个 Trial,每个完成的 Trial 只能选定一个 canonical Attempt,Artifact 的 digest 也必须和实际 bytes 对得上。两个 Target 各自的 Metric denominator 都等于 3,而 Score failed 和 Attempt succeeded 可以同时出现:前者说产品结果没过关,后者只说程序顺利跑完了。这两件事不能混。
动手实验¶
从 output/lab-01/artifacts 中任选一个 Artifact 文件,在末尾追加一个字符,然后运行下面的检查命令。
先别修报告,你要先说清楚问题究竟出在证据、评分还是 Gate 这一层。
预期输出与答案¶
第一次运行时,程序会打印报告路径,同时告诉你两个 Target 分别得到了什么结论。
inspect 仍然读同一份证据目录,所以下面每个数字都必须能在目录里找到对应的证据。
评测:shipping-boundary
计划 Trial:6
Observation Bundle:6
评分记录:6
buggy-release:failed
fixed-release:passed
计划里有 6 个 Trial,最后也收到 6 个 Bundle 和 6 条 Score。这三个数字对得上,说明每个 Trial 都留下了一份供 Scorer 复核的证据,中间没丢。金额为 100 的 buggy Trial 已经跑成 succeeded/canonical,对应的 Score 却仍是 failed,因为程序跑完只能说执行没出问题,不能说计算结果符合规则。报告会把这两层分开记。
篡改 Artifact 后再 inspect,会直接拒绝出结论。
这里程序报的是「运行证据无效」,不是「评分失败」,因为它在证据层就发现了问题,还根本没有进入评分。旧的 report.html 虽然还在原输出目录里,但它已经撑不起任何有效结论,因为报告是从证据推出来的,底层证据一改,原报告也就失效了。
如何核对¶
检查测试里的断言,看它们怎么核对 Gate、分母、报告和 Trace 文件的数量。
本篇不能证明什么¶
本实验没有运行真实模型、容器或生产计价服务,所以它只能证明本地 Fixture(测试夹具)和 Reference Harness 按声明的方式运行。