DCG — Destructive Command Guard
A high-performance Claude Code hook that intercepts and blocks destructive commands before they execute. Written in Rust with SIMD-accelerated filtering for sub-millisecond latency.
Why This Exists
AI coding agents are powerful but fallible. They can accidentally run destructive commands:
- "Let me clean up the build artifacts" →
rm -rf ./src(typo) - "I'll reset to the last commit" →
git reset --hard(destroys uncommitted changes) - "Let me fix the merge conflict" →
git checkout -- .(discards all modifications) - "I'll clean up untracked files" →
git clean -fd(permanently deletes untracked files)
DCG intercepts dangerous commands before execution and blocks them with a clear explanation, giving you a chance to stash your changes first.
Critical Design Principles
1. Whitelist-First Architecture
Safe patterns are checked before destructive patterns. This ensures explicitly safe commands are never accidentally blocked:
git checkout -b feature → Matches SAFE "checkout-new-branch" → ALLOW
git checkout -- file.txt → No safe match, matches DESTRUCTIVE → DENY
2. Fail-Safe Defaults (Default-Allow)
Unrecognized commands are allowed by default. This ensures:
- The hook never breaks legitimate workflows
- Only known dangerous patterns are blocked
- New git commands work until explicitly categorized
3. Zero False Negatives Philosophy
The pattern set prioritizes never allowing dangerous commands over avoiding false positives. A few extra prompts for manual confirmation are acceptable; lost work is not.
What It Blocks
Git Commands That Destroy Uncommitted Work
| Command | Reason | |---------|--------| | git reset --hard | Destroys uncommitted changes | | git reset --merge | Destroys uncommitted changes | | git checkout -- <file> | Discards file modifications | | git restore <file> (without --staged) | Discards uncommitted changes | | git clean -f | Permanently deletes untracked files |
Git Commands That Destroy Remote History
| Command | Reason | |---------|--------| | git push --force / -f | Overwrites remote commits | | git branch -D | Force-deletes without merge check |
Git Commands That Destroy Stashed Work
| Command | Reason | |---------|--------| | git stash drop | Permanently deletes a stash | | git stash clear | Permanently deletes all stashes |
Filesystem Commands
| Command | Reason | |---------|--------| | rm -rf (outside /tmp, /var/tmp, $TMPDIR) | Recursive deletion is dangerous |
What It ALLOWS
Safe operations pass through silently:
Always Safe Git Operations
git status, git log, git diff, git add, git commit, git push, git pull, git fetch, git branch -d (safe delete with merge check), git stash, git stash pop, git stash list
Explicitly Safe Patterns
| Pattern | Why Safe | |---------|----------| | git checkout -b <branch> | Creating new branches | | git checkout --orphan <branch> | Creating orphan branches | | git restore --staged <file> | Unstaging only, doesn't touch working tree | | git restore -S <file> | Short flag for staged | | git clean -n / --dry-run | Preview mode, no actual deletion | | rm -rf /tmp/ | Temp directories are ephemeral | | rm -rf $TMPDIR/ | Shell variable forms |
Safe Alternative: --force-with-lease
git push --force-with-lease # ALLOWED - refuses if remote has unseen commits
git push --force # BLOCKED - can overwrite others' work
Modular Pack System
DCG uses a modular "pack" system to organize patterns by category:
Core Packs (Always Enabled)
| Pack | Description | |------|-------------| | core.git | Destructive git commands | | core.filesystem | Dangerous rm -rf outside temp |
Database Packs
| Pack | Description | |------|-------------| | database.postgresql | DROP/TRUNCATE in PostgreSQL | | database.mysql | DROP/TRUNCATE in MySQL/MariaDB | | database.mongodb | dropDatabase, drop() | | database.redis | FLUSHALL/FLUSHDB | | database.sqlite | DROP in SQLite |
Container Packs
| Pack | Description | |------|-------------| | containers.docker | docker system prune, docker rm -f | | containers.compose | docker-compose down --volumes | | containers.podman | podman system prune |
Kubernetes Packs
| Pack | Description | |------|-------------| | kubernetes.kubectl | kubectl delete namespace | | kubernetes.helm | helm uninstall | | kubernetes.kustomize | kustomize delete patterns |
Cloud Provider Packs
| Pack | Description | |------|-------------| | cloud.aws | Destructive AWS CLI commands | | cloud.gcp | Destructive gcloud commands | | cloud.azure | Destructive az commands |
Infrastructure Packs
| Pack | Description | |------|-------------| | infrastructure.terraform | terraform destroy | | infrastructure.ansible | Dangerous ansible patterns | | infrastructure.pulumi | pulumi destroy |
System Packs
| Pack | Description | |------|-------------| | system.disk | dd, mkfs, fdisk operations | | system.permissions | Dangerous chmod/chown patterns | | system.services | systemctl stop/disable patterns |
Other Packs
| Pack | Description | |------|-------------| | strict_git | Extra paranoid git protections | | package_managers | npm unpublish, cargo yank |
Configuring Packs
# ~/.config/dcg/config.toml
[packs]
enabled = [
"database.postgresql",
"containers.docker",
"kubernetes", # Enables all kubernetes sub-packs
]
Environment Variables
| Variable | Description | |----------|-------------| | DCG_PACKS="containers.docker,kubernetes" | Enable packs (comma-separated) | | DCG_DISABLE="kubernetes.helm" | Disable packs/sub-packs | | DCG_VERBOSE=1 | Verbose output | | DCG_COLOR=auto\|always\|never | Color mode | | DCG_BYPASS=1 | Bypass DCG entirely (escape hatch) |
Installation
Quick Install (Recommended)
curl -fsSL "https://raw.githubusercontent.com/Dicklesworthstone/destructive_command_guard/master/install.sh?$(date +%s)" | bash
# Easy mode: auto-update PATH
curl -fsSL "https://raw.githubusercontent.com/Dicklesworthstone/destructive_command_guard/master/install.sh?$(date +%s)" | bash -s -- --easy-mode
# System-wide (requires sudo)
curl -fsSL "https://raw.githubusercontent.com/Dicklesworthstone/destructive_command_guard/master/install.sh?$(date +%s)" | sudo bash -s -- --system
From Source (Requires Rust Nightly)
cargo +nightly install --git https://github.com/Dicklesworthstone/destructive_command_guard
Prebuilt Binaries
Available for: Linux x86_64, Linux ARM64, macOS Intel, macOS Apple Silicon, Windows
Claude Code Configuration
Add to ~/.claude/settings.json:
{
"hooks": {
"PreToolUse": [
{
"matcher": "Bash",
"hooks": [
{
"type": "command",
"command": "dcg"
}
]
}
]
}
}
Important: Restart Claude Code after adding the hook.
How It Works
Processing Pipeline
┌─────────────────────────────────────────────────────────────────┐
│ Claude Code │
│ Agent executes `rm -rf ./build` │
└─────────────────────┬───────────────────────────────────────────┘
│
▼ PreToolUse hook (stdin: JSON)
┌─────────────────────────────────────────────────────────────────┐
│ dcg │
│ ┌──────────────┐ ┌──────────────┐ ┌──────────────┐ │
│ │ Parse │───▶│ Normalize │───▶│ Quick Reject │ │
│ │ JSON │ │ Command │ │ Filter │ │
│ └──────────────┘ └──────────────┘ └──────┬───────┘ │
│ │