npx skills add https://github.com/bobmatnyc/claude-mpm-skills --skill bug-fix用于验证缺陷修复的系统化工作流程,以确保质量并防止回归。
在以下情况下使用此技能:
关键:切勿在未首先复现缺陷的情况下进行修复。
## 缺陷复现
### 复现步骤
1. 导航到 `/dashboard`
2. 点击"导出数据"按钮
3. 选择日期范围:1月1日 - 12月31日
4. 点击"生成报告"
### 预期行为
- 报告以 CSV 文件形式下载
- 文件包含日期范围内的所有交易记录
- 下载在 < 5 秒内完成
### 实际行为
- 出现错误:"生成报告失败"
- 控制台错误:`TypeError: Cannot read property 'map' of undefined`
- 没有文件下载
- 问题出现频率:100%
### 环境
- 浏览器:Chrome 120.0.6099.109
- 操作系统:macOS 14.2
- 用户角色:管理员
- 数据大小:约 10,000 条交易记录
### 截图


广告位招租
在这里展示您的产品或服务
触达数万 AI 开发者,精准高效
调查缺陷为何发生,而不仅仅是发生了什么。
## 根本原因分析
### 调查
- 错误发生在 `generateReport()` 函数的第 45 行
- 函数假设 `transactions` 数组始终存在
- 当日期范围没有返回结果时,后端返回 `null`
- 前端没有处理 `null` 的情况,尝试在 `null` 上调用 `.map()`
### 根本原因
- 数组操作前缺少空值检查
- 后端 API 没有返回一致的数据结构(有时返回 `[]`,有时返回 `null`)
- 没有验证 API 响应的结构
### 为何未被发现
- 单元测试仅覆盖了正常路径(数据存在的情况)
- 集成测试没有测试空结果场景
- 后端的不一致性未在 API 契约中记录
修复根本原因,而非症状。
// 修复前(缺陷)
function generateReport(transactions) {
return transactions.map(t => ({
date: t.date,
amount: t.amount,
}));
}
// 修复后(已修复)
function generateReport(transactions) {
// 防止后端返回 null/undefined
if (!transactions || !Array.isArray(transactions)) {
console.warn('No transactions to export');
return [];
}
return transactions.map(t => ({
date: t.date,
amount: t.amount,
}));
}
通过系统化测试证明缺陷已修复。
## 修复验证
### 执行的测试
1. ✅ 遵循原始复现步骤 - 缺陷不再出现
2. ✅ 测试空日期范围 - 显示"没有数据可导出"消息
3. ✅ 测试有效日期范围 - 成功导出
4. ✅ 测试大数据集(50k+ 交易记录) - 工作正常
5. ✅ 在 Chrome、Firefox、Safari 中测试 - 全部正常工作
6. ✅ 在预发布环境中测试 - 修复已确认
### 测试的边界情况
- 空结果集 → 显示适当消息
- API 返回 null 响应 → 优雅处理
- 单条交易记录 → 正确导出
- 格式错误的交易数据 → 记录错误,不会崩溃
### 无新问题
- ✅ 无控制台错误
- ✅ 无内存泄漏
- ✅ 无性能下降
- ✅ 其他导出功能仍正常工作
关键:每个缺陷修复都必须包含测试。
describe('generateReport', () => {
// 复现原始缺陷的测试
it('should handle null transactions gracefully', () => {
const result = generateReport(null);
expect(result).toEqual([]);
expect(console.warn).toHaveBeenCalledWith('No transactions to export');
});
// 边界情况
it('should handle undefined transactions', () => {
const result = generateReport(undefined);
expect(result).toEqual([]);
});
it('should handle empty array', () => {
const result = generateReport([]);
expect(result).toEqual([]);
});
it('should handle single transaction', () => {
const transactions = [{ date: '2025-01-01', amount: 100 }];
const result = generateReport(transactions);
expect(result).toHaveLength(1);
expect(result[0]).toEqual({ date: '2025-01-01', amount: 100 });
});
// 原始正常路径(应仍正常工作)
it('should transform multiple transactions correctly', () => {
const transactions = [
{ date: '2025-01-01', amount: 100 },
{ date: '2025-01-02', amount: 200 },
];
const result = generateReport(transactions);
expect(result).toHaveLength(2);
});
});
为缺陷修复提供全面的 PR 描述。
## 缺陷修复:[简要描述]
**工单**:#123 / ENG-456 / JIRA-789
### 问题
[缺陷的清晰描述]
### 复现步骤(修复前)
1. [步骤 1]
2. [步骤 2]
3. [出现错误]
**预期**:[应该发生什么]
**实际**:[实际发生了什么]
### 根本原因
[缺陷为何发生的详细解释]
- 位置:`src/utils/report.ts`,第 45 行
- 原因:数组操作前缺少空值检查
- 影响:影响所有尝试导出空日期范围的用户
### 解决方案
[修复如何工作的解释]
- 在数组操作前添加了 null/undefined 检查
- 返回空数组而不是崩溃
- 添加了面向用户的警告消息
- 更新了 API 响应处理以更具防御性
### 修复验证(修复后)
1. ✅ 遵循复现步骤 - 缺陷不再出现
2. ✅ 测试边界情况(null、undefined、空数组)
3. ✅ 跨浏览器测试(Chrome、Firefox、Safari)
4. ✅ 在预发布环境中验证
5. ✅ 无新的控制台错误或警告
### 测试覆盖率
- 添加了 null/undefined 处理的单元测试
- 添加了空数组边界情况的测试
- 更新了导出功能的集成测试
- 所有现有测试仍通过
**覆盖率**:+15 行已覆盖,0 行未覆盖
### 回归预防
- [x] 添加了如果重新引入此缺陷会捕获的测试
- [x] 检查了代码库中的类似模式(发现 2 处,在此 PR 中修复)
- [x] 更新了文档以记录 API 响应的不一致性
### 截图/证据
**修复前(缺陷)**:

