Claude Code Hook for Context Window Monitoring
ContextGuard is a Rust-based hook for Claude Code that monitors context window usage and prevents critical context exhaustion by alerting users before reaching token limits.
- Real-time token monitoring - Tracks usage from Claude Code session JSONL files
- Automatic session continuation - SessionStart hooks for seamless context handoff
- Configurable thresholds - TOML config file (project or global)
- Zero dependencies - Fast, lightweight Rust binary (~433KB)
- Defensive error handling - Handles missing files, corrupted JSON, and edge cases
- Non-intrusive - Silent when usage is normal, alerts only when needed
ContextGuard uses two measurement methods with three hooks for comprehensive context management:
When you run /context, ContextGuard:
- Parses the output from the JSONL transcript
- Extracts exact token counts (system, tools, messages, buffer)
- Uses this as the baseline for all monitoring
- Updates automatically each time you run
/context
When no /context output is available, ContextGuard:
- Counts billable tokens from API usage events
- Applies compression ratio (accounts for deduplication)
- Adds system overhead (prompts, tools, buffer)
- Formula:
total β (billable Γ 0.071) + 60,000
- Before each prompt, reads the session transcript JSONL file
- Tries Method A (parse
/contextoutput) for exact accuracy - Falls back to Method B (heuristic) if no
/contextavailable - Checks against thresholds:
- < 60%: Silent, allows continuation
- 60-75%: Shows warning message, allows continuation
- β₯ 75%: Creates
CONTINUE_SESSION.mdwith handoff instructions
- sessionstart-context: Asks Claude to prompt user to run
/contextfor accuracy - sessionstart-continuation: Auto-loads
CONTINUE_SESSION.mdif present - Zero friction: New sessions automatically continue with previous context
π‘ Pro Tip: Run /context at the start of your session for 100% accurate monitoring!
# Clone or navigate to ContextGuard directory
cd /data/git/Guard8.ai/ContextGuard
# Build and install
./install.shAdd to ~/.claude/settings.json:
{
"hooks": {
"SessionStart": [{
"hooks": [
{
"type": "command",
"command": "~/.claude/hooks/contextguard-sessionstart-context"
},
{
"type": "command",
"command": "~/.claude/hooks/contextguard-sessionstart-continuation"
}
]
}],
"UserPromptSubmit": [{
"hooks": [{
"type": "command",
"command": "~/.claude/hooks/contextguard"
}]
}]
}
}The hook is already configured in .claude/settings.json for this project.
# Test with missing file (should return safe default)
echo '{"session_id":"test","transcript_path":"/tmp/nonexistent.jsonl","hook_event_name":"UserPromptSubmit"}' | ~/.claude/hooks/contextguard
# Expected output:
# {"continue":true}
# Warning: Transcript file does not exist: /tmp/nonexistent.jsonlContextGuard looks for config files in this order:
.claude/contextguard.toml(project-specific)~/.claude/contextguard.toml(global)- Built-in defaults (if no config found)
Create .claude/contextguard.toml:
# Total context window limit (default: 200000)
context_limit = 200000
# Critical threshold - blocks execution (default: 0.75 = 75%)
critical_threshold = 0.75
# Warning threshold - shows warning (default: 0.60 = 60%)
warning_threshold = 0.60For testing, set low thresholds (new sessions start ~30%):
context_limit = 200000
critical_threshold = 0.40 # Block at 40%
warning_threshold = 0.35 # Warn at 35%No rebuild needed - config is read at runtime!
ContextGuard/
βββ src/
β βββ main.rs # Hook entry point
β βββ config.rs # TOML config loader
β βββ hook_types.rs # Claude Code hook I/O structures
β βββ jsonl_parser.rs # JSONL transcript parsing
β βββ threshold_checker.rs # Token usage thresholds
β βββ session_handoff.rs # Session continuation generation
βββ hooks/
β βββ sessionstart-context # Prompts /context command
β βββ sessionstart-continuation # Auto-loads CONTINUE_SESSION.md
βββ .claude/
β βββ contextguard.toml # Project config (test thresholds)
β βββ settings.json # Hook registration
βββ Cargo.toml # Rust dependencies
βββ install.sh # Installation script
βββ README.md # This file
Adapted from HalluciGuard:
- Streams JSONL line-by-line (no memory overhead)
- Extracts token usage from each event
- Handles all token types: input, output, cache creation, cache read
- Defensive against missing files and corrupted lines
- Input: JSON from Claude Code via stdin
- Output: JSON response to stdout
- Fields:
continue:true(allow) orfalse(block)stopReason: Optional blocking reasonsystemMessage: Optional user-facing message
Handles known Claude Code issues:
- Issue #3046: Missing transcript files after
/clear - Issue #2597: Cross-session summary contamination
- Safe defaults: missing file = 0 tokens
β οΈ ContextGuard: Approaching context limit
Usage: 125.0k / 200.0k tokens (63%)
Consider using /clear soon.
π ContextGuard: Critical context usage!
Usage: 155.0k / 200.0k tokens (78%)
Please use /clear or start a new session to continue.
# Run tests
cargo test
# Build optimized release
cargo build --release
# Check binary size
ls -lh target/release/contextguard
# Manual test with sample data
echo '{"session_id":"test","transcript_path":"test_data.jsonl","hook_event_name":"UserPromptSubmit"}' | cargo run --release- HalluciGuard - Hallucination detection
- TaskGuard - Task management
- ccusage - Token usage analysis
Part of the Guard8.ai toolkit.
Built with TaskGuard - See tasks/ for implementation tracking