修复缺陷
概述
基于证据定位根因,做最小且安全的修改并验证。仅在高风险/不可逆变更时确认。
建议角色
- •👨💻 高级开发者:定位根因并实施最小修复。
- •🧪 QA 工程师:设计复现步骤并验证回归。
何时使用
- •失败测试、回归、崩溃、错误输出、性能下降、不稳定行为
- •堆栈、错误日志、异常、超时、带复现步骤的用户报告
- •需要纠正既有行为,而非新增功能
不适用
- •新功能或大幅行为变更(用 develop-feature)
- •大范围重构或重新设计(切换到 refactor 流程)
必需子技能
- •REQUIRED SUB-SKILL: verification-before-completion
核心模式
- •观察:捕捉精确失败(日志/堆栈/失败测试)
- •复现:最小复现或定向日志
- •定位:沿输入 → 失败追踪,找出第一个错误假设
- •修复:最小变更解决根因
- •验证:重跑复现 + 相关回归检查
快速参考
| 步骤 | 目标 | 证据 |
|---|---|---|
| 观察 | 失败内容与位置 | 堆栈、日志、失败测试 |
| 复现 | 可按需失败 | 最小复现、定向日志 |
| 定位 | 找到第一个错误假设 | 代码跟踪、git bisect |
| 修复 | 最小且安全 | 最小 diff,避免重构 |
| 验证 | 证明已修复 | 测试命令、手动步骤 |
最佳实践
观察阶段
- •精确记录:完整复制堆栈跟踪、错误消息和日志,不要依赖记忆
- •收集上下文:记录发生错误的环境(环境变量、配置、输入数据)
- •识别模式:查找是否为重复问题,检查已知 bug 或历史记录
复现阶段
- •最小化复现:尽可能创建最小的复现脚本或测试用例
- •定向日志:在关键路径添加临时日志,缩小错误范围
- •隔离变量:控制环境变量和输入,确保复现稳定
定位阶段
- •从证据出发:沿着堆栈跟踪或失败路径,找到第一个错误假设
- •代码跟踪:逐步执行代码,观察变量状态和程序流程
- •版本比对:使用 git bisect 找到引入 bug 的提交
修复阶段
- •最小变更:只修改必要的代码,避免顺手重构
- •根因修复:针对根本原因,而不是症状(如不直接用 try/catch 掩盖错误)
- •保护性编程:添加必要的检查和断言,防止类似问题
- •文档更新:如果 bug 揭示了设计缺陷,考虑更新架构文档
验证阶段
- •复现修复:运行之前的复现步骤,确认问题已解决
- •回归检查:运行相关测试,确保没有引入新问题
- •边缘案例:测试边界条件和异常情况
- •证据留存:保存测试输出和日志,证明修复有效
常见陷阱
- •猜测根因:没有充分证据就假设问题原因
- •只补症状:用 try/catch 或返回默认值掩盖错误
- •过度重构:在修复 bug 时顺便重构,增加风险
- •跳过验证:修复后不充分测试就声称完成
- •禁用测试:为通过测试而禁用或修改测试用例
实施要点
- •从证据出发,不凭猜测;引用检查过的文件/函数/行号。
- •缺少复现时先补证据(临时日志/失败测试)。
- •优先局部、可回滚变更;范围扩大或风险上升再询问。
- •解释为什么能修复根因(不是只说改了什么)。
高风险确认条件
- •破坏性或不可逆操作(数据删除、历史重写、破坏性迁移)
- •安全、鉴权变更或敏感数据处理
- •破坏 API、契约或兼容性风险
示例
症状: TypeError: Cannot read properties of undefined (reading 'id')
根因: 认证 token 过期时 user 可能为 undefined。
修复(最小保护):
ts
// before const userId = user.id; // after if (!user) return res.status(401).end(); const userId = user.id;
验证: 添加测试 “expired token returns 401” 并重跑失败端点。
常见错误
- •只补症状(try/catch)而不定位根因
- •没有复现或证据就猜测
- •为小 bug 做大范围重构
- •跳过验证或回归检查
- •通过禁用测试或加超时来“变绿”
借口 vs 事实
| 借口 | 事实 |
|---|---|
| “没时间复现” | 盲修会引入回归;做最小复现或日志。 |
| “先加 try/catch 就行” | 只是掩盖失败;应修复错误数据来源。 |
| “为稳妥起见先重构” | 变更越大风险越高;先做最小修复。 |
| “涉及多模块必须先问” | 说明范围变化;仅在风险增加时询问。 |
红旗 - 立刻停止
- •“先加 try/catch”
- •“先禁用测试”
- •“无法复现就猜”
- •“不如全量重构”
- •“不验证就上线”
- •“高风险变更未明确确认”