**修复后(已修复)**:


### 部署说明
- 无需迁移
- 无需环境变量更改
- 可立即安全部署
- 回滚:还原此提交
### 相关问题
- 关闭 #123
- 与 #456 相关(类似的空值处理问题)
创建 .github/PULL_REQUEST_TEMPLATE/bug_fix.md:
## 缺陷修复
**工单**:[工单编号/链接]
### 问题
[缺陷描述]
### 复现步骤(修复前)
1.
2.
3.
**预期**:
**实际**:
### 根本原因
[缺陷为何发生的解释]
### 解决方案
[修复如何工作]
### 验证(修复后)
- [ ] 原始复现步骤不再触发缺陷
- [ ] 测试了边界情况
- [ ] 在多个浏览器/环境中测试
- [ ] 无新的错误或警告
### 测试覆盖率
- [ ] 为缺陷场景添加了测试
- [ ] 为边界情况添加了测试
- [ ] 所有现有测试通过
### 截图
**修复前**:[截图]
**修复后**:[截图]
name: Bug Fix Verification
on:
pull_request:
types: [opened, synchronize]
jobs:
verify-bug-fix:
if: contains(github.event.pull_request.labels.*.name, 'bug')
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Check PR description
run: |
PR_BODY="${{ github.event.pull_request.body }}"
if [[ ! "$PR_BODY" =~ "Root Cause" ]]; then
echo "::error::Bug fix PR must document root cause"
exit 1
fi
if [[ ! "$PR_BODY" =~ "Verification" ]]; then
echo "::error::Bug fix PR must document verification steps"
exit 1
fi
- name: Run tests
run: npm test
- name: Check test coverage
run: |
COVERAGE=$(npm test -- --coverage --json | jq '.total.lines.pct')
if (( $(echo "$COVERAGE < 90" | bc -l) )); then
echo "::warning::Test coverage is below 90%"
fi
universal-verification-pre-merge - 合并前验证清单universal-verification-screenshot - UI 缺陷的视觉验证universal-debugging-systematic-debugging - 系统化调试方法universal-debugging-root-cause-tracing - 根本原因分析技术universal-testing-testing-anti-patterns - 需要避免的测试模式每周安装量
105
仓库
GitHub 星标数
18
首次出现
2026年1月23日
安全审计
已安装于
claude-code81
gemini-cli80
opencode79
codex74
cursor74
github-copilot70
Systematic workflow for verifying bug fixes to ensure quality and prevent regressions.
Use this skill when:
Critical : Never fix a bug without first reproducing it.
## Bug Reproduction
### Steps to Reproduce
1. Navigate to `/dashboard`
2. Click "Export Data" button
3. Select date range: Jan 1 - Dec 31
4. Click "Generate Report"
### Expected Behavior
- Report downloads as CSV file
- File contains all transactions for date range
- Download completes in < 5 seconds
### Actual Behavior
- Error appears: "Failed to generate report"
- Console error: `TypeError: Cannot read property 'map' of undefined`
- No file downloads
- Issue occurs 100% of the time
### Environment
- Browser: Chrome 120.0.6099.109
- OS: macOS 14.2
- User Role: Admin
- Data Size: ~10,000 transactions
### Screenshots


