# Trip Conditions for the Munder Difflin Circuit Breaker: 7 Runtime Triggers Explained

> Understand Munder Difflin Circuit Breaker trip conditions. Learn about 7 runtime triggers like tool loops and API errors that stop agents when thresholds are breached.

- Repository: [Chaitanya Giri/munder-difflin](https://github.com/chaitanyagiri/munder-difflin)
- Tags: deep-dive
- Published: 2026-08-27

---

**The Munder Difflin Circuit Breaker monitors agent runtime behavior through seven distinct trip conditions—including repeated tool loops, API error storms, and token velocity spikes—that escalate agents from healthy to stopped when thresholds are breached in [`src/main/breaker.ts`](https://github.com/chaitanyagiri/munder-difflin/blob/main/src/main/breaker.ts).**

The `chaitanyagiri/munder-difflin` repository implements a sophisticated circuit-breaker pattern for coordinating autonomous agents. Understanding the **trip conditions for the Munder Difflin Circuit Breaker** is essential for configuring safe operational limits and debugging agent behavior during high-load scenarios.

## The Seven Trip Conditions Defined in [`src/main/breaker.ts`](https://github.com/chaitanyagiri/munder-difflin/blob/main/src/main/breaker.ts)

Inside [`src/main/breaker.ts`](https://github.com/chaitanyagiri/munder-difflin/blob/main/src/main/breaker.ts), the `evaluate()` method checks seven specific conditions each heartbeat. When any condition returns true, the breaker sets a `tripping` flag and provides a human-readable reason.

### 1. Repeated Identical Tool Calls (Loop Detection)

The breaker detects agent loops by counting consecutive identical tool invocations. When `s.repeatCount >= cfg.repeatedToolLimit` (default **8** identical calls), the breaker trips with reason `looping`. This prevents infinite loops of the same tool name and input. [Source: lines 94-96]

### 2. API-Error Storm Detection

Consecutive API errors without successful progress trigger this condition. The breaker tracks `s.errorCount` against `cfg.errorStormLimit` (default **5** consecutive errors). This catches retry storms and upstream service failures. [Source: lines 98-100]

### 3. Per-Agent Token Cap

Each agent can have a specific token budget via `agentTokenCaps`. The breaker compares `tokensOf(input.sample)` against the agent's individual `perAgentCap`. Unlike floor-wide limits, this applies per agent ID. [Source: lines 103-105]

### 4. Floor-Wide Cost Cap

When the total USD cost across all agents exceeds the configurable `costCapUsd`, the breaker identifies the top spender (`isTopSpender`) and trips only for that agent. This ensures budget enforcement targets the primary consumer. [Source: lines 108-110]

### 5. Floor-Wide Token Cap

Similar to the cost cap, this monitors aggregate token usage against `costCapTokens`. When breached, only the `isTopTokenSpender` agent is tripped, preventing floor-wide token exhaustion while allowing efficient agents to continue. [Source: lines 112-114]

### 6. Token-Velocity Spike

The breaker calculates output token velocity (Δoutput / Δminutes) and compares it to `cfg.tokenVelocityPerMin` (default **60,000 tokens/minute**). Spikes indicating runaway generation trigger immediate escalation. Note: This check is disabled during compaction (when `s.compactingUntil` is active). [Source: lines 124-126]

### 7. No-Progress Debounce

When an agent generates tokens but shows no coordination file activity (`!input.progressing && !toolActive`) for `NO_PROGRESS_BEATS` (default **2 consecutive beats**), the breaker trips. This catches stalled or zombie agents. This is also disabled during compaction. [Source: lines 132-138]

## Escalation Ladder and Recovery Logic

The Munder Difflin Circuit Breaker implements a four-level escalation system evaluated in `tick()`:

- **healthy**: Normal operation
- **steering**: Initial warning state
- **constrained**: Severely limited operation
- **stopped**: Halted execution (or `constrained` if `hardStop` is disabled)

The system escalates one level per beat when conditions are met and recovers one level per healthy beat. The optional `hardStop` flag in [`src/main/config.ts`](https://github.com/chaitanyagiri/munder-difflin/blob/main/src/main/config.ts) promotes the maximum level from `constrained` to `stopped`.

## Configuring Trip Thresholds in [`src/main/config.ts`](https://github.com/chaitanyagiri/munder-difflin/blob/main/src/main/config.ts)

All thresholds are configurable through the runtime configuration accessed via `getConfig()`:

- `repeatedToolLimit`: Integer (default 8)
- `errorStormLimit`: Integer (default 5)
- `agentTokenCaps`: Map of agent IDs to token limits
- `costCapUsd`: Number for floor-wide USD budget
- `costCapTokens`: Number for floor-wide token budget
- `tokenVelocityPerMin`: Integer (default 60000)
- `hardStop`: Boolean to enable full stops vs. constrained mode

## Implementation Example: Detecting Trips in Practice

Below is a complete example showing initialization, feeding usage data, and handling trip decisions:

```typescript
import { CircuitBreaker } from './src/main/breaker';
import { getConfig } from './src/main/config';

// Initialize with live configuration
const breaker = new CircuitBreaker(() => getConfig());

// Simulate agent inputs across a heartbeat
const inputs = [
  {
    agentId: 'agent-42',
    sample: {
      input: 1200,
      output: 8000,
      cacheRead: 300,
      cacheCreation: 200,
      usd: 0.45,
      ts: Date.now()
    },
    progressing: true  // File-mtime indicates coordination activity
  }
];

// Evaluate current tick
const decisions = breaker.tick(inputs, Date.now());

// React to breaker decisions
for (const d of decisions) {
  if (d.action !== 'none') {
    console.log(`[Breaker] ${d.state.agentId} → ${d.state.level}: ${d.state.reason}`);
    // Implement corrective action (steer message, pause, or terminate)
  }
}

```

To simulate the repeated-tool trip condition:

```typescript
// Record identical tool usage 8+ times
for (let i = 0; i < 8; i++) {
  breaker.recordToolUse('agent-42', 'search', { query: 'foo' });
}

// Next tick will escalate to 'steering' with reason:
// "looping: 8× identical tool call (search)"

```

## Summary

- The **Munder Difflin Circuit Breaker** evaluates seven distinct trip conditions in [`src/main/breaker.ts`](https://github.com/chaitanyagiri/munder-difflin/blob/main/src/main/breaker.ts) to prevent runaway agent behavior.
- **Loop detection** triggers after 8 identical tool calls; **error storms** after 5 consecutive API failures.
- **Budget controls** include per-agent token caps and floor-wide cost/token limits targeting the top spender.
- **Velocity spikes** (>60,000 tokens/min) and **no-progress states** (2+ beats without coordination activity) trigger escalation.
- The system respects **compaction exemptions**, disabling velocity and no-progress checks when `s.compactingUntil` is active.
- Escalation follows a ladder from healthy → steering → constrained → stopped, configurable via `hardStop` in [`src/main/config.ts`](https://github.com/chaitanyagiri/munder-difflin/blob/main/src/main/config.ts).

## Frequently Asked Questions

### What file contains the core trip condition logic?

The `evaluate()` method in [`src/main/breaker.ts`](https://github.com/chaitanyagiri/munder-difflin/blob/main/src/main/breaker.ts) contains all seven trip condition checks, including the loop detection (lines 94-96), error storm detection (lines 98-100), and velocity calculations (lines 124-126).

### How do I configure the repeated tool call limit?

Set `repeatedToolLimit` in your configuration object returned by [`src/main/config.ts`](https://github.com/chaitanyagiri/munder-difflin/blob/main/src/main/config.ts). The default is 8 identical calls, after which the breaker returns a `looping` reason and escalates the agent.

### Why does the breaker ignore velocity spikes during compaction?

While `s.compactingUntil` is truthy, the breaker disables velocity and no-progress checks (lines 78-81) to prevent false positives during legitimate high-throughput compaction operations that would otherwise appear as runaway generation.

### What is the difference between the floor-wide cost cap and per-agent token cap?

The **per-agent token cap** enforces limits on individual agent consumption using `agentTokenCaps`, while the **floor-wide cost cap** monitors aggregate USD spend across all agents and only trips the current top spender when `costCapUsd` is exceeded.