enhance-hooks
Use when reviewing hooks for safety, timeouts, and correct frontmatter.
Best use case
enhance-hooks is best used when you need a repeatable AI agent workflow instead of a one-off prompt.
Use when reviewing hooks for safety, timeouts, and correct frontmatter.
Teams using enhance-hooks should expect a more consistent output, faster repeated execution, less prompt rewriting.
When to use this skill
- You want a reusable workflow that can be run more than once with consistent structure.
When not to use this skill
- You only need a quick one-off answer and do not need a reusable workflow.
- You cannot install or maintain the underlying files, dependencies, or repository context.
Installation
Claude Code / Cursor / Codex
Manual Installation
- Download SKILL.md from GitHub
- Place it in
.claude/skills/enhance-hooks/SKILL.mdinside your project - Restart your AI agent — it will auto-discover the skill
How enhance-hooks Compares
| Feature / Agent | enhance-hooks | Standard Approach |
|---|---|---|
| Platform Support | Not specified | Limited / Varies |
| Context Awareness | High | Baseline |
| Installation Complexity | Unknown | N/A |
Frequently Asked Questions
What does this skill do?
Use when reviewing hooks for safety, timeouts, and correct frontmatter.
Where can I find the source code?
You can find the source code on GitHub using the link provided at the top of the page.
SKILL.md Source
# enhance-hooks
Analyze hook definitions and scripts for safety, correctness, and best practices.
## Parse Arguments
```javascript
const args = '$ARGUMENTS'.split(' ').filter(Boolean);
const targetPath = args.find(a => !a.startsWith('--')) || '.';
const fix = args.includes('--fix');
```
## Workflow
1. **Discover** - Find hook files (.md, .sh, .json)
2. **Classify** - Identify hook type and event
3. **Parse** - Extract frontmatter and script content
4. **Check** - Run all pattern checks against knowledge below
5. **Filter** - Apply certainty filtering
6. **Report** - Generate markdown output
7. **Fix** - Apply auto-fixes if --fix flag present
---
## Hook Knowledge Reference
### What Are Hooks
Hooks are automated actions triggered at specific points in a Claude Code session. They enable validation, monitoring, and control of Claude's actions through bash commands or LLM-based evaluation.
### Hook Lifecycle (Complete Reference)
Hooks fire in this sequence:
| Order | Event | Description | Matcher Required |
|-------|-------|-------------|------------------|
| 1 | `SessionStart` | Session begins or resumes | No |
| 2 | `UserPromptSubmit` | User submits a prompt | No |
| 3 | `PreToolUse` | Before tool execution (can modify/block) | Yes |
| 4 | `PermissionRequest` | When permission dialog appears | Yes |
| 5 | `PostToolUse` | After tool succeeds | Yes |
| 6 | `SubagentStart` | When spawning a subagent | No |
| 7 | `SubagentStop` | When subagent finishes | No |
| 8 | `Stop` | Claude finishes responding | No |
| 9 | `PreCompact` | Before context compaction | No |
| 10 | `SessionEnd` | Session terminates | No |
| 11 | `Notification` | Claude Code sends notifications | No |
### Hook Types
**Command Hooks** (`type: "command"`):
- Execute bash commands with full stdin/stdout control
- Available for all events
**Prompt Hooks** (`type: "prompt"`):
- Use LLM evaluation for intelligent, context-aware decisions
- **Only supported for `Stop` and `SubagentStop` events**
### Configuration Locations
| File | Location | Scope | Committed |
|------|----------|-------|-----------|
| User settings | `~/.claude/settings.json` | All projects | No |
| Project settings | `.claude/settings.json` | Current project | Yes |
| Local settings | `.claude/settings.local.json` | Current project | No |
### Configuration Structure
```json
{
"hooks": {
"PreToolUse": [
{
"matcher": "Bash",
"hooks": [
{
"type": "command",
"command": ".claude/hooks/validate-bash.sh",
"timeout": 30
}
]
}
],
"PostToolUse": [
{
"matcher": "Write|Edit",
"hooks": [
{
"type": "command",
"command": "$CLAUDE_PROJECT_DIR/.claude/hooks/format-code.sh"
}
]
}
],
"Stop": [
{
"hooks": [
{
"type": "prompt",
"prompt": "Check if all requested tasks are complete.",
"timeout": 30
}
]
}
]
}
}
```
### Matcher Syntax
| Pattern | Description |
|---------|-------------|
| `Write` | Match exact tool name |
| `Edit\|Write` | Match multiple tools (regex OR) |
| `Notebook.*` | Regex pattern matching |
| `*` or `""` | Match all tools |
| (omitted) | Required for Stop, SubagentStop, UserPromptSubmit |
### Input Schema (JSON via stdin)
All hooks receive this JSON structure:
```json
{
"session_id": "abc123",
"transcript_path": "/path/to/transcript",
"cwd": "/project/root",
"permission_mode": "default",
"hook_event_name": "PreToolUse",
"tool_name": "Bash",
"tool_input": {
"command": "npm test",
"description": "Run test suite"
}
}
```
### Exit Codes
| Exit Code | Behavior |
|-----------|----------|
| 0 | Success - stdout shown to user or added as context |
| 2 | Blocking error - stderr shown, action blocked |
| Other | Non-blocking error - stderr shown in verbose mode |
### Output Schemas
**PreToolUse Decision Control:**
```json
{
"hookSpecificOutput": {
"hookEventName": "PreToolUse",
"permissionDecision": "allow|deny|ask",
"permissionDecisionReason": "Reason for decision",
"updatedInput": {
"command": "modified command"
},
"additionalContext": "Context for Claude"
}
}
```
**Stop/SubagentStop Control:**
```json
{
"decision": "block",
"reason": "Tasks incomplete: missing test coverage"
}
```
### Environment Variables
| Variable | Description | Available In |
|----------|-------------|--------------|
| `CLAUDE_PROJECT_DIR` | Absolute path to project root | All hooks |
| `CLAUDE_CODE_REMOTE` | "true" if remote session | All hooks |
| `CLAUDE_ENV_FILE` | Path to persist env vars | SessionStart only |
| `CLAUDE_FILE_PATHS` | Space-separated file paths | PostToolUse (Write/Edit) |
### Practical Hook Examples
**Security Firewall (PreToolUse):**
```bash
#!/usr/bin/env bash
set -euo pipefail
cmd=$(jq -r '.tool_input.command // ""')
# Block dangerous patterns
if echo "$cmd" | grep -qE 'rm -rf|git reset --hard|curl.*\|.*sh'; then
echo '{"decision": "block", "reason": "Dangerous command blocked"}' >&2
exit 2
fi
exit 0
```
**Auto-Formatter (PostToolUse):**
```bash
#!/usr/bin/env bash
set -euo pipefail
files=$(jq -r '.tool_input.file_path // ""')
for file in $files; do
case "$file" in
*.py) black "$file" 2>/dev/null || true ;;
*.js|*.ts) prettier --write "$file" 2>/dev/null || true ;;
esac
done
exit 0
```
**Command Logger (PreToolUse):**
```bash
#!/usr/bin/env bash
set -euo pipefail
cmd=$(jq -r '.tool_input.command // ""')
printf '%s %s\n' "$(date -Is)" "$cmd" >> .claude/bash-commands.log
exit 0
```
**Workflow Orchestration (SubagentStop - prompt type):**
```json
{
"hooks": {
"SubagentStop": [
{
"hooks": [
{
"type": "prompt",
"prompt": "Review the subagent's work. Did it complete all tasks?"
}
]
}
]
}
}
```
---
## Detection Patterns
### 1. Frontmatter Validation (HIGH Certainty)
**Required:**
- YAML frontmatter with `---` delimiters
- `name` field in frontmatter
- `description` field in frontmatter
**Recommended:**
- `timeout` for command hooks (default: 30s)
- Hook type specification
**Flag:**
- Missing frontmatter delimiters
- Missing name or description
### 2. Script Safety (HIGH Certainty)
**Required Safety Patterns:**
- `set -euo pipefail` at script start
- Error handling for jq/JSON parsing
- Proper quoting of variables
**Dangerous Patterns to Flag:**
| Pattern | Risk | Certainty |
|---------|------|-----------|
| `rm -rf` | Destructive without confirmation | HIGH |
| `git reset --hard` | Data loss risk | HIGH |
| `curl \| sh` | Remote code execution | HIGH |
| `eval "$input"` | Arbitrary code execution | HIGH |
| `rm -r` | Recursive delete (may be intentional) | MEDIUM |
| `git push --force` | Force push (may be intentional) | MEDIUM |
### 3. Exit Code Handling (HIGH Certainty)
**Check:** Scripts use correct exit codes
**Flag:**
- Missing `exit 0` for success path
- Using exit code 1 for blocking (should be 2)
- No exit code at end of script
### 4. Hook Type Appropriateness (HIGH Certainty)
**Check:** Hook type matches event
**Flag:**
- Prompt hooks used for events other than Stop/SubagentStop
- Missing type specification
### 5. Lifecycle Event Appropriateness (MEDIUM Certainty)
| Event | Appropriate Use Cases |
|-------|----------------------|
| `PreToolUse` | Security validation, command blocking, input modification |
| `PostToolUse` | Formatting, logging, notifications |
| `Stop` | Completion checks, cleanup, summary |
| `SubagentStop` | Workflow orchestration, result validation |
| `SessionStart` | Environment setup, initialization |
**Flag:**
- PostToolUse hooks trying to block actions (too late)
- PreToolUse hooks doing heavy processing (should be fast)
- Prompt hooks on unsupported events
### 6. Timeout Configuration (MEDIUM Certainty)
**Guidelines:**
- Default: 30 seconds for command hooks
- Network operations: Always set explicit timeout
- External service calls: Set timeout based on expected latency
**Flag:**
- No timeout for network operations
- Timeout missing for external service calls
- Unreasonably long timeouts (>60s without justification)
### 7. Output Format (MEDIUM Certainty)
**PreToolUse Output Fields:**
- `permissionDecision`: allow, deny, or ask
- `permissionDecisionReason`: Explanation for decision
- `updatedInput`: Modified tool input (optional)
- `additionalContext`: Context for Claude (optional)
**Flag:**
- Invalid permissionDecision values
- Missing reason for deny decisions
- Malformed JSON output
### 8. Matcher Patterns (MEDIUM Certainty)
**Check:** Matcher syntax is valid
**Flag:**
- Invalid regex patterns
- Too broad matchers (`*` without justification)
- Matcher on events that don't support it (Stop, SubagentStop)
### 9. Anti-Patterns (LOW Certainty)
- Complex logic in hooks (should be simple and fast)
- Missing documentation/comments
- Hardcoded paths (should use `$CLAUDE_PROJECT_DIR`)
- Network calls without error handling
- Secrets/credentials in hook scripts
---
## Auto-Fix Implementations
### 1. Missing safety header
```bash
#!/usr/bin/env bash
set -euo pipefail
```
### 2. Missing exit code
Add `exit 0` at end of script
### 3. Missing frontmatter fields
```yaml
---
name: hook-name
description: Hook description
timeout: 30
---
```
### 4. Wrong blocking exit code
Replace `exit 1` with `exit 2` for blocking errors
---
## Output Format
```markdown
## Hook Analysis: {hook-name}
**File**: {path}
**Type**: {command|prompt|config}
**Event**: {PreToolUse|PostToolUse|Stop|...}
### Summary
- HIGH: {count} issues
- MEDIUM: {count} issues
### Frontmatter Issues ({n})
| Issue | Fix | Certainty |
### Safety Issues ({n})
| Issue | Fix | Certainty |
### Exit Code Issues ({n})
| Issue | Fix | Certainty |
### Lifecycle Issues ({n})
| Issue | Fix | Certainty |
### Output Format Issues ({n})
| Issue | Fix | Certainty |
```
---
## Pattern Statistics
| Category | Patterns | Auto-Fixable |
|----------|----------|--------------|
| Frontmatter | 3 | 2 |
| Safety | 6 | 2 |
| Exit Code | 3 | 2 |
| Hook Type | 2 | 0 |
| Lifecycle | 5 | 0 |
| Timeout | 3 | 0 |
| Output | 3 | 0 |
| Matcher | 3 | 0 |
| Anti-Pattern | 5 | 0 |
| **Total** | **33** | **6** |
---
<examples>
### Example: Missing Safety Header
<bad_example>
```bash
#!/usr/bin/env bash
cmd=$(jq -r '.tool_input.command // ""')
```
**Why it's bad**: Missing `set -euo pipefail` means errors may silently pass.
</bad_example>
<good_example>
```bash
#!/usr/bin/env bash
set -euo pipefail
cmd=$(jq -r '.tool_input.command // ""')
```
**Why it's good**: Fails fast on errors, unset variables, and pipe failures.
</good_example>
### Example: Wrong Exit Code for Blocking
<bad_example>
```bash
if [[ "$cmd" == *"rm -rf"* ]]; then
echo "Blocked dangerous command" >&2
exit 1 # Wrong!
fi
```
**Why it's bad**: Exit code 1 is non-blocking. Action will still proceed.
</bad_example>
<good_example>
```bash
if [[ "$cmd" == *"rm -rf"* ]]; then
echo '{"decision": "block", "reason": "Dangerous command"}' >&2
exit 2 # Correct blocking exit code
fi
```
**Why it's good**: Exit code 2 blocks the action. JSON output provides context.
</good_example>
### Example: Prompt Hook on Wrong Event
<bad_example>
```json
{
"hooks": {
"PreToolUse": [
{
"hooks": [{ "type": "prompt", "prompt": "Is this safe?" }]
}
]
}
}
```
**Why it's bad**: Prompt hooks only work for Stop and SubagentStop events.
</bad_example>
<good_example>
```json
{
"hooks": {
"PreToolUse": [
{
"hooks": [{ "type": "command", "command": "./validate.sh" }]
}
]
}
}
```
**Why it's good**: Command hooks work for all events.
</good_example>
### Example: Dangerous Command Pattern
<bad_example>
```bash
if echo "$cmd" | grep -q 'rm'; then
exit 2
fi
```
**Why it's bad**: Too broad - blocks legitimate `rm file.tmp`.
</bad_example>
<good_example>
```bash
if echo "$cmd" | grep -qE 'rm\s+(-rf|-fr)\s+/'; then
exit 2
fi
```
**Why it's good**: Specific pattern targets actual dangerous commands.
</good_example>
### Example: Hardcoded Path
<bad_example>
```bash
log_file="/home/user/project/.claude/commands.log"
```
**Why it's bad**: Hardcoded path breaks on other machines.
</bad_example>
<good_example>
```bash
log_file="$CLAUDE_PROJECT_DIR/.claude/commands.log"
```
**Why it's good**: Uses environment variable for portability.
</good_example>
</examples>
---
## Constraints
- Only apply auto-fixes for HIGH certainty issues
- Be cautious about security patterns - false negatives worse than false positives
- Never remove content, only suggest improvements
- Validate against embedded knowledge reference aboveRelated Skills
enhance-cross-file
Use when checking cross-file consistency: tools vs frontmatter, agent references, duplicate rules, contradictions.
enhance-prompts
Use when improving general prompts for structure, examples, and constraints.
enhance-skills
Use when reviewing SKILL.md files for structure and trigger quality.
enhance-claude-memory
Use when improving CLAUDE.md or AGENTS.md project memory files.
enhance-agent-prompts
Use when improving agent prompts, frontmatter, and tool restrictions.
enhance-docs
Use when improving documentation structure, accuracy, and RAG readiness.
enhance-orchestrator
Use when coordinating multiple enhancers for /enhance command. Runs analyzers in parallel and produces unified report.
enhance-plugins
Use when analyzing plugin structures, MCP tools, and plugin security patterns.
validate-delivery
Use when user asks to "validate delivery", "check readiness", or "verify completion". Runs tests, build, and requirement checks with pass/fail instructions.
repo-intel
Use when user asks to "run repo intel", "generate repo map", "analyze repo", "query hotspots", "check ownership", or "bus factor". Unified static analysis - git history, AST symbols, project metadata.
perf-analyzer
Use when synthesizing perf findings into evidence-backed recommendations and decisions.
discover-tasks
Use when user asks to "discover tasks", "find next task", "prioritize issues", "what should I work on", or "list open issues". Discovers and ranks tasks from GitHub, GitLab, local files, and custom sources.