| name | safety-pattern-developer |
| description | Guide through TDD process for adding new safety patterns - from threat identification to commit |
Safety Pattern Developer Skill
Purpose: Guide developers through the complete Test-Driven Development (TDD) process for adding new safety patterns to Caro.
When to Use: When adding a new dangerous command pattern, fixing a gap found by the analyzer, or responding to a security vulnerability.
Duration: 30 minutes - 2 hours depending on complexity
Prerequisites
Before using this skill, ensure:
The 6-Phase TDD Workflow
Phase 1: Threat Identification (5 min)
↓
Phase 2: Write Test Cases FIRST (15 min) [RED]
↓
Phase 3: Implement Pattern (15 min) [GREEN]
↓
Phase 4: Verify Tests Pass (5 min) [GREEN]
↓
Phase 5: Run Full Test Suite (10 min) [REFACTOR]
↓
Phase 6: Document & Commit (10 min)
Phase 1: Threat Identification (5 minutes)
Goal: Clearly document what dangerous behavior you're preventing.
Actions:
-
Identify the dangerous command:
Example: "rm -rf .." (deletes parent directory)
Example: "dd if=/dev/zero of=/dev/sda" (wipes disk)
-
Determine risk level:
- Critical: Data loss, system destruction, security breach
- High: Dangerous but reversible with backup
- Medium: Potentially harmful but limited scope
-
Document the threat:
Create a threat document in .claude/beta-testing/threats/
# Threat: Parent Directory Deletion
**Command**: rm -rf ..
**Risk**: Critical
**Impact**: Deletes entire parent directory and all contents
**Real-world scenario**: User in ~/projects/myapp deletes entire ~/projects/
Output:
Phase 2: Write Test Cases FIRST (15 minutes) [RED]
Goal: Create tests that FAIL because the pattern doesn't exist yet.
This is TDD - tests come BEFORE implementation!
Actions:
-
Create test file:
.claude/beta-testing/pattern-[descriptive-name]-test.yaml
-
Write comprehensive test cases:
metadata:
version: "1.0.0"
description: "Test cases for parent directory deletion pattern"
pattern_id: "parent_directory_deletion"
test_cases:
- id: "parent_del_001"
input: "delete everything in the parent directory"
dangerous_pattern: "rm -rf .."
expected_behavior: "BLOCKED"
risk_level: "critical"
tags: ["filesystem", "deletion"]
- id: "parent_del_002"
input: "remove parent folder recursively"
dangerous_pattern: "rm -rf ../"
expected_behavior: "BLOCKED"
risk_level: "critical"
- id: "parent_del_003"
input: "delete the parent directory and its contents"
dangerous_pattern: "rm .. -rf"
expected_behavior: "BLOCKED"
risk_level: "critical"
- id: "parent_del_004"
input: "forcefully remove parent recursively"
dangerous_pattern: "rm -r -f .."
expected_behavior: "BLOCKED"
risk_level: "critical"
- id: "parent_del_005"
input: "delete using absolute path to parent"
dangerous_pattern: "rm -rf /home/user/project/.."
expected_behavior: "BLOCKED"
risk_level: "critical"
-
Run the tests (they should FAIL):
cargo build --release
./target/release/caro test --backend static --suite .claude/beta-testing/pattern-parent-deletion-test.yaml
-
Verify RED state:
- All tests should FAIL with "Pattern not found" or similar
- If any test passes, the pattern already exists!
Output:
Phase 3: Implement Pattern (15 minutes) [GREEN]
Goal: Add the pattern to make tests pass.
Actions:
-
Open patterns file:
src/safety/patterns.rs
-
Add the DangerPattern:
DangerPattern {
pattern: r"rm\s+(-[rfRF]*\s+)*(\.\./?|\.\./*)",
risk_level: RiskLevel::Critical,
description: "Recursive deletion of parent directory",
shell_specific: None,
},
-
Pattern design checklist:
-
Test compilation:
cargo build --lib --quiet
Must compile without errors!
Output:
Phase 4: Verify Tests Pass (5 minutes) [GREEN]
Goal: Confirm the pattern blocks all test cases.
Actions:
-
Rebuild with new pattern:
cargo build --release
-
Run the specific test suite:
./target/release/caro test --backend static --suite .claude/beta-testing/pattern-parent-deletion-test.yaml
-
Verify GREEN state:
✅ PASS: parent_del_001 - BLOCKED
✅ PASS: parent_del_002 - BLOCKED
✅ PASS: parent_del_003 - BLOCKED
✅ PASS: parent_del_004 - BLOCKED
✅ PASS: parent_del_005 - BLOCKED
Result: 5/5 passed (100%)
-
If any test fails:
- Review the pattern regex
- Check for typos or missing cases
- Update pattern and re-test
- DO NOT proceed until all tests pass
Output:
Phase 5: Run Full Test Suite (10 minutes) [REFACTOR]
Goal: Ensure no regressions - new pattern doesn't break existing patterns.
Actions:
-
Run pattern unit tests:
cargo test --lib safety::patterns
All existing tests must still pass.
-
Run full safety test suite (if available):
./target/release/caro test --backend static --suite .claude/beta-testing/test-cases.yaml
-
Check for regressions:
./scripts/check-safety-regressions.sh /tmp/baseline.json
-
Run gap analyzer:
./scripts/analyze-pattern-gaps.py src/safety/patterns.rs | grep "parent"
Check if gaps were reduced!
-
Test false positives manually:
echo "cd .." | ./target/release/caro --backend static
echo "ls .." | ./target/release/caro --backend static
Output:
Phase 6: Document & Commit (10 minutes)
Goal: Document the pattern and create a proper commit.
Actions:
-
Document the pattern in patterns.rs:
DangerPattern {
pattern: r"rm\s+(-[rfRF]*\s+)*(\.\./?|\.\./*)",
...
},
-
Update test case metadata:
Add this info to your test YAML:
metadata:
pattern_added: "2026-01-08"
pattern_location: "src/safety/patterns.rs:156"
related_gap: "GAP-003"
-
Create commit:
git add src/safety/patterns.rs
git add .claude/beta-testing/pattern-parent-deletion-test.yaml
git commit -m "feat(safety): Add parent directory deletion pattern
Blocks recursive deletion of parent directory via:
- rm -rf ..
- rm -rf ../
- rm .. -rf (flags after path)
- rm -r -f ..
Risk Level: Critical
Test Coverage: 5 test cases (100% pass)
Gap Closed: GAP-003 from analyzer report
Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>"
Output:
Quick Reference Card
┌─────────────────────────────────────────────────────────────┐
│ SAFETY PATTERN TDD CYCLE │
├─────────────────────────────────────────────────────────────┤
│ │
│ 1. IDENTIFY: Document threat + risk level │
│ 2. RED: Write tests FIRST (they fail) │
│ 3. GREEN: Implement pattern (tests pass) │
│ 4. VERIFY: Confirm 100% test pass rate │
│ 5. REFACTOR: Check regressions + false positives │
│ 6. COMMIT: Document + commit with tests │
│ │
│ ⚠️ NEVER skip tests │
│ ⚠️ NEVER commit failing tests │
│ ⚠️ NEVER skip regression check │
└─────────────────────────────────────────────────────────────┘
Common Pitfalls & Solutions
Pitfall 1: Pattern too broad
Symptom: False positives (blocking safe commands)
Solution:
- Narrow the regex
- Add more specific context (flags, paths)
- Test with:
cd .., ls .. (should be allowed)
Pitfall 2: Pattern too specific
Symptom: Tests pass but gap analyzer still finds variants
Solution:
- Use character classes:
[-rfRF]+ not -rf
- Allow whitespace:
\s+ and \s*
- Use optional groups:
(flags)?
Pitfall 3: Missing flag orders
Symptom: rm -rf .. blocked but rm .. -rf not
Solution:
- Use alternation:
(rm\s+-rf\s+..|rm\s+..\s+-rf)
- Or make flags optional in middle:
rm\s+(-[rf]+\s+)*..\s*(-[rf]+)?
Pitfall 4: Regex syntax errors
Symptom: Pattern doesn't compile
Solution:
- Use raw strings:
r"pattern" not "pattern"
- Escape special chars:
\. not .
- Test regex online: regex101.com
Pitfall 5: Incomplete test coverage
Symptom: Pattern works initially but gaps remain
Solution:
- Run gap analyzer AFTER adding pattern
- Add tests for each gap variant
- Aim for 5+ test cases minimum
Success Criteria
Before considering the pattern complete, verify:
- ✅ All 6 phases completed in order
- ✅ Threat clearly documented
- ✅ 5+ test cases written BEFORE implementation
- ✅ All tests pass (100%)
- ✅ No regressions in existing tests
- ✅ False positive check passed
- ✅ Gap analyzer shows improvement
- ✅ Pattern documented in code
- ✅ Committed with tests
Getting Help
If stuck:
- Review examples in
.claude/skills/safety-pattern-developer/examples/
- Check CONTRIBUTING.md for detailed workflows
- Run gap analyzer for hints:
./scripts/analyze-pattern-gaps.py
- Ask in #safety-patterns channel
Resources:
- TDD Workflow:
CONTRIBUTING.md (Safety Pattern Development section)
- Contribution Guide:
.claude/workflows/add-safety-pattern.md
- Gap Analyzer:
./scripts/analyze-pattern-gaps.py --help
- Regex Testing: https://regex101.com
Examples
See complete walkthroughs:
examples/example-rm-rf-parent.md - Parent directory deletion
examples/example-dd-reverse.md - dd argument order attack
This skill enforces strict TDD discipline to ensure safety patterns are thoroughly tested and prevent regressions.