当 Spec 遇见遗留系统:构建一个带人工审核节点的长任务 Agent

文章来源声明: 原文作者:一只爱撸猫的程序猿; 来源站点:掘金; 原文链接:https://juejin.cn/post/7693165008605511680; 本文基于上述来源整理/加工,觅优补充点评,仅供技术学习交流。版权归原作者所有。
觅优短评

对做遗留系统迁移和高不确定业务改造的团队很有参考价值:它把“AI 改代码”的信任问题转化为流程设计与人工分工问题,其中暂停点选择与重规划分级两处最可直接借鉴。

当 Spec 遇见遗留系统:构建一个带人工审核节点的长任务 Agent -----------------------------------

记录一次用 LangGraph 把"写 Spec、生成、验证、人工把关"这套流程落成真实系统的过程,以及中间踩过的几个坑。

手头有个活儿:翻新一个老功能,表结构改了,业务逻辑却只存在于没人维护的旧代码里。我对这块业务不熟,Git blame 能查到的最后一个改动者早就转岗了。

这种场景下让 AI 直接"改代码"是最危险的用法——它会很自信地把不确定的地方悄悄填上合理但未必正确的假设,而这些假设往往要等到生产环境才会暴露。于是我没有用对话式的方式让 Agent 改代码,而是把整个过程拆成了一个显式的 Spec 驱动循环,在高风险的地方插了人工审核节点。

Spec 不是写完才能用的东西,它是和代码一起演化的活文档——每一轮生成,都是在验证这份 Spec 里的假设站不站得住。

为什么不是直接对话生成

对话式迭代在小改动上很好用:描述需求、看结果、调整、再来一轮。问题出现在改动跨越多个文件、涉及我自己都说不清楚的业务规则时——这时候真正难的部分是"这段逻辑到底在做什么、为什么这么做",而不是"怎么写代码"。把这个设计决策交给一次性的对话,相当于让 AI 替我做了一堆本该由我(或者原业务方)拍板的判断,而我浑然不知它做了哪些假设。

所以我把流程拆成了五个阶段,对应一个可以暂停、可以恢复、可以重新来过的状态机,而不是一条从 Prompt 直接到代码的直线。

①Spec 构建

从旧代码反推业务逻辑,生成结构化草稿

②代码生成

按 Spec + 新表结构生成实现

③自动验证

跑测试 / LLM 评分,判断是否达标

④风险分级人审

仅高风险改动暂停,等待人工批准

⑤部署上线

灰度验证,异常自动回滚

↻ 验证失败或审批被拒,带着原因回到①局部重新生成,不推倒重来

几个值得记下来的设计决策

重试和"重新规划"必须分开处理

验证失败分两种性质完全不同的情况:一种是实现细节写错了,换个写法重试就能过;另一种是对任务的理解方向本身就错了,这时候继续在错误方向上重试毫无意义,必须带着失败原因回到 Spec 这一步重新拆解。一开始我把两者混在一起处理,结果 Agent 会在同一个方向上反复试错,浪费了大量 token 却一直不得要领。

# 验证失败 → 记录原因,而不是直接判定任务失败
task.failure_reason = result.reason
task.retry_count += 1
task.status = (
    TaskStatus.PENDING if task.retry_count <= MAX_RETRIES
    else TaskStatus.FAILED  # 重试耗尽,交给人判断是否要重新规划
)

暂停点要选在"进程可以退出"的地方

高风险审批不能用一个 input() 卡住进程等人确认——现实中人不会随时在线。用 LangGraph 的 checkpointer 把状态持久化到数据库后,这个进程可以安全退出,明天审批通过了,外部的轮询器会把流程从暂停点原样唤醒,而不是从头跑一遍。这个区别在"能跑 demo"和"能真正用于长任务"之间,几乎是分水岭。

踩过的坑 一开始没给"重新规划"设上限,一个任务被连续拒绝 + 重新生成了十几轮都没过。后来意识到,连续失败次数过多本身就是一个信号——不是 Agent 做得不够好,是需求本身没讲清楚,这种情况应该直接升级成"需要人重新讨论这个需求",而不是让循环继续空转。

人在这个系统里到底该做什么

把人的角色简单理解成"审一眼 Spec 对不对"是不够的。实际拆开看,人要做四件事,而且缺一不可:

环节人要做什么为什么 AI 替代不了
补充信息把 AI 从旧代码里猜不出来的业务背景补上答案在组织的隐性知识里,不在代码里
审 Spec确认 AI 有没有理解错业务逻辑理解偏差只有懂业务的人能看出来
审输出真的跑一下生成的代码,不只是读起来顺眼符合 Spec ≠ 运行起来是对的
拍板判断剩余的不确定性能不能接受上线风险容忍度是业务判断,不是正确性判断

这里最容易踩的一个坑是把"人工审核"做成橡皮图章——看一眼 AI 给的验证结论就点通过。这比完全不审查更危险,因为它制造了一种已经把过关的假象,而实际上什么都没验证。

目前的结果

这套系统已经在真实的迁移任务上跑了起来,接下来打算补全的数据:

  • Task 平均重试几次才通过自动验证 — [待补充]
  • 高风险 Task 占全部 Task 的比例,验证风险分级是否真的有区分度 — [待补充]
  • 从提交审批到人工响应的平均等待时长 — [待补充]
  • 端到端跑完一次完整迁移的 token 成本 — [待补充]

这几个数字比"这套系统设计得多精巧"更有说服力——下一篇会补上真实数据和跑出来之后暴露的新问题。