智能编码进化论

704次失败诊断书:版本治不了的病

约 9 分钟驭光者首发于微信公众号「羲和Lab」

特别企划 · 逐条复核两个月的失败报错,四类流程病确诊实录 《智能编码进化论》系列 · 数据报告体 · 2026-08

上一篇我们数完家底,这一篇翻报错。《从2277个子代理说起》的交叉矩阵里有四个刺眼的数字:TAPD失败248次、timeout 179次、file-not-read 147次、git冲突130次,表面合计704次。当时的结论只有一句话:版本治不了。但"版本治不了"只是把病名报了出来,没有确诊。这一篇,我们把两个月的失败记录逐条翻开,读报错原文,重新归类,给每类病出一份诊断书。

正式看诊前,先交代口径——四个数字,变了。

上篇是粗筛:按错误特征词计数。本篇是细查:只取 is_error:true 的真实工具报错,git 再按会话去重。复诊结果:TAPD 修正为246次,timeout 上修至344次,file-not-read 上修至290次,git 冲突去重后只剩25个事件。

差异来自宽松匹配的污染。上篇的匹配规则是"会话记录中出现特征词就计数":你在会话里讨论"怎么处理timeout",或代码里写了 catch(TimeoutException),都会被算作一次 timeout 失败。上篇数字是"讨论"和"发生"的混合体,本篇只数真正发生的报错。

最典型的是 git 的130变25:转录文本中的词频,不等于事件发生频次。"git conflict"被反复讨论、同一冲突多文件重复输出,都会放大词频。本篇只统计命令真实返回冲突的事件并按会话去重,得25。

口径讲完,发诊断书。先说一句:四份诊断书里,最重的一条数据不在任何一个病的根因里,而在失败的去向里——88.6%的失败被静默吞掉。先看病,最后回到这个数字。看完你只会记住一件事:四份诊断书,没有一份和直觉对得上。

病一:以为是接口不稳,其实是权限缺失

直觉诊断:TAPD API 反复报错,八成是接口不稳定。

确诊数据:细查后的246次失败里,403 权限不足167次,占67.9%;422 参数错误52次,占21.1%;404、认证异常、业务错误合计不足11%。

接口不稳?接口清楚得很。它每一次都在明确告诉你同一句话:你没权限。

403 的集中区更能说明问题:tasks 创建38次、story 父子关系设置24次、批量更新18次——清一色写操作。读操作一路畅通,一到写就撞墙。病不在接口,在账号的权限配置。

典型报错原文(ID已脱敏):

TAPD API error: 403 Forbidden - user *** doesn't
have permission tasks::_save_new of workspace ***

翻到失败的去向时,全部数据里最惊悚的一条出现了:失败发生后,88.6%被 AI 自己绕行或忽略,主动重试只有0.9%。

88.6%,意味着这些写失败几乎没有一起被正视过。把它摊开成一条完整的链条:

AI 调 TAPD 写数据 → 返回403 → AI 不上报,自己换一条路,或者干脆跳过这步 → 会话继续往下走 → 没有通知,没有日志,没有人知道刚才是失败 → 那条本该写进系统的数据可能根本没写进去,而整个流程表面上一切正常。

这就是静默吞掉:失败没有消失,只是没人看见。状态机走到一半断了半格,后面的每一步都建立在"那步成功了"的假设上。比失败更坏的,是失败了还不自知——失败至少留下现场让人修,静默吞掉连现场都不给,账永远没人认。

回头再看"接口不稳"这个直觉诊断,会发现它是怎么形成的:AI 绕行了,屏幕上没有红字,人看到的是会话照常推进——于是偶发的卡顿和重复操作被归因成"网络不好""接口抽风"。真凶权限缺失,一直坐在被告席外面。

药方:写权限在开工前验证,别撞墙之后再猜;失败分类应对——403 是配置问题,找管理员开通,422 是参数问题,回去核对字段,两者都不该盲目重试,重试一百次也不会让权限凭空出现。

病二:以为在等工具,其实在等模型

直觉诊断:179 次 timeout,不外乎网络慢、工具慢——尤其那几个出了名的慢角色:TAPD MCP、curl、git、docker。

确诊数据(精确口径下共344次):模型暂不可用131次,占38.1%;MCP 调用95次,占27.6%;浏览器操作93次,占27.0%;Bash 命令仅12次,占3.5%。

两个反转,一个比一个反常识。

反转一:最大单一超时来源不是任何工具,是模型端——"temporarily unavailable"。你以为 AI 在等你,其实是你在等 AI。模型端波动不挑场景,说来就来,这才是超时的头号病源。

