Documentation

Hooks and Integrations

Claude Code

Agentinel integrates with Claude Code via its PreToolUse lifecycle hook, intercepting every Bash tool call that contains an npm install command before it executes.


How the hook works

Claude Code supports a hooks system defined in a hooks.json file placed in your project root. Hooks can run before or after specific tool calls. Agentinel registers as a PreToolUse hook scoped to the Bash tool.

When Claude attempts to run any Bash command, Claude Code passes the full command string to Agentinel's hook runner. If the command contains an npm install or npm i call, Agentinel extracts the package names, runs the OSV scan, and returns a decision.

Commands that do not contain an npm install are passed through immediately with zero overhead.

Generated hooks.json

Running npx asen init writes the following hooks.json to your project root:

hooks.json
{
  "hooks": {
    "PreToolUse": [
      {
        "matcher": "Bash",
        "hooks": [
          {
            "type": "command",
            "command": "npx agentinel-hook"
          }
        ]
      }
    ]
  }
}

What is npx agentinel-hook?

This is a thin binary shipped with the Agentinel package that reads the tool call payload from stdin, runs the scan, and writes the decision payload to stdout. Claude Code reads the stdout and decides whether to proceed.

What a block looks like in Claude Code

When Agentinel detects a malicious or hallucinated package, it returns the following structured payload to Claude Code via stdout:

JSON (hook response)
{
  "hookEvent": "PreToolUse",
  "action": "BLOCK",
  "reason": "agentinel blocked react-router-v7-beta: Package does not exist on npm (hallucination)."
}

Claude Code receives this payload and surfaces it to the user in its interface. The Bash command is not executed. Claude will typically respond by explaining that the package was blocked and suggesting alternatives.

Claude Code terminal
[agentinel] BLOCKED: react-router-v7-beta
Reason: Package does not exist on npm (hallucination).
The install command was not executed.

Claude: I was trying to install react-router-v7-beta but Agentinel blocked it
because this package does not exist. The correct package is react-router.

Warn mode payload

In warn mode, the action is WARN rather than BLOCK, and the install proceeds:

JSON (warn response)
{
  "hookEvent": "PreToolUse",
  "action": "WARN",
  "reason": "agentinel flagged some-new-package: Low download count (847). Proceeding."
}

Claude Code specific notes

  • The hooks.json file must be in the root of your project for Claude Code to detect it. Global hooks are not supported.
  • The hook runner must exit with code 0 for Claude Code to read its stdout. Agentinel always exits cleanly.
  • Claude Code passes the full Bash command string, not a parsed argument list. Agentinel uses regex to extract npm package names from the command.
  • Multi-package installs (e.g. npm install a b c) are fully supported; each package is scanned individually.

Other integrations