Skip to main content

Overview

Bug fixing with Forge combines human debugging intuition with AI agent execution power. You identify and reproduce the bug, AI agents help fix it, and you verify the solution actually works.

The Bug Fixing Cycle


Step 1: Capture the Bug Report

Start with clear bug documentation.

Bug Report Template

Create a detailed task card with:
  • Via UI
  • Via CLI
  • Via MCP (Claude Code)
Title: "API returns 500 on malformed JSON input"

Description:
  Environment: Production API v2.3.1
  Endpoint: POST /api/users

  Steps to Reproduce:
  1. Send POST request with malformed JSON
  2. Missing closing brace in request body

  Expected: 400 Bad Request with error message
  Actual: 500 Internal Server Error

  Impact: High - crashes API server
  Frequency: ~50 requests/day

  Example Request:
  {
    "name": "John Doe",
    "email": "john@example.com"
    # Missing closing brace

Labels: bug, backend, priority:high, security

Step 2: Reproduce the Bug

Before fixing, ensure you can reliably reproduce it.

Create Reproduction Task

# Create a task specifically for reproduction
forge task create \
  --title "Reproduce: API 500 on malformed JSON" \
  --description "Write failing test that demonstrates the bug" \
  --labels "bug,reproduction" \
  --agent claude-code

Why Reproduction Matters

Benefits of Reproduction

Confirms the bug existsProvides regression testDocuments exact conditionsVerifies fix actually works

Example Reproduction Test

The AI agent might create:
// test/api/users.test.ts
describe('POST /api/users - Error Handling', () => {
  it('should return 400 for malformed JSON', async () => {
    const malformedJson = '{"name":"John","email":"john@example.com"'; // Missing }

    const response = await request(app)
      .post('/api/users')
      .set('Content-Type', 'application/json')
      .send(malformedJson);

    expect(response.status).toBe(400); // Currently fails with 500
    expect(response.body).toHaveProperty('error');
    expect(response.body.error).toContain('Invalid JSON');
  });
});

Step 3: Diagnose Root Cause

Use AI agents to help analyze the problem.

Diagnostic Approaches

  • Code Analysis
  • Log Analysis
  • Stack Trace Analysis
# Let agent analyze the codebase
forge task create \
  --title "Analyze root cause: API 500 error" \
  --description "Review error handling middleware and JSON parsing logic" \
  --agent claude-code \
  --labels "analysis,bug"
Agent might find:
// Missing error handling in middleware
app.use(express.json()); // ❌ No error handler

Step 4: Create Fix Tasks

Break down the fix into focused tasks.

Example: JSON Parsing Bug Fix

# Task 1: Add error handling middleware
forge task create \
  --title "Add JSON parsing error handler" \
  --description "Catch SyntaxError from express.json() and return 400" \
  --agent claude-code \
  --labels "bug,fix"

# Task 2: Add validation
forge task create \
  --title "Add request validation middleware" \
  --description "Validate request body structure before processing" \
  --agent cursor-cli \
  --labels "bug,validation"

# Task 3: Improve error messages
forge task create \
  --title "Add detailed error messages for malformed JSON" \
  --description "Return helpful error messages indicating what's wrong" \
  --agent gemini \
  --labels "bug,ux"

Step 5: Try Multiple Approaches

Use Forge’s multi-attempt feature to explore different solutions.

Approach Comparison

1

Attempt 1: Middleware Approach (Claude)

// Add error handling middleware
app.use((err, req, res, next) => {
  if (err instanceof SyntaxError && err.status === 400 && 'body' in err) {
    return res.status(400).json({
      error: 'Invalid JSON',
      message: err.message
    });
  }
  next();
});
Pros: Standard Express pattern Cons: Only handles middleware errors
2

Attempt 2: Custom Parser (Gemini)

// Replace express.json() with custom parser
app.use((req, res, next) => {
  try {
    req.body = JSON.parse(req.body);
    next();
  } catch (err) {
    return res.status(400).json({
      error: 'Malformed JSON',
      details: err.message
    });
  }
});
Pros: Full control over parsing Cons: Reinventing the wheel
3

Attempt 3: Wrapper with Validation (Cursor)

// Use express-json-validator-middleware
import { Validator } from 'express-json-validator-middleware';

const validator = new Validator({});

app.use(express.json({
  verify: (req, res, buf) => {
    try {
      JSON.parse(buf);
    } catch (err) {
      throw new SyntaxError('Invalid JSON format');
    }
  }
}));
Pros: Validates before parsing Cons: Additional dependency

Compare Attempts

# Run all three approaches
forge task start task-1 --agent claude-code
forge task fork task-1 --agent gemini
forge task fork task-1 --agent cursor-cli

# Compare results
forge task compare task-1

# Test each approach
forge task test task-1-attempt-1
forge task test task-1-attempt-2
forge task test task-1-attempt-3
Decision Matrix:
CriterionClaude (Middleware)Gemini (Custom)Cursor (Validation)
Code Quality⭐⭐⭐⭐⭐⭐⭐⭐⭐⭐⭐⭐
Performance⭐⭐⭐⭐⭐⭐⭐⭐⭐⭐⭐⭐⭐
Maintainability⭐⭐⭐⭐⭐⭐⭐⭐⭐⭐⭐
Security⭐⭐⭐⭐⭐⭐⭐⭐⭐⭐⭐⭐
WinnerBest overall⚠️ Good alternative

Step 6: Verify the Fix

Never trust a fix without verification.

Verification Checklist

# Run the original failing test
forge task test task-reproduction

# Should now pass ✅
# Create additional test task
forge task create \
  --title "Test edge cases for JSON parsing fix" \
  --description "Test various malformed JSON scenarios" \
  --agent claude-code
Tests should cover:
  • Missing closing bracket
  • Extra commas
  • Invalid escape sequences
  • Empty request body
  • Non-JSON content type
# Run full test suite
forge task create \
  --title "Run full test suite" \
  --agent cursor-cli
Ensure the fix didn’t break existing functionality.
# Benchmark before and after
forge task create \
  --title "Benchmark JSON parsing performance" \
  --description "Compare performance before and after fix" \
  --agent gemini

Step 7: Add Regression Test

Prevent the bug from coming back.
# Create comprehensive test task
forge task create \
  --title "Add regression test suite for JSON parsing" \
  --description "Cover all malformed JSON scenarios found in production" \
  --agent claude-code \
  --labels "testing,regression"

Example Regression Test Suite

describe('JSON Parsing - Regression Tests', () => {
  test.each([
    ['missing closing brace', '{"name":"John"'],
    ['extra comma', '{"name":"John",}'],
    ['invalid escape', '{"name":"John\\x"}'],
    ['trailing text', '{"name":"John"}extra'],
    ['leading text', 'extra{"name":"John"}'],
  ])('should return 400 for: %s', async (scenario, malformed) => {
    const response = await request(app)
      .post('/api/users')
      .send(malformed);

    expect(response.status).toBe(400);
    expect(response.body.error).toBeDefined();
  });
});

Step 8: Document the Fix

Update documentation to help prevent similar bugs.
  • Code Comments
  • CHANGELOG
  • API Documentation
// ⚠️ IMPORTANT: JSON parsing error handler
// This middleware catches SyntaxError from malformed JSON
// and returns 400 instead of crashing with 500.
// See: https://github.com/yourorg/repo/issues/123
app.use((err, req, res, next) => {
  if (err instanceof SyntaxError && 'body' in err) {
    return res.status(400).json({
      error: 'Invalid JSON',
      message: 'Request body contains malformed JSON'
    });
  }
  next();
});

Real-World Example: Memory Leak Bug

Here’s a complete bug fix workflow for a production memory leak:
1

Day 1 - Investigation

# Create investigation tasks
forge task create --title "Analyze memory usage patterns" --agent claude-code
forge task create --title "Review event listener registrations" --agent gemini
forge task create --title "Check for unclosed connections" --agent cursor-cli

# Run parallel analysis
forge task start-batch task-1 task-2 task-3

# Finding: WebSocket connections not cleaned up on disconnect
2

Day 2 - Fix Attempts

# Try different fix approaches
forge task create --title "Add connection cleanup on disconnect" --agent claude-code
forge task fork task-4 --agent gemini  # Alternative approach

# Compare solutions
forge task compare task-4

# Claude's approach wins - more comprehensive
3

Day 3 - Verification & Ship

# Add monitoring and tests
forge task create --title "Add memory leak regression tests" --agent claude-code
forge task create --title "Add connection pool monitoring" --agent gemini

# Verify fix in staging
forge task create --title "Load test in staging environment" --agent cursor-cli

# All passed - merge and deploy
forge task merge-all-approved

Bug Severity & Agent Strategy

Choose your approach based on bug severity:
  • Critical (P0)
  • High (P1)
  • Medium (P2)
  • Low (P3)
Characteristics: Production down, data loss, security breachStrategy:
# Use fastest, most reliable agent
forge task create --title "URGENT: Fix auth bypass" --agent claude-code

# No time for multiple attempts - go with proven agent
# Document and refactor later if needed

Pro Tips for Bug Fixing

Never start fixing until you have a failing test:
# ✅ Correct order
1. Write failing test
2. Run test (confirms it fails)
3. Fix the bug
4. Run test (confirms it passes)

# ❌ Wrong order
1. Make changes hoping to fix bug
2. Deploy and pray
# Create bisect task
forge task create \
  --title "Bisect: Find commit that introduced bug" \
  --description "Use git bisect to find regression commit" \
  --agent claude-code
Good labels help with prioritization and analytics:
--labels "bug,security,database,priority:high,customer-reported"

Common Bug Patterns

Null/Undefined Errors

Best Agent: Claude Code (thorough type checking)
forge task create \
  --title "Add null checks to user profile" \
  --agent claude-code

Race Conditions

Best Agent: Claude Code (complex async logic)
forge task create \
  --title "Fix race condition in payment processing" \
  --agent claude-code

Memory Leaks

Best Agent: Claude Code or Cursor CLI
forge task create \
  --title "Fix memory leak in event listeners" \
  --agent claude-code

Performance Issues

Best Agent: Try multiple, compare benchmarks
forge task create \
  --title "Optimize slow database query" \
  --agent claude-code

forge task fork task-1 --agent gemini

Next Steps


Remember: Bugs are opportunities to improve. With Forge, you can experiment with multiple fix approaches in isolation, choose the best solution, and ensure it never happens again.