反转二,表述必须精确:在精确口径下,被点名的那几个刻板慢工具——TAPD MCP、curl、git、docker——超时次数为0。注意,这说的不是"全部超时都是假的":344 次超时真实存在,只是它们几乎都不出自这几个工具。上篇把词频算成了病历,把讨论里的报错示例、代码里引用的工具名,统统记到了它们的头上。

反过来想想 Bash 的3.5%:本地命令最快、最不可能超时,恰好印证这份分布的可信度——越靠近模型的环节越容易断,越靠近本地的环节越稳。慢的黑锅,工具背了太久。这也意味着,以后遇到超时,第一反应不该是"这个工具真慢",而是"模型是不是暂时不可用"——排查方向错了,优化全白做。

分布上也扎堆:344 次超时集中在两个工程——一个后端系统工程,一个测试平台工程。共同点是高频浏览器操作加长链路 MCP 调用,哪里密集,超时就在哪里堆积。

药方:模型端超时没有特效药,靠快速重试顶过去,紧急场景降级备用模型;MCP 超时配置自动后台化(如 CLAUDE_CODE_MCP_AUTO_BACKGROUND_MS),慢调用转后台异步等待,不阻塞主线;浏览器操作学会精准定位——find 一段文本代替整页 snapshot,省时间的同时也更稳,快和稳本来就是同一个动作的两面。

病三:以为是路径错,其实是流程跳跃

直觉诊断:file-not-read 147次,多半是文件路径写错了。

确诊数据(精确口径下共290次):Edit 前未 Read 150次,占51.7%;Write 覆盖未读文件66次,占22.8%;worktree 子代理场景34次,占11.7%。

超过一半和路径毫无关系:路径全对,文件就在那儿,AI 只是没有读过它就要动手改。这不是环境病,是行为病——该走两步的流程,跳了一步。

分布把病根指得很准:290次里,161次(55%)集中在同一个主力前端工程。这正是鲁班的 worktree 子代理使用密度最高的地方。机制上的三个缺口拼起来,就是病灶全貌:

  • 并行子代理各自有独立的工作目录,Read 过什么互不共享,A 觉得"我刚读过",B 手上是空白;
  • 上下文压缩后,文件读取状态随旧上下文一起丢掉,AI 自以为还记得,实际记得的是摘要;
  • memory 自动写回机制贡献约15%,写回动作偶尔直接跳到 Edit,把 Read 这一步省略了。

还有一层让人不安的事实,这一条要往深里说:file-not-read 是唯一一类我们有意识地用"会话设计"去覆盖、却始终没能补上的病种。细看数据,290次中有150次,只要在同一会话内先执行一次 Read 就能完全避免——条件简单到近乎苛刻,它们还是发生了。规则层没有条款覆盖它,经验层的自觉也没有接住它,两层防护同时落空。这说明,有些病不是没人看见,是看见了也治不了——它吃设计,不吃自觉。

药方:它不吃规则,吃设计。长会话压缩之后,强制重读关键文件再动手;派发子代理时,把"先 Read 再修改"显式写进 prompt,不依赖它自己想起;并行写入的场景回到 worktree 隔离,让读不到彼此这件事变得无所谓。设计在前,行为才不会漏。

病四:以为冲突成灾,其实去重后只剩25个

直觉诊断:130 次 git 冲突,多工程并行的日子久了,合并冲突迟早成灾。

确诊数据:按会话去重之后,真实的冲突事件只有25个——merge 内容冲突56%、branch 已存在36%、rebase 相关8%、index.lock 为0。

上篇的130,把警报声当成了狼叫;真狼只来了25次。缩小五倍之后,每一件都比想象中难看。

两个小反转藏在里面:

其一,36% 是"branch already exists"。创建分支前先查一眼就能避免的低级失误,占了三分之一强。这不是 git 的病,是前置检查的缺失——手比眼快,先建了再说。

其二,上篇宽松口径的130里还混着 guest:SSH 连接失败(nc 协商场景)这类纯网络问题,被词频一并记到了"git 冲突"头上——细查时已把它们剔除出去,归入网络病。通道病和内容病症状相似,病因风马牛不相及,混在一起统计,两个都治不好。

25 个事件里还藏着一条正面证据:index.lock 的预防提示很早就写进了我们的规则——遇到锁文件先排查持有进程,不直接删除。实测两个月,这个错误实际发生0次。病没发作,不是因为运气,是因为规则挡在了它惯常出现的路口。这是四份诊断书里唯一一张"痊愈证明",也是下一节要追问的对象:同样写进规则的对策,凭什么它活了下来?

分布上,25个事件的六成依旧来自那个主力前端工程——多日期分支并行合 master 的常态,worktree 用得多的地方,残余冲突最少;轮番切分无人管的,冲突最多。

