defineEval 的结构
tags 与 environment
tags 可供 --tag 和 experiment 的 evals 谓词读取。environment 只声明环境 profile;具体 image / template 由 experiment 使用的 Sandbox 配置映射。
单轮评估
t.send() 驱动一次交互,t.succeeded() 和 t.calledTool() 是作用域断言,t.check() 是立即记录的值断言。
Turn 对象
多轮评估
t.newSession()。
数据驱动测试(dataset fan-out)
一个文件可以导出评估用例数组:sql/0000、sql/0001 等。详见 数据驱动测试。
Sandbox workspace
Coding-agent 评估用例仍然是普通.eval.ts 文件,只是 test 里会准备 Sandbox workspace、发送任务并检查文件结果:
输出信息
setup 用于这条评估用例的 Fixture。第二个参数绑定到评估用例 setup 阶段;test(t) 里的反馈绑定到评估用例 run 阶段:
progress 只更新运行中的短期状态,不进入结果。diagnostic 会写进当前 Attempt 的 result.json,但不会代替断言或自动改变判定:业务结论仍用 t.check / t.require / gate;基础设施无法继续时抛出异常。
评估的生命周期
setup(sandbox, ctx) 准备 Fixture;配一个 teardown(sandbox, ctx) 收尾,两者合起来是这条评估用例的 Fixture,每个 Attempt 各执行一次。执行顺序:setup 在 Sandbox 生命周期 Hook 和 git 基线锚点之后、test(t) 之前跑;teardown 是 Attempt 收尾链的第一段(先评估用例 teardown,再 agent teardown,最后 Sandbox teardown),这时 Sandbox 还活着,收尾代码可以照常读 Sandbox。
大多数 Fixture 不需要 teardown——写进 Sandbox 的起始文件、装的依赖随 Sandbox 销毁自动没了。需要 teardown 的是Sandbox 外的 Fixture:在共享外部服务里为这个 Attempt 建的临时资源(临时 repo、bucket、队列 topic),不收就泄漏。
同一条评估用例的多个 Attempt(runs 大于 1、或同批多个实验跑同一条评估用例)并发执行且共享同一个模块,setup 的句柄不能放进普通模块变量——会被后一个并发 Attempt 覆写。以 sandbox 实例作键存取(WeakMap):sandbox 与 Attempt 一一对应,天然是 per-attempt 键:
teardown 当且仅当这条 Attempt 走到过 setup 的时点才执行——setup 抛错不豁免,收尾代码要对可能没建成的资源做防御。teardown 抛错或超过 30 秒清理上限只记 teardown-failed 诊断,不改变这个 Attempt 已经产出的判定;要让某个收尾动作影响结论,在 setup / test 里抛错,不要指望 teardown 能改判。
命名约定
文件名
只有
.eval.ts 会被 runner 发现。ID 命名空间
evals/billing/refund.eval.ts 的 ID 是 billing/refund。数据集
适合大量结构相同、输入不同的 case。
Sandbox workspace
适合 coding agent,需要真实文件系统、命令和 diff。