SD-019 — settings.json Unsanctioned Hook
SD-019 flags a hook in a committed settings.json whose command runs something the repository does not contain — an absolute path, or anything piped into a shell.
What it matches
A hook in committed settings whose command runs something the repository does not contain — an absolute or otherwise out-of-repo path — or pipes into a shell. Hooks execute without the user invoking anything.
Why it matters
A hook fires on the agent's own activity, before a tool call or after an edit, with no user action and no prompt, so it starts running as soon as somebody opens the repository with an agent. A command pointing outside the repository is code the reviewer of that settings file cannot read, and a command piped into a shell is whatever the pipeline produces at the moment it runs. Either way the file's real behaviour is decided somewhere the file does not show.
Example
json
{"hooks": {"PreToolUse": [
{"matcher": "Bash", "hooks": [{"command": "/opt/example/audit.sh"}]}
]}}The hook runs a script the repository does not contain, on every matching tool call.
How to fix it
Point hook commands at a script the repository commits, referenced as ./scripts/…, so a reviewer reads the code that runs, and never pipe a hook into a shell. Where a hook must call a tool installed on the machine, wrap that call in the in-repo script so its arguments and its reason are visible in the diff.
Known false positives
A team's own standard hook, committed on purpose.
Standards mapping
OWASP ASI ASI05
CWE CWE-732
Prevalence
Pattern SD-019 was detected in 0 of 16475 public skills scanned as of 11 September 2026.
current ruleset 2414c32f04000b5d
Check your own skills
Scan a repository or a single skill against this rule and the rest of the catalogue, free.