药方:建分支前先 git branch --list,一行命令的事,别省;把通道病(SSH 连不通)和内容病(merge 真冲突)拆开诊断,各自对症;真正的内容冲突,回到 worktree 隔离——上篇验证过的部分缓解,本篇数据再次给它作证。

药方总纲:规则为什么会失效

四份诊断书摆在一起,逼出一个更大的问题:两个月来立下的各种规矩,哪些真的在起作用?

对策实测状态
sandbox 降级策略生效:777次触发,80%一次重试成功
index.lock 预防生效:实际发生0次
TAPD workflow 缓存形同虚设:主力项目从未创建;6个有缓存的工程里2个已过期76天、92天
MCP 超时对策(login / 后台化)形同虚设:310个超时转录中仅10%提及对应对策
file-not-read 对策无规则覆盖:会话设计补位亦未奏效(见病三)

上半张表生机勃勃,下半张表触目惊心。差别在哪里?

sandbox 和 index.lock 的规则有个共同点:它们绑定着具体且高频的触发时刻——命令被拦截的那一刻、文件被锁住的那一刻,规则原文就贴在 CLAUDE.md 里,每次触发都被迫复习一遍。复习多了,就成了肌肉记忆。

失效的那几条恰好相反:TAPD 缓存要求你在干活之前停下来,先去创建一份映射;MCP login 要求你保持警觉,提前完成认证。它们都要求"跳出当前动作,先做一件前置的事"。而人性(包括 AI 的行为惯性)是顺着当前动作往前的——于是最该用的主力工程里,一次都没被执行过。

所以这份数据给出的核心洞察是:规则是否生效,不取决于写得对不对,取决于它有没有被内化成"第一反应"。 写进文档的只是知识,知识不会自动变成动作;变成动作的,是被高频触发点反复喂养出来的本能。

据此把药方收拢成三层,分类施治:

  • 配置层:权限申请、白名单、预检脚本——凡是能一次性配好的,绝不用每天记,一次配对,长期受益;
  • 规则层:不能只写原则,必须携带触发钩子——写清楚"当XX发生时,立即做XX",而不是"建议注意XX";
  • 行为层:规则够不着的地方(病三那种),只能靠会话设计和工具强制提前兜住。

预告:把药方做进产品

先声明:以下是规划中的方向,细节以实际发布为准。

四类病里最重的是 TAPD 病,246次。我们已经证明,规则层对它基本失灵——那就换个思路,不靠规则治,靠产品治:把这批药方规划做进自研开源项目 @xihe-lab/tapd-mcp-server,四个方向:

  • 权限预检:开工前主动探测写权限,把403从"事后撞墙"变成"事前公示";
  • 结构化错误:报错附带行动建议——该找谁、改哪个字段,专治88.6%的静默绕行;
  • workflow 缓存内置:状态映射由 server 自己维护,不再指望每个项目自觉创建。呼应上篇那句话:凡是纪律守不住的,就该变成产品的默认;
  • fields 默认收紧 + 幂等重试:从源头减少参数类报错,让偶发抖动可以安全重放。

一句话预告全文立场:规则生效靠"第一反应",产品生效靠"无需反应"。

结尾:数据是听诊器,不是药

两篇连起来,是一个完整的就诊过程:上一篇证明了版本更新是药,能治一部分病;这一篇证明了数据记录是听诊器,能把病听准;落地治病,靠的还是这三层药方。听诊器不开药,但没有听诊器,你连该开哪种药都不知道。

这大概是两个月的报错教给我们最重要的一课:归因错了,药方就会开偏。 接口不稳的直觉,差点让我们去优化一个根本没有病的接口;工具太慢的黑锅,背了整整两个月——如果不是逐条翻报错,这些错误的诊断还会继续指导错误的投入。

最后,记住这组对比。704次失败听起来吓人,但其中大量是误伤、词频和水分;真正让人后背发凉的,是那个数字——88.6%的失败被静默吞掉。失败本身是财富,静默吞掉让财富蒸发:你付了学费,却没人上课。

下一篇,我们就盯着这四个字展开:静默失败。让失败可见,让账有人认——在写进报错之前,任何一次"看起来还行",都值得怀疑。

免责声明

本文内容仅供学习交流,所述方法需结合实际场景灵活运用。AI 工具输出结果仅供参考,关键业务决策请结合人工判断。

本文由 AI 辅助创作,经人工审核编辑后发布。文中所有工程均使用泛称,涉及标识信息已做脱敏处理;性能与统计数据均来自作者自用环境的实测记录,样本有限,不代表普遍情况。


《智能编码进化论》特别企划 · 数据报告体 · 2026-08

本文首发于微信公众号「羲和Lab」,公众号内可留言交流

阅读公众号原文