214 lines
5.8 KiB
Markdown
214 lines
5.8 KiB
Markdown
# 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**:
|
|
```bash
|
|
nano hooks/command-validator.js
|
|
```
|
|
|
|
2. **Find the dangerousPatterns array** (around line 23):
|
|
```javascript
|
|
this.dangerousPatterns = [
|
|
/rm\s+-rf\s+\//, // Delete root
|
|
/mkfs\./, // Format filesystem
|
|
// Add your pattern here
|
|
];
|
|
```
|
|
|
|
3. **Add your pattern**:
|
|
```javascript
|
|
this.dangerousPatterns = [
|
|
/rm\s+-rf\s+\//, // Delete root
|
|
/mkfs\./, // Format filesystem
|
|
/docker\s+system\s+prune\s+--all/, // Delete all Docker data
|
|
/kubectl\s+delete\s+namespace\s+production/, // Delete prod namespace
|
|
];
|
|
```
|
|
|
|
4. **Test your pattern**:
|
|
```bash
|
|
echo '{"tool": "Bash", "parameters": {"command": "docker system prune --all"}}' | node hooks/command-validator.js
|
|
```
|
|
|
|
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 suspiciousPatterns array**:
|
|
```javascript
|
|
this.suspiciousPatterns = [
|
|
/sudo\s+rm/, // Sudo with rm
|
|
/chmod\s+777/, // Overly permissive
|
|
// Add your pattern here
|
|
];
|
|
```
|
|
|
|
2. **Add patterns that should warn but not block**:
|
|
```javascript
|
|
this.suspiciousPatterns = [
|
|
/sudo\s+rm/, // Sudo with rm
|
|
/chmod\s+777/, // Overly permissive
|
|
/npm\s+install\s+.*--global/, // Global npm installs
|
|
/pip\s+install.*--user/, // User pip installs
|
|
];
|
|
```
|
|
|
|
## Customize for Your Tech Stack
|
|
|
|
### For Docker Environments
|
|
|
|
Add Docker-specific protections:
|
|
```javascript
|
|
// In dangerousPatterns:
|
|
/docker\s+rm\s+.*-f.*/, // Force remove containers
|
|
/docker\s+rmi\s+.*-f.*/, // Force remove images
|
|
|
|
// In suspiciousPatterns:
|
|
/docker\s+run.*--privileged/, // Privileged containers
|
|
/docker.*-v\s+\/:\/.*/, // Mount root filesystem
|
|
```
|
|
|
|
### For Kubernetes
|
|
|
|
Protect production namespaces:
|
|
```javascript
|
|
// In dangerousPatterns:
|
|
/kubectl\s+delete\s+.*production.*/,
|
|
/kubectl\s+delete\s+.*prod.*/,
|
|
/helm\s+delete\s+.*production.*/,
|
|
|
|
// In suspiciousPatterns:
|
|
/kubectl\s+apply.*production.*/,
|
|
/kubectl.*--all-namespaces.*delete/,
|
|
```
|
|
|
|
### For Database Operations
|
|
|
|
Prevent destructive database commands:
|
|
```javascript
|
|
// In dangerousPatterns:
|
|
/DROP\s+DATABASE.*/i,
|
|
/TRUNCATE\s+TABLE.*/i,
|
|
/DELETE\s+FROM.*WHERE\s+1=1/i,
|
|
|
|
// In suspiciousPatterns:
|
|
/UPDATE.*SET.*WHERE\s+1=1/i,
|
|
/ALTER\s+TABLE.*DROP.*/i,
|
|
```
|
|
|
|
## Environment-Specific Patterns
|
|
|
|
### For Production Servers
|
|
|
|
```javascript
|
|
// In dangerousPatterns:
|
|
/systemctl\s+stop\s+(nginx|apache|mysql)/,
|
|
/service\s+(nginx|apache|mysql)\s+stop/,
|
|
/killall\s+-9.*/,
|
|
|
|
// In suspiciousPatterns:
|
|
/sudo\s+systemctl\s+restart.*/,
|
|
/sudo\s+service.*restart.*/,
|
|
```
|
|
|
|
### For Development Machines
|
|
|
|
```javascript
|
|
// In suspiciousPatterns:
|
|
/rm\s+-rf\s+node_modules/, // Can break local dev
|
|
/git\s+reset\s+--hard\s+HEAD~[0-9]+/, // Lose multiple commits
|
|
/git\s+push\s+.*--force.*/, // Force push
|
|
```
|
|
|
|
## Test Your Custom Patterns
|
|
|
|
Create a test script to verify your patterns work:
|
|
|
|
```bash
|
|
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"}}' | node hooks/command-validator.js
|
|
|
|
# Test suspicious pattern (should warn)
|
|
echo "Testing suspicious pattern..."
|
|
echo '{"tool": "Bash", "parameters": {"command": "npm install -g dangerous-package"}}' | node hooks/command-validator.js
|
|
|
|
# Test normal command (should pass)
|
|
echo "Testing normal command..."
|
|
echo '{"tool": "Bash", "parameters": {"command": "ls -la"}}' | node hooks/command-validator.js
|
|
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:
|
|
```javascript
|
|
validateCommandSafety(command) {
|
|
// Your existing patterns...
|
|
|
|
// Context-aware validation
|
|
if (command.toLowerCase().includes("git push")) {
|
|
// Check if we're in a production branch
|
|
try {
|
|
const { execSync } = require('child_process');
|
|
const currentBranch = execSync('git branch --show-current',
|
|
{ encoding: 'utf8' }).trim();
|
|
if (['main', 'master', 'production'].includes(currentBranch)) {
|
|
return {
|
|
allowed: true,
|
|
reason: "⚠️ Pushing to protected branch",
|
|
severity: "warning"
|
|
};
|
|
}
|
|
} catch {
|
|
// Ignore errors
|
|
}
|
|
}
|
|
}
|
|
```
|
|
|
|
## Pattern Syntax Reference
|
|
|
|
Use JavaScript 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
|
|
- `i` flag - Case insensitive matching
|
|
|
|
**Examples**:
|
|
- `/rm\s+-rf\s+\//` - Matches "rm -rf /"
|
|
- `/git\s+push.*--force/` - Matches "git push" followed by "--force" anywhere
|
|
- `/^sudo\s+/` - Matches commands starting with "sudo"
|
|
|
|
## Reload Changes
|
|
|
|
After modifying patterns:
|
|
|
|
1. **Test the changes**:
|
|
```bash
|
|
./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 |