Where Does Exactly-Once Live? Model, Harness, and Tool-Contract Effects on Duplicate Side Effects in LLM Agents
Jiapeng Li
cs.LG, cs.AI, cs.SE
2026-09-24
微软 Limbo 沙盒 25930 局实测:读回查得清时前沿模型重复率仅 0.5%,查不清(迟到提交、重复投递)时达 56%~74%;给全部写操作加幂等键把重复率从 28% 压到 4%。
Agent 用工具调用对外部系统做写操作:扣款、发帖、发邮件、触发部署。调用要过网络,网络会丢消息。一次写超时或返回 500,动作可能已经生效也可能没有:盲目重试会重复扣款,直接放弃又漏掉必须做的工作。分布式系统的成熟解法放在接口层,即幂等键、条件写、可查询的操作状态;LLM agent 继承了模糊性,默认没继承解法。
该由谁保证「恰好执行一次」(exactly-once):模型、harness,还是工具契约?三项并行工作各测了一角,这个归因问题此前没人系统回答。
Limbo 是微软出的确定性沙盒,分三层:
理论先钉两条边界:不知道在途时间上界时,任何只靠读回验证的策略都不可能 exactly-once,「请求没送到」和「还在路上」观察上不可区分;每次重发复用同一个幂等键,则五种结果下都 exactly-once。
沙盒经 MCP 暴露,同一环境不改一行就跑在最小脚手架和三个生产 harness(GitHub Copilot CLI、Hermes、Codex CLI)下,合计 25930 局、9 个模型、2 种契约、15 种恢复条件。反事实契约 keys-everywhere 只改一件事:把幂等键扩展到所有非幂等写,用来隔离契约的因果效应。
| 设置 | 重复率 |
| 丢确认:前沿模型 / 弱模型 | 0.5% / 18% |
| 迟到提交,前沿模型 | 56% |
| 重复投递,各模型 | 74%75% |
| keys-everywhere,无 guard | 迟到提交 61%→9%,重复投递 74%→7% |
| keys-everywhere + guard | 迟到提交 68%→7%,重复投递 74%→0%,EOS 99% |
| 透明重试(sdk-retry) | EOS 从 72% 跌到 50% |
整体重复率 28%→4% 就出自 keys-everywhere 这一个改动。方差分解给出归因:读回查得清的故障,模型解释 53% 的可解释方差;查不清的,契约解释 81%,harness 只占 03%。三个生产 harness 和最小脚手架跑同一模型,重复率几乎一样(native 下 26%30%),差的主要是成本:Codex CLI 每局约 15.3 万 token,最小脚手架 1.2 万。
等待换不来 exactly-once。重尾延迟下等满一小时(每局 49.9 分钟)只到 84% 的 EOS;keys 加 guard 用 1.5 分钟到 94%。键失效全部可解释:432 次复用原键的重发零重复,重复来自首次没带键(68%)或重试时换了新键。
三个反直觉副产物。最终一致的读路径比没有读路径更糟(13.4% 对 0.8%,强一致对照),agent 信任了看不到迟到效果的读,无读回时反而 87% 升级人工。guard 会反噬:gpt-6-sol 在迟到提交下被 guard「先验证再放行」的承诺劝退了升级策略,重复率从 50% 涨到 71%。最不舒服的一条:产生了重复的 episode 里,90% 的 agent 汇报任务完成,80% 连「结果不确定」都没标。另外,去掉任务末尾「每个动作恰好执行一次」那句话,可查清故障的重复率从 12% 升到 22%,弱模型从 29% 升到 51%。
对做工具和协议的人,这是可执行清单:非幂等写都该接受幂等键(agent 有键就用,98% 附带率)、每个写声明读回操作、文档写清可见性延迟和在途上界。MCP 目前只把 idempotent 当建议性 hint,论文主张升为规范。对做 harness 的人:透明重试对非幂等写是有害默认值;一个不到两百行、只读契约的 guard 能跨 harness 无改动迁移,但别对外承诺验证,那会让强模型放弃自己更保守的升级。对选型的人:换更强的模型,只解决读回查得清的那一半问题。
作者自述:服务是模拟的;模型走同一网关,采样与推理设置锁在 provider 默认;harness 被限制为只用沙盒工具,抹掉了部分 harness 差异;重尾延迟分布是建模选择;任务偏短;gpt-4.1 只覆盖 87% 的设计;分层方差分解和多个实验是预注册后的探索性分析。论文还披露部分代码与稿件用 GitHub Copilot 起草。
读下来另有几处要留神:判分用模拟时间,等待策略的真实成本要打折换算;模拟 on-call 永远诚实作答;「弱模型」只有两个样本,18% 那个数对弱模型群体的代表性有限;native 契约里 2/11 的非幂等写路径接受键,作者说这个比例已经恭维了真实 API,反过来说明 28%→4% 在真实接口上未必一步到位。