ARTICLE · INTELLIGENCE

战地情报 · 详情页

来自尧图项目组的一线实战观察与深度解析

Codex修Bug反复改坏别处?用一张任务卡锁住复现、范围、验收和回滚

Codex修Bug反复改坏别处?用一张任务卡锁住复现、范围、验收和回滚

让 Codex 修 Bug,别只说“修好”。这篇用满 99 元免运费的边界错误演示:先让测试失败,再限定可改文件,用同一测试与相邻回归验收,并记录回滚范围。附可复制的四栏任务卡

让 Codex 修一个小 Bug,最怕的不是它没改对那一行,而是它顺手重构公共函数、改配置、更新依赖;眼前的用例绿了,别处却坏了。

这种场景下,“帮我修好这个 Bug”不是足够清楚的任务。更稳妥的做法,是在动手前写一张任务卡:先明确怎样复现,再划定可修改范围,约定验收证据,并保留回滚路径。下面给出日常修 Bug 能直接复制的形式。

一张卡,先把“修好”说清楚

四项不需要写成长文,但最好都能被检查:

项目要写清的事没写清时容易发生什么
复现输入、预期结果、当前结果、运行命令没看到失败,就把“看起来合理”的改动当修复
范围哪些文件可改,哪些只可读,超范围怎么办顺手重构、改锁文件或覆盖已有改动
验收修复前后的同一测试、相邻场景、差异检查单个测试绿了,却不知道回归风险
回滚变更清单、未验证项、由谁决定撤销出问题后找不到本次究竟动了哪里

注意:“范围”限制的是写入,不是调查。可以让 Codex 只读检查调用链和测试;如果查出根因不在允许修改的文件里,就先说明证据并停下来,不要为了遵守文件名单硬改错误位置。

如果还在决定该用编辑器内工具还是 Codex 这类终端 Agent,可以先看 GPT108 的AI 编程工具选择指南:用同一缺陷检查改动范围与测试结果。选定工具之后,再用下面这张任务卡约束具体的一次修复。GPT108 是独立第三方 AI 会员服务平台,不是 OpenAI 官方网站或授权合作方;这条链接是补充阅读,不代表工具官方背书。

用一个边界 Bug 走一遍

下面是虚构的小例子,用于说明流程,不代表任何真实订单系统。规则为“满 99 元免运费”,金额统一用分表示。现有代码把刚好 9900 分排除在免运费之外:

# src/shipping.pydefshipping_fee(amount_cents:int)->int:return0ifamount_cents>9900else800

要覆盖的边界至少有三点:9899 分运费 800 分,9900 分运费 0 分,9901 分运费 0 分。先写或找到能在旧代码上失败的测试,再动生产代码:

# tests/test_shipping.pyimportpytestfromsrc.shippingimportshipping_fee@pytest.mark.parametrize(("amount_cents","expected_fee"),[(9899,800),(9900,0),(9901,0)],)deftest_free_shipping_boundary(amount_cents,expected_fee):assertshipping_fee(amount_cents)==expected_fee

示例命令是python -m pytest -q tests/test_shipping.py。在旧代码下,9900 分那一项应失败;改成>= 9900后再运行,同一组测试应通过。真实项目要用自己的目录、测试框架和业务规则,不能直接把示例阈值复制进生产代码。

这里最重要的证据不是“Codex 说已经修复”,而是同一条可执行用例修复前失败、修复后通过。如果环境跑不起来,就如实写“未验证”,先排查依赖或请人协助,不能把代码审阅等同于实测。

可直接复制给 Codex 的修 Bug 任务卡

把方括号内容替换成你项目的真实情况:

任务:修复[具体故障],不要顺带重构。 1. 复现 - 现象:[输入/操作]时,实际结果是[实际];预期是[预期]。 - 先只读检查相关代码、现有测试和工作区改动。 - 给出最小复现测试或复现命令;先运行并记录失败结果。 - 如果无法复现,说明缺少的环境或数据,不要宣称已修复。 2. 范围 - 允许修改:[目标代码文件]、[对应测试文件]。 - 其他文件可只读排查,不改配置、依赖、锁文件或公共接口。 - 保留工作区原有改动;不要覆盖、重置或清理它们。 - 若证据表明必须超出范围,先列出文件、原因和影响,停下等我确认。 3. 验收 - 修改尽量小,并说明根因与所改代码的对应关系。 - 改后运行同一复现测试,再运行[相邻模块回归测试命令]。 - 检查变更差异和 git diff --check;不要把测试通过当成全部验收。 - 汇报实际执行的命令、结果、未执行项和剩余风险。 4. 回滚 - 不主动提交、推送、部署,也不执行 git reset/checkout 等覆盖操作。 - 列出本次新增或修改的文件,区分原有改动与本次改动。 - 如验证失败,停止扩大修改,说明如何安全撤销“本次改动”,由我决定是否回退。

这一卡的价值是减少猜测:模型知道什么叫完成,也知道遇到新根因何时停。审查、针对性修复与验证应连成一个循环;关键是每一轮都依靠实际结果,而非让代理无限“再试一次”。

验收时,我会额外看这 5 件事

  1. 失败是否真实存在。修复前的测试是否确实命中报告的故障,而非一个与问题无关的新断言?如果旧代码也通过,测试没有证明这次修复。
  2. 边界是否够近。不只测出错值,也测它两侧及一个正常场景;像免运费阈值就要覆盖 9899、9900、9901 分。
  3. 差异是否聚焦。看git diff,确认没有无关格式化、依赖升级或 API 变化;已有未提交改动要单独标记,不能一股脑算成 Codex 的工作。
  4. 回归是否有证据。跑相关测试或构建命令。若耗时或权限使其没跑,要列成“未验证”,而不是写“应该没问题”。
  5. 撤销是否可定位。记录本次触及的文件与改动点。回滚通常应针对本次变更,由人审查后执行,避免误删同一工作区里别人的修改。

尤其要防一种“绿色假象”:为了让测试通过,直接改了测试预期、跳过失败用例或刷新快照,却没有解释业务规则为什么要变。验收需要把需求、旧失败、代码改动和新结果连成一条线。

什么时候不要让它继续改?

如果出现以下任一情况,先暂停:无法稳定复现;根因指向允许范围外的公共模块;变更需要数据库迁移或线上配置;测试环境和生产行为不一致;工作区已有改动与待修改位置重叠。这些不是“Codex 不行”,而是任务边界已经变化,需要人重新确认方案和风险。

一句话总结:修 Bug 不是让代理尽可能多改,而是让每一次改动都有可复现的起点、有限的范围、可核查的结果和可定位的退路。下一次提任务,先把这四栏填上,通常比多说一句“仔细一点”更有用。

RELATED READING

延伸阅读

更多一线实战笔记与深度复盘,助您持续精进