Investigate WHY the bug occurs, not just WHAT happens.
## Root Cause Analysis
### Investigation
- Error occurs in `generateReport()` function at line 45
- Function assumes `transactions` array always exists
- When date range returns no results, backend returns `null`
- Frontend doesn't handle `null` case, tries to call `.map()` on `null`
### Root Cause
- Missing null check before array operations
- Backend API doesn't return consistent data structure (sometimes `[]`, sometimes `null`)
- No validation of API response shape
### Why This Wasn't Caught
- Unit tests only covered happy path (data exists)
- Integration tests didn't test empty result scenario
- Backend inconsistency not documented in API contract
Fix the root cause, not the symptom.
// BEFORE (Bug)
function generateReport(transactions) {
return transactions.map(t => ({
date: t.date,
amount: t.amount,
}));
}
// AFTER (Fixed)
function generateReport(transactions) {
// Guard against null/undefined from backend
if (!transactions || !Array.isArray(transactions)) {
console.warn('No transactions to export');
return [];
}
return transactions.map(t => ({
date: t.date,
amount: t.amount,
}));
}
Prove the bug is fixed through systematic testing.
## Fix Verification
### Testing Performed
1. ✅ Followed original reproduction steps - bug no longer occurs
2. ✅ Tested with empty date range - shows "No data to export" message
3. ✅ Tested with valid date range - exports successfully
4. ✅ Tested with large dataset (50k+ transactions) - works correctly
5. ✅ Tested in Chrome, Firefox, Safari - all working
6. ✅ Tested on staging environment - fix confirmed
### Edge Cases Tested
- Empty result set → Shows appropriate message
- Null response from API → Handled gracefully
- Single transaction → Exports correctly
- Malformed transaction data → Logs error, doesn't crash
### No New Issues
- ✅ No console errors
- ✅ No memory leaks
- ✅ No performance degradation
- ✅ Other export features still work
Critical : Every bug fix must include tests.
describe('generateReport', () => {
// Test that reproduces original bug
it('should handle null transactions gracefully', () => {
const result = generateReport(null);
expect(result).toEqual([]);
expect(console.warn).toHaveBeenCalledWith('No transactions to export');
});
// Edge cases
it('should handle undefined transactions', () => {
const result = generateReport(undefined);
expect(result).toEqual([]);
});
it('should handle empty array', () => {
const result = generateReport([]);
expect(result).toEqual([]);
});
it('should handle single transaction', () => {
const transactions = [{ date: '2025-01-01', amount: 100 }];
const result = generateReport(transactions);
expect(result).toHaveLength(1);
expect(result[0]).toEqual({ date: '2025-01-01', amount: 100 });
});
// Original happy path (should still work)
it('should transform multiple transactions correctly', () => {
const transactions = [
{ date: '2025-01-01', amount: 100 },
{ date: '2025-01-02', amount: 200 },
];
const result = generateReport(transactions);
expect(result).toHaveLength(2);
});
});
Comprehensive PR description for bug fixes.
## Bug Fix: [Brief Description]
**Ticket**: #123 / ENG-456 / JIRA-789
### Problem
[Clear description of the bug]
### Reproduction Steps (Before Fix)
1. [Step 1]
2. [Step 2]
3. [Error occurs]
**Expected**: [What should happen]
**Actual**: [What happened instead]
### Root Cause
[Detailed explanation of why bug occurred]
- Where: `src/utils/report.ts`, line 45
- Why: Null check missing before array operation
- Impact: Affects all users trying to export with empty date ranges
### Solution
[Explanation of how fix works]
- Added null/undefined check before array operations
- Return empty array instead of crashing
- Added user-facing warning message
- Updated API response handling to be more defensive
### Fix Verification (After)
1. ✅ Followed reproduction steps - bug no longer occurs
2. ✅ Tested edge cases (null, undefined, empty array)
3. ✅ Tested across browsers (Chrome, Firefox, Safari)
4. ✅ Verified on staging environment
5. ✅ No new console errors or warnings
### Test Coverage
- Added unit tests for null/undefined handling
- Added tests for empty array edge case
- Updated integration tests for export feature
- All existing tests still passing
**Coverage**: +15 lines covered, 0 lines uncovered
### Regression Prevention
- [x] Tests added that would catch this bug if reintroduced
- [x] Similar patterns checked in codebase (found 2, fixed in this PR)
- [x] Documentation updated to note API response inconsistency
### Screenshots/Evidence
**Before (Bug)**:

