/**
* fix_bug 工具
*
* 功能:指导完整的 Bug 修复流程
* 模式:指令生成器模式 - 返回详细的修复指南,由 AI 执行实际操作
*
* 流程:问题定位 → 原因分析 → 修复方案 → 验证测试
*/
const PROMPT_TEMPLATE = `# Bug 修复指南
## 🐛 Bug 信息
**错误信息**:
\`\`\`
{error_message}
\`\`\`
{stack_trace_section}
{reproduce_section}
{behavior_section}
---
## 📍 阶段 1: 问题定位
### 步骤 1.1: 分析错误信息
1. **识别错误类型**:
- 语法错误(SyntaxError)
- 运行时错误(TypeError, ReferenceError, RangeError)
- 逻辑错误(结果不符合预期)
- 异步错误(Promise rejection, 回调异常)
2. **提取关键信息**:
- 错误名称: [从错误信息中提取]
- 错误消息: [具体描述]
- 发生位置: [文件:行号]
### 步骤 1.2: 分析堆栈跟踪
**操作**:
1. 找到堆栈中第一个项目文件(排除 node_modules)
2. 追踪调用链,理解执行流程
3. 记录所有相关的项目文件
**相关文件列表**:
| 文件 | 行号 | 函数/方法 |
|------|------|-----------|
| [文件路径] | [行号] | [函数名] |
### 步骤 1.3: 读取相关代码
**操作**: 读取以下文件并分析:
- 错误发生的文件
- 调用链上的文件
- 相关的配置文件
- 相关的测试文件(如有)
### 📋 定位结论
| 项目 | 内容 |
|------|------|
| 问题文件 | [文件路径] |
| 问题位置 | 第 X 行 |
| 问题代码 | \`[代码片段]\` |
| 触发条件 | [什么情况下触发] |
---
## 🔍 阶段 2: 原因分析
### 步骤 2.1: 5 Whys 分析
使用 5 Whys 方法深入分析根本原因:
1. **Why 1**: 为什么会出现这个错误?
- [答案]
2. **Why 2**: 为什么会 [Why 1 的答案]?
- [答案]
3. **Why 3**: 为什么会 [Why 2 的答案]?
- [答案]
4. **Why 4**: 为什么会 [Why 3 的答案]?
- [答案]
5. **Why 5**: 为什么会 [Why 4 的答案]?
- [答案]
### 步骤 2.2: 代码逻辑分析
1. **数据流分析**: 追踪数据从输入到出错位置的流动
2. **状态分析**: 检查相关变量/状态在出错时的值
3. **边界条件**: 检查是否处理了所有边界情况
4. **异常处理**: 检查是否有适当的错误处理
### 📋 分析结论
| 项目 | 内容 |
|------|------|
| 直接原因 | [直接导致错误的原因] |
| 根本原因 | [深层次的原因] |
| 触发条件 | [什么情况下会触发] |
| 影响范围 | [受影响的功能/模块] |
---
## 🔧 阶段 3: 修复方案
### 步骤 3.1: 设计修复方案
**方案 A**: [方案描述]
- 修改内容: [具体修改]
- 优点: [优点]
- 缺点: [缺点]
- 风险: [潜在风险]
**方案 B**: [备选方案描述]
- 修改内容: [具体修改]
- 优点: [优点]
- 缺点: [缺点]
- 风险: [潜在风险]
**选择方案**: [选择的方案]
**选择理由**: [为什么选择这个方案]
### 步骤 3.2: 影响范围评估
| 影响项 | 说明 |
|--------|------|
| 修改文件 | [文件列表] |
| 影响功能 | [功能列表] |
| 需要测试 | [测试范围] |
| 是否需要回归 | [是/否] |
### 步骤 3.3: 实施修复
**修改文件**: \`[文件路径]\`
**修改前**:
\`\`\`
[原代码]
\`\`\`
**修改后**:
\`\`\`
[新代码]
\`\`\`
**修改说明**: [解释修改的原因和逻辑]
---
## ✅ 阶段 4: 验证测试
### 步骤 4.1: 单元测试
为修复编写针对性的单元测试:
\`\`\`typescript
describe('[功能描述]', () => {
// 测试正常情况
it('should [正常行为描述]', () => {
// 测试代码
});
// 测试修复的 Bug 场景
it('should handle [Bug 场景]', () => {
// 测试代码 - 确保 Bug 已修复
});
// 测试边界情况
it('should handle [边界情况]', () => {
// 边界测试
});
});
\`\`\`
### 步骤 4.2: 手动验证
1. [ ] 按原复现步骤验证问题已修复
2. [ ] 验证正常流程不受影响
3. [ ] 验证边界情况处理正确
4. [ ] 验证错误处理正确
### 步骤 4.3: 回归测试
1. [ ] 运行相关模块的测试
2. [ ] 运行全量测试(如有 CI)
3. [ ] 检查是否引入新问题
---
## 📋 修复检查清单
### 定位阶段
- [ ] 错误类型已识别
- [ ] 问题代码已定位
- [ ] 相关文件已读取
### 分析阶段
- [ ] 5 Whys 分析已完成
- [ ] 根本原因已确定
- [ ] 影响范围已评估
### 修复阶段
- [ ] 修复方案已设计
- [ ] 代码修改已完成
- [ ] 修改已解释清楚
### 验证阶段
- [ ] 单元测试已添加
- [ ] 手动验证已通过
- [ ] 回归测试已通过
### 提交阶段
- [ ] 代码已提交
- [ ] Commit message 清晰描述了修复内容
---
## 📝 修复总结
完成修复后,填写以下总结:
| 项目 | 内容 |
|------|------|
| Bug 描述 | [简述] |
| 根本原因 | [原因] |
| 修复方案 | [方案] |
| 修改文件 | [文件列表] |
| 测试覆盖 | [测试情况] |
| 修复时间 | [耗时] |
---
## 💡 经验教训
记录本次 Bug 的经验教训,避免类似问题:
1. **代码层面**: [如何避免写出类似 Bug]
2. **测试层面**: [应该增加什么测试]
3. **流程层面**: [流程上如何改进]
---
## 📤 输出格式要求
请严格按以下 JSON 格式输出修复指南:
\`\`\`json
{
"bug_summary": "Bug 简述(一句话)",
"analysis": {
"error_type": "错误类型",
"direct_cause": "直接原因",
"root_cause": "根本原因",
"affected_scope": "影响范围"
},
"location": {
"file": "问题文件路径",
"line": 42,
"function": "问题函数名",
"code_snippet": "问题代码片段"
},
"fix_plan": {
"chosen_solution": "选择的修复方案",
"reason": "选择理由",
"steps": [
{ "step": 1, "action": "修复步骤", "file": "文件", "change": "变更内容" }
],
"code_before": "修改前代码",
"code_after": "修改后代码"
},
"verification": {
"test_cases": ["测试用例1", "测试用例2"],
"manual_checks": ["手动验证项1", "手动验证项2"]
}
}
\`\`\`
## ⚠️ 边界约束
- ❌ 仅提供修复指南,不保证自动修改代码
- ❌ 不执行代码或命令
- ✅ 输出结构化修复方案和验证步骤
- 💡 如需自动修复,可配合 fix 工具应用 patch
---
*指南版本: 1.0.0*
*工具: MCP Probe Kit - fix_bug*
`;
import { parseArgs, getString } from "../utils/parseArgs.js";
/**
* fix_bug 工具实现
*/
export async function fixBug(args: any) {
try {
// 智能参数解析,支持自然语言输入
const parsedArgs = parseArgs<{
error_message?: string;
stack_trace?: string;
steps_to_reproduce?: string;
expected_behavior?: string;
actual_behavior?: string;
}>(args, {
defaultValues: {
error_message: "",
stack_trace: "",
steps_to_reproduce: "",
expected_behavior: "",
actual_behavior: "",
},
primaryField: "error_message", // 纯文本输入默认映射到 error_message 字段
fieldAliases: {
error_message: ["error", "err", "message", "错误", "错误信息"],
stack_trace: ["stack", "trace", "堆栈", "调用栈"],
steps_to_reproduce: ["steps", "reproduce", "步骤", "复现步骤"],
expected_behavior: ["expected", "期望", "期望行为"],
actual_behavior: ["actual", "实际", "实际行为"],
},
});
const errorMessage = getString(parsedArgs.error_message);
const stackTrace = getString(parsedArgs.stack_trace);
const stepsToReproduce = getString(parsedArgs.steps_to_reproduce);
const expectedBehavior = getString(parsedArgs.expected_behavior);
const actualBehavior = getString(parsedArgs.actual_behavior);
if (!errorMessage) {
throw new Error("缺少必填参数: error_message(错误信息)");
}
// 构建可选部分
const stackTraceSection = stackTrace
? `**堆栈跟踪**:\n\`\`\`\n${stackTrace}\n\`\`\``
: "**堆栈跟踪**: 未提供(建议提供以便更准确定位)";
const reproduceSection = stepsToReproduce
? `**复现步骤**:\n${stepsToReproduce}`
: "";
let behaviorSection = "";
if (expectedBehavior || actualBehavior) {
behaviorSection = [
expectedBehavior ? `**期望行为**: ${expectedBehavior}` : "",
actualBehavior ? `**实际行为**: ${actualBehavior}` : "",
]
.filter(Boolean)
.join("\n\n");
}
const guide = PROMPT_TEMPLATE
.replace(/{error_message}/g, errorMessage)
.replace(/{stack_trace_section}/g, stackTraceSection)
.replace(/{reproduce_section}/g, reproduceSection)
.replace(/{behavior_section}/g, behaviorSection);
return {
content: [{ type: "text", text: guide }],
};
} catch (error) {
const errorMsg = error instanceof Error ? error.message : String(error);
return {
content: [{ type: "text", text: `❌ 生成修复指南失败: ${errorMsg}` }],
isError: true,
};
}
}