模块二:AI 协作方法论 | 第05讲:AI 协作调试法——从报错到修复的可复制方法论
项目:VibeNote 智能笔记 · Next.js / React / TypeScript / Tailwind
本讲目标:用工序替代运气;用结构化信息替代复制整页日志。
一、开场:无效调试循环,本质是信息不对称
reference/practice/vibe-coding-methodology.md 把「按了葫芦起了瓢」写得很具体:模型在错误假设上反复打补丁,代码越改越乱;你如果只是验证者,模型会在无效循环里消耗算力与你的耐心。课程原稿 课程内容/2.5 从报错到修复:一套可复制的AI协作调试法.md 只有骨架;本讲补齐:三连跪规则、结构化报错、读栈方法、隔离工具箱、根因声明、验证分层、何时重置会话、VibeNote 场景清单。
我想先把话说白:调试不是模型「再试一次」的抽奖游戏。它是信息收集与假设检验。你把信息组织得越像工单,模型越像合格协作方;你把信息组织得像情绪发泄,模型就只能陪你掷骰子。
flowchart TD
R[Reproduce 复现] --> I[Isolate 隔离]
I --> D[Diagnose 诊断根因]
D --> F[Fix 修复]
F --> V[Verify 验证]
V -->|失败| R
flowchart LR
A[尝试1] --> B[尝试2]
B --> C[尝试3]
C --> S[停止盲试]
S --> H[人类定位根因]
H --> F2[基于根因修复]
二、三次尝试规则(3-strikes):给协作装刹车
同一问题连续三次修复仍失败,停止让模型继续「盲试」。 参考文章把它当作危险信号:说明模型可能困在错误框架里。此时标准动作不是「换模型」,而是:
- 你亲自读栈与相关代码,写出「目前最可信的失败链路」
- 用最小复现把范围砍到最小面
- 写「根因一句话」或「未定位但已排除清单」
- 再开新会话,携带以上结构化信息让模型重生补丁
这条规则的价值是保护你的仓库:补丁堆叠是最贵的技术债之一。
三、结构化报错:最低八字段(缺一补一)
- 现象:用户可见 / API 返回 / 监控指标
- 复现步骤:从冷启动到失败的可重复路径
- 期望 vs 实际:对照写,别混写
- 环境:分支、commit、Node、OS、是否 Docker
- 错误栈:保留顶部与 Caused by,删中间重复帧
- 相关代码:只贴失败路径,不要整文件
- 已排除假设:防止模型回到死胡同
- 根因一句话:未知就写「尚未定位」
你可以把这段直接复制成 issue 模板。字段齐全的意义是:把调试从聊天变成数据库查询——缺列的查询,优化器再强也没用。
四、读懂报错:先回答三个问题再贴给 AI
- 哪一层错了:编译期、运行时、网络、权限、数据一致性?
- 根因 vs 连锁:谁是第一块倒下的骨牌?
- 失败语义:401/403/404/500 在业务里分别意味着什么?
把答案写进工单,比多贴两百行日志更有用。很多「AI 修不好」其实是人类没把语义分类做对,模型只能猜。
五、五步法详解(Reproduce / Isolate / Diagnose / Fix / Verify)
Reproduce
不能稳定复现就不要大规模改代码。先补日志、加最小用例、或在本地脚本复现。
Isolate
用 mock、特性开关、二分注释、git bisect 把问题缩小到「一个函数、一个路由、一个组件」。
Diagnose
人类必须下场。 参考方法论强调:你先定位根因,再明确告诉模型「之前的假设错在哪」。
Fix
让模型基于根因与机制出补丁,而不是基于「还是不行」出补丁。
Verify
至少 lint + build;涉及资金/权限/删除要走更强验证;AI 功能要测降级。
六、读栈:从上到下找「第一帧你的代码」
别从栈底开始梦游。优先定位仓库内第一帧,再看是否误用 API,最后才深入 node_modules。对 Next.js:构建日志与浏览器控制台与服务端终端是三个不同战场,先分清战场再贴栈。
七、何时重置上下文(新开会话)
满足任一条就建议新开:
- 模型引用不存在文件或旧 API
- 同题三轮以上
- 对话混入多个需求
- 你重复粘贴同一段约束超过两次
新会话只带:摘要 + 根因/排除项 + 最小相关文件。这是第03讲「会话脏了要换盆」的调试版。
八、常见 AI 调试坑(自查表)
- 只贴最后一行错误
- 贴整页日志但没有分支与版本
- 一次让模型修三件事
- 不说「禁止改动范围」
- 把猜测写成了事实
九、可运行示例:解析 tsc 单行错误(结构化习惯)
// scripts/parse-tsc-line.mjs
// node scripts/parse-tsc-line.mjs "src/note.ts(12,5): error TS2322: ..."
const line = process.argv[2] || "";
const m = line.match(/^(?<file>[^:]+)\((?<line>\d+),(?<col>\d+)\):\s*error\s*(?<code>TS\d+):\s*(?<msg>.*)$/);
console.log(m ? m.groups : { raw: line, hint: "未识别的 tsc 行" });
十、可运行示例:从栈提取「文件:行」候选
// scripts/stacktrace-files.mjs
const text = process.argv[2] || "";
const re = /\(?([A-Za-z]:[^)\n]+|\/[^)\n]+):(\d+):(\d+)\)?/g;
const seen = new Set();
let m;
while ((m = re.exec(text)) !== null) {
const key = `${m[1]}:${m[2]}`;
if (!seen.has(key) && !m[1].includes("node_modules")) {
seen.add(key);
console.log(key);
}
}
十一、与 Workflow 的映射(第02讲)
Bugfix 工单字段应对应五步法:复现→隔离范围→根因→补丁→验证命令。这样 PR 描述本身就是调试剧本,而不是事后补写。
十二、VibeNote 案例:AI Route 500
坏工单:「AI 挂了修一下。」
好工单:保存笔记触发 /api/ai/expand 返回 500;复现路径为选中文本点扩写;期望 200 与流式 chunk;实际 JSON 报错;分支 main Node 20;栈顶指向 adapter;已排除代理;根因未知→下一步检查环境变量加载与模型名配置。
十三、VibeNote 流式与 React 专项清单
useEffect清理是否取消 fetch/stream?- 组件卸载后是否仍
setState? - 是否把仅服务端可用的 key 间接串进 client props?
- 是否在 Strict Mode 下双调用导致状态错乱?
十四、调试与安全:脱敏是硬要求
调试时最容易手滑把用户笔记正文、token、内网地址贴进对话。默认脱敏:ID 哈希化、正文截断、密钥占位符。安全不是「合规同学的洁癖」,是你职业底线。
十五、协作时序图:人类何时介入
sequenceDiagram
participant You as 你
participant AI as AI
You->>AI: 结构化工单
AI-->>You: 补丁1
AI-->>You: 补丁2
AI-->>You: 补丁3
You->>You: 停:自定位根因
You->>AI: 根因+允许范围+验证命令
AI-->>You: 补丁4
You->>You: lint/build/手工→合并
十六、根因声明怎么写才「可执行」
推荐句式:根因 = 模块 + 条件 + 错误行为 + 机制。若机制未知,写「未定位 + 下一步实验」而不是编造故事。调试里最贵的是假根因,因为它会让后续所有补丁建立在沙上。
十七、让 AI 写补丁的 Prompt 骨架(调试专用)
- 这是我的根因判断(或未知声明)
- 这是允许修改的文件列表
- 这是禁止事项(依赖/schema/目录)
- 这是验证命令与期望输出
- 如果需要假设,请列出假设并标注未验证
这就是把第01讲 RCTFC 用在调试场景。
十八、验证分层:别只用「我点过了」
- 静态检查(lint/tsc)
- 构建(build)
- 业务路径(手工 + 边界)
- 回归(至少一条自动化或脚本化检查)
十九、团队机制:看板列「Stuck > 3」
进入该列必须附:时间线、证据链、根因或排除项。没有根因分析不允许继续「再试」。这会把调试从个人玄学变成组织流程。
二十、练习建议:每天 15 分钟读栈训练
挑一条真实栈,手写:第一帧你的代码、可能的根因假设、下一步验证动作。两周后你会明显变快——不是因为你更聪明,是因为路径依赖形成了。
二十一、FAQ
Q:三连跪会不会太死板?
A:它防的是仓库被补丁淹没;你可以把阈值调成 2 或 4,但不能没有阈值。
Q:我不会定位怎么办?
A:从最小复现与二分法开始;定位是技能,不是天赋。
Q:要不要让 AI 先列假设?
A:要,但必须标注未验证,避免当事实。
二十二、本讲小结
- 三连跪是刹车,不是认输。
- 结构化报错决定模型上限。
- 五步法让调试可复盘、可教学。
- 新会话 + 蒸馏信息对抗上下文污染。
- 人负责根因,模型负责在正确假设下加速。
二十三、思考题
- 你上一次三连跪,如果真写根因一句话,会怎么写?
- 你愿意把「三连跪停手」写进
AGENTS.md吗? - 你如何训练同事「先读懂栈再贴栈」?
二十四、下讲预告
下一讲深潜「方案先行、实现为后」:如何把设计文档当作模型锚点,如何分模块推进与逐步验证,如何用文档驱动开发把 VibeNote 做到可维护。
二十五、延伸阅读:把「无效循环」画成检查清单
当你发现模型开始同时改多个无关文件、开始引入可疑依赖、开始解释「这可能是缓存问题」却没有任何验证步骤,你就该问自己:我是不是没给够结构化信息?我是不是该亲自下场? 这张心智检查清单比任何「调试提示词」都稳。
二十六、调试中的「时间盒」
给自己设 45 分钟:前 15 分钟只复现与读栈,中间 15 分钟隔离,最后 15 分钟才允许大规模改代码。时间盒能防止「越急越改越乱」。调试最怕的是焦虑驱动的编辑,AI 只是把这种编辑加速了而已。
二十七、与测试的关系:调试结束要有「防回归锚点」
哪怕只加一个最小测试或一个脚本化检查,也比「我记得修好了」强。参考方法论强调验证前移;调试是验证缺失的代价,别付两次。
二十八、Next.js 常见坑位速查(补充)
- Server Component 里误用浏览器 API
use client边界放错导致打包异常- Route Handler 里未处理
OPTIONS或 CORS fetch缓存策略导致「改了但像没改」
这些坑当你结构化描述时,会更容易被模型一次命中。
二十九、调试记录模板(建议放 docs/debug/)
- 日期 / 分支 / 触发人
- 现象与影响面
- 复现步骤
- 时间线(发现→定位→修复→验证)
- 根因与修复摘要
- 防回归措施(测试/监控/告警)
这份记录会成为团队真正的「被动上下文」:下次类似问题,先搜索 docs/debug 再开新对话。
三十、结语
调试是最能检验「AI 协作成熟度」的场景之一。你会立刻看到:没有流程的人,会把模型当成算命先生;有流程的人,会把模型当成在正确坐标系里的加速器。把坐标系建好,速度才有意义。
参考阅读:reference/practice/vibe-coding-methodology.md(无效调试循环、亲自定位根因);课程内容/2.5 从报错到修复:一套可复制的AI协作调试法.md。
三十一、把「根因—修复—验证」写成一页纸(团队版)
很多团队在复盘时只会写「修了」,不会写「为什么发生」。建议你固定一页纸结构:根因链条(触发条件→失效机制→外部表现)、修复策略(临时/永久)、验证证据(命令输出截图或日志行号)、防复发(监控/测试/规则)。这一页纸比十屏聊天更适合放进仓库,也更适合作为下一次 AI 对话的附件。
三十二、调试时如何写「已排除假设」
已排除假设不是摆设,它会显著降低模型的搜索空间。示例:已排除数据库连接失败(其他读写正常);已排除未登录(请求带 cookie);已排除前端旧 bundle(硬刷新与无痕模式复现)。写法要像证据列表,而不是情绪列表。
三十三、当你不得不同时修多个问题时:排队规则
如果线上同时爆了两个问题,先把它们拆成两张工单,两张会话。不要在同一个 thread 里混聊。上下文串线会让调试成本指数上升。你可以用优先级排队,但别用「一锅炖」。
三十四、调试中的「回滚意识」
任何调试补丁都要回答:如果更糟,怎么回滚?尤其在数据库迁移或权限变更场景。把回滚路径写进工单,模型更少会给出「不可逆」的花活。
三十五、用日志而不是用printf:为了下一次AI协作
结构化日志(requestId、userId 哈希、route、耗时)在调试时是你给模型的黄金上下文。临时 console.log 可以,但要记得升级成可检索日志,否则下次你还要靠记忆。
三十六、前端调试:别忽视「状态机不完整」
很多 bug 不是算法错,而是 UI 只有 happy path。调试时先问:loading/error/empty 是否都存在?VibeNote 这种编辑器产品尤其典型:网络失败时如果还能「看起来像保存成功」,用户会恨你,你也会恨自己。
三十七、后端调试:先确认「输入契约」
Route Handler 的 Zod 校验失败与业务异常是两条路径。调试时把 body 打印成结构化 JSON(脱敏后)比猜字段名有效得多。让 AI 改代码前,先让输入输出契约稳定。
三十八、AI 相关调试:分清「提供商错误」与「你的集成错误」
429/401/402 往往是密钥、配额、账单;5xx 可能是提供商不稳定,也可能是你传参不合法。把它们分类写进工单,模型更容易一次命中。
三十九、性能问题也是 bug:调试要换量纲
卡顿与慢请求要用 profiling 或最少也要有耗时日志。不要把「有点慢」丢给模型:它无法从你的感觉里读出瓶颈。
四十、结语补一句
调试能力的提升,会让你对 AI 的态度更健康:你会更少迷信「更强模型」,更多相信「更清楚的问题」。这才是工程师该走的路线。
四十一、从「背锅」到「可学习」:调试文化的团队收益
当调试记录可检索,新同学不会重复踩坑;当调试记录不可检索,老人会变成瓶颈。把调试写成文档,不是额外工作,是把隐性经验显性化。AI 时代显性化经验尤其值钱,因为它能被动挂载、能被复制、能被审查。
四十二、调试与 Code Review 的接口
Review 时不只看代码风格,要看:有没有验证?有没有边界?有没有回滚?有没有把根因写清楚?这些问题的答案,决定这次修复是资产还是负债。
四十三、调试时如何与产品经理沟通
用现象与影响面说话,而不是用栈。栈给工程,影响面给产品。两边对齐后,优先级才合理,你也更容易拿到「允许下线的窗口」去做更深验证。
四十四、调试与监控:把「事后救火」变成「事前预警」
同类错误第二次出现,就该加监控或告警,而不是第二次再人肉排查。调试的终点不是「修好了」,是系统更不容易再坏。
四十五、给 solo 开发者的建议
你没有同事帮你 review,更要写调试记录与未来自己对话。你可以很短,但不能没有:根因一句话 + 验证命令 + 相关 commit。
四十六、再谈三连跪:不是惩罚,是保护
三连跪停手保护的是你的注意力和仓库健康。它不是否认 AI,是否认「在错误坐标系里继续加速」。
四十七、你可以今天就改的一个习惯
从今天起,每次把错误贴给 AI 之前,先自己用中文写三行:我认为错在哪一层;我下一步怎么验证;我不确定的是什么。写完再贴栈,你会惊讶地发现:很多时候你已经不需要 AI 了。
四十八、与第01讲的关系
调试是 Prompt 的极限场景:信息噪声最大、情绪最强、时间最紧。把调试工单写好,你的日常需求 Prompt 会自动变好。
四十九、与第04讲的关系
把三连跪与结构化模板写进规则文件,让团队默认遵守。规则会让个人习惯变成集体默认。
五十、收束
调试方法论不性感,但它决定你能不能长期用 AI。长期用的关键不是炫技,是少返工、少欠债、少熬夜。
五十一、把调试变成「可教学案例」(训练营用法)
你可以每周挑一个真实 bug,脱敏后做成内部案例:坏工单 vs 好工单 vs 最终根因 vs 防回归措施。训练营里最值钱的不是听讲座,而是反复看「当时哪里信息不够」。VibeNote 这种产品调试案例特别丰富:离线、同步、流式、权限、富文本,每一个都值得沉淀。
五十二、调试中的「情绪管理」其实是流程管理
焦虑时人会更倾向「多改一点试试」。流程的意义就是把动作变慢:先复现、先隔离、先验证假设。AI 会放大你的动作速度,所以流程也要同步升级,否则你会更快地把仓库弄乱。
五十三、常见误判:把连锁反应当根因
例如 UI 显示错误,根因可能在数据层;数据层异常,根因可能是上游超时。调试时要区分「第一因」与「放大器」。写根因一句话时,明确你指的是哪一层的第一因。
五十四、调试与文档同步
如果根因是「文档写错/约定不清」,修复代码同时修文档。否则你会迎来第二次、第三次同样的工单。文档修复也是调试产出物,而且是最便宜的那种。
五十五、把「调试」写进 on-call playbook
即便你没有正式 on-call,也建议有半页 playbook:先查哪些日志、先跑哪些命令、先联系谁、哪些事绝对不能做(例如生产环境直接改数据)。 playbook 是规则文件的应急版。
五十六、收束语
调试是工程师的底色。AI 不会拿走底色,只会让你更频繁地面对「更快出错」的风险。把工序立起来,你才能把风险变成优势。
五十七、最后一页:调试自检表(打印贴显示器)
- 我是否稳定复现?
- 我是否知道失败语义(HTTP/TS/网络)?
- 我是否找到第一帧我的代码?
- 我是否写清允许修改范围?
- 我是否准备验证命令与回滚?
- 我是否已经三连跪却仍不愿下场?
五十八、与下一讲的桥
当你调试结束,你会更理解为什么「方案先行」重要:很多 bug 来自实现前没把契约写清。下一讲我们把设计—实现—测试串成一条铁链,让 VibeNote 的迭代成本持续下降。
五十九、再补八个「你应该问自己的问题」
- 这是回归吗?哪次提交引入?
- 只在生产发生吗?还是本地也可复现?
- 是否与特定数据相关?
- 是否与并发相关?
- 是否与缓存相关?
- 是否与权限相关?
- 是否与第三方相关?
- 是否与时间/时区相关?
六十、结语后语
把调试当成手艺练,你会越来越不怕 AI。怕 AI 的根源往往是怕失控;工序就是可控性来源。愿你的 VibeNote 少点深夜救火,多点白天迭代。
六十一、把「调试」写进 Definition of Done(再强调)
合并前:根因是否记录?验证是否可重复?是否需要更新监控?三条任一缺失,就当作没修完。DoD 不是官僚,是把个人记忆变成团队默认。
六十二、最后一句话
别用更大的模型替代更清楚的问题;先用结构化调试把问题变清楚,模型自然会变强。
六十三、练习作业(可选)
本周每次调试都保存一张「结构化工单」截图或文本到 docs/debug/,月底你会得到一本比任何教程都真的教材。真的,去做。真的,去做,别收藏就算了。收藏不会帮你修 bug,工序才会。从下一次报错开始,你就按模板写,坚持七天,你会感到明显轻松。轻松来自可控,可控来自结构化,结构化来自你愿意慢那五分钟。五分钟很值得。别省这五分钟。省了之后会后悔。真的别省。就这样。去练。加油。行。好。