claude-hooks/docs/how-to/customize-patterns.md
Ryan Malloy 162ca67098 Initial commit: Claude Code Hooks with Diátaxis documentation
 Features:
- 🧠 Shadow learner that builds intelligence from command patterns
- 🛡️ Smart command validation with safety checks
- 💾 Automatic context monitoring and backup system
- 🔄 Session continuity across Claude restarts

📚 Documentation:
- Complete Diátaxis-organized documentation
- Learning-oriented tutorial for getting started
- Task-oriented how-to guides for specific problems
- Information-oriented reference for quick lookup
- Understanding-oriented explanations of architecture

🚀 Installation:
- One-command installation script
- Bootstrap prompt for installation via Claude
- Cross-platform compatibility
- Comprehensive testing suite

🎯 Ready for real-world use and community feedback!

🤖 Generated with Claude Code

Co-Authored-By: Claude <noreply@anthropic.com>
2025-07-19 18:25:34 -06:00

5.7 KiB

How to Add Custom Command Validation Patterns

When to use this guide: You want to block specific commands or add warnings for commands that are problematic in your environment.

Add a Dangerous Command Pattern

If you have commands that should never be run in your environment:

  1. Edit the command validator:

    nano hooks/command_validator.py
    
  2. Find the dangerous_patterns list (around line 23):

    self.dangerous_patterns = [
        r'rm\s+-rf\s+/',           # Delete root
        r'mkfs\.',                 # Format filesystem  
        # Add your pattern here
    ]
    
  3. Add your pattern:

    self.dangerous_patterns = [
        r'rm\s+-rf\s+/',           # Delete root
        r'mkfs\.',                 # Format filesystem
        r'docker\s+system\s+prune\s+--all',  # Delete all Docker data
        r'kubectl\s+delete\s+namespace\s+production',  # Delete prod namespace
    ]
    
  4. Test your pattern:

    echo '{"tool": "Bash", "parameters": {"command": "docker system prune --all"}}' | python3 hooks/command_validator.py
    

    Should return: {"allow": false, "message": "⛔ Command blocked: Dangerous command pattern detected"}

Add Warning Patterns

For commands that are risky but sometimes legitimate:

  1. Find the suspicious_patterns list:

    self.suspicious_patterns = [
        r'sudo\s+rm',              # Sudo with rm
        r'chmod\s+777',            # Overly permissive
        # Add your pattern here
    ]
    
  2. Add patterns that should warn but not block:

    self.suspicious_patterns = [
        r'sudo\s+rm',              # Sudo with rm
        r'chmod\s+777',            # Overly permissive
        r'npm\s+install\s+.*--global',  # Global npm installs
        r'pip\s+install.*--user',       # User pip installs
    ]
    

Customize for Your Tech Stack

For Docker Environments

Add Docker-specific protections:

# In dangerous_patterns:
r'docker\s+rm\s+.*-f.*',      # Force remove containers
r'docker\s+rmi\s+.*-f.*',     # Force remove images

# In suspicious_patterns:  
r'docker\s+run.*--privileged',  # Privileged containers
r'docker.*-v\s+/:/.*',         # Mount root filesystem

For Kubernetes

Protect production namespaces:

# In dangerous_patterns:
r'kubectl\s+delete\s+.*production.*',
r'kubectl\s+delete\s+.*prod.*',
r'helm\s+delete\s+.*production.*',

# In suspicious_patterns:
r'kubectl\s+apply.*production.*',
r'kubectl.*--all-namespaces.*delete',

For Database Operations

Prevent destructive database commands:

# In dangerous_patterns:
r'DROP\s+DATABASE.*',
r'TRUNCATE\s+TABLE.*',
r'DELETE\s+FROM.*WHERE\s+1=1',

# In suspicious_patterns:
r'UPDATE.*SET.*WHERE\s+1=1',
r'ALTER\s+TABLE.*DROP.*',

Environment-Specific Patterns

For Production Servers

# In dangerous_patterns:
r'systemctl\s+stop\s+(nginx|apache|mysql)',
r'service\s+(nginx|apache|mysql)\s+stop',
r'killall\s+-9.*',

# In suspicious_patterns:
r'sudo\s+systemctl\s+restart.*',
r'sudo\s+service.*restart.*',

For Development Machines

# In suspicious_patterns:
r'rm\s+-rf\s+node_modules',    # Can break local dev
r'git\s+reset\s+--hard\s+HEAD~[0-9]+',  # Lose multiple commits
r'git\s+push\s+.*--force.*',   # Force push

Test Your Custom Patterns

Create a test script to verify your patterns work:

cat > test_patterns.sh << 'EOF'
#!/bin/bash

# Test dangerous pattern (should block)
echo "Testing dangerous pattern..."
echo '{"tool": "Bash", "parameters": {"command": "docker system prune --all"}}' | python3 hooks/command_validator.py

# Test suspicious pattern (should warn)  
echo "Testing suspicious pattern..."
echo '{"tool": "Bash", "parameters": {"command": "npm install -g dangerous-package"}}' | python3 hooks/command_validator.py

# Test normal command (should pass)
echo "Testing normal command..."
echo '{"tool": "Bash", "parameters": {"command": "ls -la"}}' | python3 hooks/command_validator.py
EOF

chmod +x test_patterns.sh
./test_patterns.sh

Advanced: Context-Aware Patterns

For patterns that depend on file context:

  1. Edit the validation function to check current directory or files:
    def validate_command_safety(self, command: str) -> ValidationResult:
        # Your existing patterns...
    
        # Context-aware validation
        if "git push" in command.lower():
            # Check if we're in a production branch
            try:
                current_branch = subprocess.check_output(['git', 'branch', '--show-current'], 
                                                        text=True).strip()
                if current_branch in ['main', 'master', 'production']:
                    return ValidationResult(
                        allowed=True,
                        reason="⚠️ Pushing to protected branch",
                        severity="warning"
                    )
            except:
                pass
    

Pattern Syntax Reference

Use Python regex patterns:

  • \s+ - One or more whitespace characters
  • .* - Any characters (greedy)
  • .*? - Any characters (non-greedy)
  • [0-9]+ - One or more digits
  • (option1|option2) - Either option1 or option2
  • ^ - Start of string
  • $ - End of string

Examples:

  • r'rm\s+-rf\s+/' - Matches "rm -rf /"
  • r'git\s+push.*--force' - Matches "git push" followed by "--force" anywhere
  • r'^sudo\s+' - Matches commands starting with "sudo"

Reload Changes

After modifying patterns:

  1. Test the changes:

    ./test_patterns.sh
    
  2. No restart needed - changes take effect immediately since hooks are called fresh each time

  3. Verify in Claude by trying a command that should trigger your new pattern