longline
A safety hook for Claude Code that parses Bash commands and enforces configurable security policies.
What it does
longline acts as a Claude Code PreToolUse hook. It intercepts Bash commands before execution, parses them using tree-sitter, evaluates them against YAML-defined safety rules, and returns allow/ask/deny decisions.
Key features:
- Structured parsing of pipelines, redirects, command substitutions, loops, conditionals, and compound statements
- Configurable safety levels (critical, high, strict)
- Optional AI evaluation for inline interpreter code
- 1000+ golden test cases for accuracy
- JSONL audit logging
- Fail-closed design: unknown/unparseable constructs default to
ask
Installation
# Build and install
# Copy rules
Configuration
Add to your Claude Code settings (~/.claude/settings.json):
Usage
longline reads hook JSON from stdin and outputs decisions to stdout:
# Test a command
|
# Inspect rules
# Check a specific command
# Show loaded rule files
Subcommand options
rules - display rule configuration:
check - test commands against rules:
Rules
Rules are defined in YAML with three matcher types:
- command: Match command name and arguments
- pipeline: Match command sequences (e.g.,
curl | sh) - redirect: Match output redirection targets
Example rule:
- id: rm-recursive-root
level: critical
match:
command: rm
flags:
any_of:
args:
any_of:
decision: deny
reason: "Recursive delete targeting root filesystem"
Rules organization
Rules can be split across multiple files using a manifest:
rules/
manifest.yaml # Top-level config, lists files to include
core-allowlist.yaml # Generic safe commands (ls, cat, grep...)
git.yaml # Git allowlist + destructive git rules
filesystem.yaml # Filesystem destruction rules
secrets.yaml # Secrets exposure rules
...
Use longline files --config rules/manifest.yaml to see loaded files.
Safety levels
- critical: Catastrophic operations (rm -rf /, dd to disk, etc.)
- high: Dangerous operations (secret access, network exfiltration)
- strict: Potentially risky operations requiring review
Decision model
allow: Command is safe, proceed without promptingask: Command requires user approvaldeny: Command is blocked (can be downgraded toaskwith--ask-on-deny)
AI Judge
For inline interpreter code (e.g., python -c "..."), longline can use AI to evaluate the embedded code instead of defaulting to ask.
Strict mode (--ask-ai): Conservative evaluation, flags potential dangers.
Lenient mode (--ask-ai-lenient or --lenient): Prefers allow for normal development tasks like file reading, Django template loading, and standard dev operations.
Supported bash constructs
The parser handles:
- Simple commands, pipelines (
|), lists (&&,||,;) - Subshells
(...), command substitutions$(...)and backticks - for/while loops, if/else, case statements
- Compound statements
{ ...; }, function definitions - Test commands
[[ ... ]], comments
All commands within these constructs are extracted and evaluated. Unknown or unparseable constructs become Opaque nodes and result in ask (fail-closed).
License
MIT