**After (Fixed)**:


### Deployment Notes
- No migrations required
- No environment variable changes
- Safe to deploy immediately
- Rollback: Revert this commit
### Related Issues
- Closes #123
- Related to #456 (similar null handling issue)
Create .github/PULL_REQUEST_TEMPLATE/bug_fix.md:
## Bug Fix
**Ticket**: [Ticket number/link]
### Problem
[Description of bug]
### Reproduction Steps (Before Fix)
1.
2.
3.
**Expected**:
**Actual**:
### Root Cause
[Explanation of why bug occurred]
### Solution
[How fix works]
### Verification (After)
- [ ] Original reproduction steps no longer trigger bug
- [ ] Edge cases tested
- [ ] Tested in multiple browsers/environments
- [ ] No new errors or warnings
### Test Coverage
- [ ] Tests added for bug scenario
- [ ] Tests added for edge cases
- [ ] All existing tests passing
### Screenshots
**Before**: [Screenshot]
**After**: [Screenshot]
name: Bug Fix Verification
on:
pull_request:
types: [opened, synchronize]
jobs:
verify-bug-fix:
if: contains(github.event.pull_request.labels.*.name, 'bug')
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Check PR description
run: |
PR_BODY="${{ github.event.pull_request.body }}"
if [[ ! "$PR_BODY" =~ "Root Cause" ]]; then
echo "::error::Bug fix PR must document root cause"
exit 1
fi
if [[ ! "$PR_BODY" =~ "Verification" ]]; then
echo "::error::Bug fix PR must document verification steps"
exit 1
fi
- name: Run tests
run: npm test
- name: Check test coverage
run: |
COVERAGE=$(npm test -- --coverage --json | jq '.total.lines.pct')
if (( $(echo "$COVERAGE < 90" | bc -l) )); then
echo "::warning::Test coverage is below 90%"
fi
universal-verification-pre-merge - Pre-merge verification checklistuniversal-verification-screenshot - Visual verification for UI bugsuniversal-debugging-systematic-debugging - Systematic debugging methodologyuniversal-debugging-root-cause-tracing - Root cause analysis techniquesuniversal-testing-testing-anti-patterns - Testing patterns to avoidWeekly Installs
105
Repository
GitHub Stars
18
First Seen
Jan 23, 2026
Security Audits
Gen Agent Trust HubPassSocketPassSnykPass
Installed on
claude-code81
gemini-cli80
opencode79
codex74
cursor74
github-copilot70
minimal-run-and-audit:AI论文复现执行与审计技能,标准化测试与报告
6,100 周安装