---
description: Claude Code hooks can block risky tool calls and prompts on each machine. See which governance controls hooks handle and where gateway policy takes over.
title: Claude Code Hooks for Governance and Gateway Policy
image: https://storage.ghost.io/c/84/03/8403f2f6-141c-411a-8f55-a32d4291533e/content/images/size/w1200/2026/10/claude-code-hooks-for-governance-and-gateway-policy-bifrost-1920x1080.png
---

Try Bifrost Enterprise free for 14 days. [Request access](https://www.getmaxim.ai/#enterprise-trial)

**TL;DR**

- Claude Code hooks run shell commands, HTTP endpoints, MCP tools, or model prompts at lifecycle events such as `PreToolUse` and `UserPromptSubmit`, and they can block the action before it happens.
- A `PreToolUse` hook that returns `deny` stops a tool call before it executes, which makes hooks the right control for local actions like shell commands and file edits.
- Managed settings with `allowManagedHooksOnly` lock hooks organization-wide, but hooks still only see one session on one machine and cannot enforce budgets, team-wide model access, or cross-team audit.
- Gateway policy takes over for anything that crosses the network: identity, spend, model allow-lists, MCP tool access, guardrails, and request logs.
- Bifrost pairs with Claude Code through `ANTHROPIC_BASE_URL`, and a pinned managed setting can make Bifrost the only endpoint Claude Code may reach.

Claude Code hooks are user-defined handlers that execute automatically at specific points in a Claude Code session, and they are the most direct way to stop an agent from running a command, editing a file, or sending a prompt it should not. They govern what happens on the developer's machine; they do not govern spend, model access, or audit across a team. [Bifrost](https://www.getmaxim.ai/bifrost), the [open-source AI gateway that Claude Code can route through](https://github.com/maximhq/bifrost), enforces those organization-wide controls on every request Claude Code sends. This guide covers which Claude Code hooks matter for governance, how to lock them down, and where gateway policy takes over.

## What Are Claude Code Hooks?

Claude Code hooks are configured handlers (shell commands, HTTP endpoints, MCP tool calls, single-turn model prompts, or subagents) that fire at defined lifecycle events and can inspect, modify, allow, or block what happens next. They are defined in JSON settings files and apply in the terminal, IDE extensions, the desktop app, and cloud sessions.

Each hook has three levels, as Anthropic's [hooks reference](https://code.claude.com/docs/en/hooks) describes: a hook event (such as `PreToolUse`), a matcher group that filters when it fires (such as "only for the Bash tool"), and one or more hook handlers that run when matched. Handlers receive the event as JSON on stdin (or as a POST body for HTTP hooks) and answer with an exit code or a JSON decision.

Hooks can live in user settings, project settings, local settings, managed policy settings, plugins, skills, and subagent definitions. That flexibility is useful for developers and a risk for governance, since anyone who can edit one of those files can add or remove a hook. The broader view of [Claude Code governance for securing agent access](https://www.getmaxim.ai/articles/claude-code-governance-securing-agent-access-with-an-ai-gateway/) starts from the same split between local and network controls.

## Claude Code Hook Events That Matter for Governance

Of the more than 30 Claude Code hook events, a handful carry most of the governance load: `PreToolUse` and `PermissionRequest` for actions, `UserPromptSubmit` for prompts, `ConfigChange` for settings tampering, and `PostToolUse` plus `SessionEnd` for local audit. Each event differs in whether it can block.

| Hook event | Fires when | Can block? | Governance use |
| --- | --- | --- | --- |
| `PreToolUse` | Before any tool call | Yes | Deny destructive commands, protected paths, unapproved MCP tools |
| `PermissionRequest` | When a permission prompt would appear | Yes, through the decision object | Auto-deny categories of requests, route approvals to policy |
| `UserPromptSubmit` | Before a prompt reaches Claude | Yes | Stop prompts containing secrets or restricted data |
| `ConfigChange` | When a settings or skill file changes | Yes, except managed policy changes | Block or audit tampering with project and user settings |
| `PostToolUse` | After a tool succeeds | No | Log actions locally, feed results to scanners |
| `SessionStart` / `SessionEnd` | Session boundaries | No | Record who ran which session, ship local logs |

Exit code 2 blocks on most events that can block: on `PreToolUse` it stops the tool call, and on `UserPromptSubmit` it stops the prompt so it never reaches the model. `PermissionRequest` ignores exit code 2 and denies only through its decision object. For structured control on `PreToolUse`, a hook exits 0 and prints JSON with a `permissionDecision` of `allow`, `deny`, `ask`, or `defer`. These events cover actions on the machine; the network-side equivalent is [policy-based governance at the gateway](https://www.getmaxim.ai/articles/policy-based-governance-at-the-gateway-one-control-plane-for-every-ai-call/), where one control plane evaluates every AI call.

## How a PreToolUse Hook Blocks a Tool Call

A `PreToolUse` hook runs after Claude proposes a tool call and before the tool executes. If the matcher and the optional `if` rule match, the handler runs and can return `deny`, which blocks the call and returns a reason to Claude so it can choose a different approach.

![](https://storage.ghost.io/c/84/03/8403f2f6-141c-411a-8f55-a32d4291533e/content/images/2026/10/image-4.png)

*Figure 1: A PreToolUse hook is the last check before a local action executes, and a deny decision stops the call before it runs.*

This configuration narrows a handler to `rm` subcommands of the Bash tool:

```json
{
  "hooks": {
    "PreToolUse": [
      {
        "matcher": "Bash",
        "hooks": [
          {
            "type": "command",
            "if": "Bash(rm *)",
            "command": "/opt/claude-policy/block-destructive.sh"
          }
        ]
      }
    ]
  }
}
```

The script reads the event JSON and returns a deny decision:

```bash
#!/bin/bash
COMMAND=$(jq -r '.tool_input.command')
if echo "$COMMAND" | grep -q 'rm -rf'; then
  jq -n '{hookSpecificOutput: {hookEventName: "PreToolUse",
    permissionDecision: "deny",
    permissionDecisionReason: "Destructive command blocked by policy"}}'
else
  exit 0
fi
```

Two details matter for governance. A matcher of `Bash` does not catch the same write performed by the `Edit` tool, so policies need matchers for every tool that can reach a protected resource. The `if` filter is also best-effort: when Claude Code cannot parse which commands a Bash input runs, the hook runs regardless, and Anthropic recommends the permission system, such as managed `permissions.deny` rules, for any hard allow or deny. Deny and ask permission rules are evaluated whatever the hook returns, so hooks add restrictions on top of the permission system rather than replacing it. A practical companion is the guide to [securing Claude Code in production with SSO, audit logs, and PII guardrails](https://www.getmaxim.ai/articles/securing-claude-code-in-production-sso-audit-logs-and-pii-guardrails-for-engineering-teams/).

## Enforcing Hooks Organization-Wide with Managed Settings

Managed settings make Claude Code hooks an organizational control rather than a personal one. An administrator deploys `managed-settings.json` (or an MDM profile, or server-managed settings), sets `allowManagedHooksOnly`, and every machine runs the managed hooks while user, project, local, and most plugin hooks are blocked.

Anthropic's [managed settings guide](https://code.claude.com/docs/en/managed-settings) lists three delivery mechanisms: a file in a system directory, an MDM or OS-level policy, and server-managed settings fetched from the admin console. The properties that make managed hooks enforceable:

- **Merge, not replace:** user and project hooks add to managed hooks but cannot remove them
- **Locked disable switch:** `disableAllHooks` set in user, project, or local settings cannot disable managed hooks
- **Restricted sources:** `allowManagedHooksOnly` blocks hooks from user, project, local, and non-forced plugin sources
- **HTTP allowlists:** `allowedHttpHookUrls` limits which endpoints HTTP hooks may call, for hooks from every source

HTTP hooks are particularly useful for central policy. Instead of shipping a script to every laptop, a managed `PreToolUse` HTTP hook can POST each proposed tool call to an internal policy service that answers with the same JSON decision format. The service then becomes the single place to change local-action policy. For fleets that already standardize on a gateway, the comparison of [Claude Code gateways for enterprise governance](https://www.getmaxim.ai/articles/best-claude-code-gateway-for-enterprise-governance/) shows how the two policy surfaces are usually divided, and [Bifrost Enterprise](https://www.getmaxim.ai/bifrost/enterprise) adds SSO-based identity for the gateway side.

## Claude Code Hooks and Claude Code Security

Claude Code hooks improve Claude Code security for actions that stay on the machine: destructive shell commands, writes to protected paths, prompts that contain credentials, and changes to settings files. They are the only control that sees those actions, because none of them crosses the network.

Hooks also carry security caveats from the same reference:

- **Full user permissions:** command hooks execute with the developer's own permissions and can read or modify anything that account can
- **Workspace trust:** in interactive sessions, hooks wait for the workspace trust dialog, but `p` and SDK sessions treat the folder as trusted, so hooks committed to a repository run without a prompt
- **Fail-open defaults:** a handler that crashes or times out is a non-blocking error unless the hook sets `onFailure` to `block`
- **Tool coverage:** each matcher covers only the tools it names, so a gap in matchers is a gap in policy

None of these is a reason to avoid hooks. They are a reason to keep anything that must hold under adversarial conditions (credentials, spend, model access) off the laptop and on infrastructure the platform team controls. The same reasoning appears in the broader guide to [AI coding agent security across Cursor, Claude Code, and Copilot](https://www.getmaxim.ai/articles/ai-coding-agent-security-governing-cursor-claude-code-and-copilot/), and gateway-side [secrets detection](https://docs.getbifrost.ai/enterprise/guardrails/secrets-detection) backs up a prompt hook that misses a credential.

## Where Claude Code Hooks Stop

Claude Code hooks stop at the boundary of one session on one machine. They cannot see other developers' sessions, other coding agents, or traffic from services that embed the Claude Agent SDK, and they cannot hold provider credentials or count spend against a budget shared by a team.

| Governance requirement | Claude Code hooks | AI gateway |
| --- | --- | --- |
| Block a local shell command or file edit | Yes | No, the gateway never sees it |
| Block a prompt containing a secret | Yes, `UserPromptSubmit` | Yes, with gateway guardrails |
| Keep provider API keys off laptops | No | Yes |
| Enforce a per-team monthly budget | No | Yes |
| Restrict which models a developer can call | Partially, per machine | Yes, per credential |
| Restrict which MCP tools an agent reaches | Per session | Yes, per credential across all clients |
| Produce one audit log across every developer | No, logs stay local | Yes |
| Apply the same rules to Codex CLI and SDK services | No | Yes |

The table maps to a simple rule: if the control is about what the agent does on the machine, use a hook; if it is about who may spend what, on which model, with which tools, use the gateway. The cost side of that rule is covered in detail in [the hidden cost of Claude Code at enterprise scale](https://www.getmaxim.ai/articles/the-hidden-cost-of-claude-code-at-enterprise-scale/).

## Where Gateway Policy Takes Over

Gateway policy takes over for every control that applies to network traffic: authentication, model access, budgets, rate limits, MCP tool access, content guardrails, and request logging. Claude Code sends every model request to `ANTHROPIC_BASE_URL`, so a gateway at that URL enforces policy on all of it.

![](https://storage.ghost.io/c/84/03/8403f2f6-141c-411a-8f55-a32d4291533e/content/images/2026/10/image-5.png)

*Figure 2: Hooks see actions that never leave the laptop; the gateway sees every request that does, from every developer and every agent.*

Anthropic's [LLM gateway guidance for Claude Code](https://code.claude.com/docs/en/llm-gateway) lists what a gateway centralizes: credentials, usage tracking by developer or team, budgets and rate limits, audit logging, and provider switching. It also documents the control that ties both layers together: setting `allowedProviders` to `["customEndpoint"]` with a pinned `ANTHROPIC_BASE_URL` in managed settings makes Claude Code refuse any session pointed elsewhere.

[Bifrost](https://www.getmaxim.ai/bifrost) implements each gateway control for Claude Code traffic:

- **Identity:** [virtual keys](https://docs.getbifrost.ai/features/governance/virtual-keys) or, on Enterprise, SSO-issued tokens through `apiKeyHelper` attribute each request to a developer
- **Spend:** [budgets and rate limits](https://docs.getbifrost.ai/features/governance/budget-and-limits) at the virtual key, team, and customer levels reject requests once any budget is exhausted
- **Model access:** each virtual key allows specific providers and models, so a team can be limited to approved Claude models on approved providers
- **Tool access:** Bifrost acts as an [MCP gateway](https://www.getmaxim.ai/bifrost/resources/mcp-gateway), exposing connected MCP servers through one `/mcp` endpoint with [per-key MCP tool filtering](https://docs.getbifrost.ai/features/governance/mcp-tools)
- **Content:** [Bifrost guardrails](https://docs.getbifrost.ai/enterprise/guardrails) validate LLM inputs and outputs and MCP tool executions
- **Audit:** [request logs](https://docs.getbifrost.ai/features/observability/default) record identity, model, tokens, and cost per call, and Enterprise [audit logs](https://docs.getbifrost.ai/enterprise/audit-logs) record administrative changes

For the cost side specifically, [Claude Code logging and spend limits for engineering teams](https://www.getmaxim.ai/articles/claude-code-logging-and-spend-limits-for-engineering-teams/) walks through per-team budgets in practice.

## Combining Hooks and Bifrost: A Reference Setup

A complete Claude Code governance setup uses one managed settings file to do three jobs: lock hooks for local actions, pin the gateway as the only endpoint, and fetch a short-lived Bifrost credential. Every prompt and tool call then passes both layers in sequence.

![](https://storage.ghost.io/c/84/03/8403f2f6-141c-411a-8f55-a32d4291533e/content/images/2026/10/image-6.png)

*Figure 3: Each layer blocks what it can see: hooks stop local intent early, and Bifrost enforces identity, spend, and tool policy on the network path.*

An example `managed-settings.json`:

```json
{
  "allowManagedHooksOnly": true,
  "allowedProviders": ["customEndpoint"],
  "apiKeyHelper": "~/.bifrost/bin/bifrost --context production auth print-token",
  "env": {
    "ANTHROPIC_BASE_URL": "<https://bifrost.example.com/anthropic>",
    "CLAUDE_CODE_API_KEY_HELPER_TTL_MS": "900000"
  },
  "hooks": {
    "PreToolUse": [
      {
        "matcher": "Bash|mcp__.*",
        "hooks": [{ "type": "http", "url": "<https://policy.example.com/claude/pre-tool-use>" }]
      }
    ],
    "UserPromptSubmit": [
      {
        "hooks": [{ "type": "command", "command": "/opt/claude-policy/scan-prompt.sh" }]
      }
    ]
  }
}
```

The [Claude Code integration guide](https://docs.getbifrost.ai/cli-agents/claude-code) covers the `apiKeyHelper` flow in detail: with Bifrost Enterprise SSO, the [Bifrost CLI](https://docs.getbifrost.ai/quickstart/cli/getting-started) prints a session token for the signed-in user and refreshes it automatically, so no long-lived secret sits in settings. On the open-source gateway, the helper can fetch a virtual key from a vault instead. To route Claude Code's MCP connections through the same policy, add Bifrost as an HTTP MCP server; the walkthrough on [using an MCP gateway with Claude Code](https://www.getmaxim.ai/articles/using-an-mcp-gateway-with-claude-code-a-practical-guide/) covers that step.

Bifrost adds 11 microseconds of overhead per request at 5,000 RPS in [sustained benchmarks](https://www.getmaxim.ai/bifrost/resources/benchmarks), which is negligible next to model latency in the agent loop that hooks run inside.

## Frequently Asked Questions

### What are hooks in Claude Code?

Hooks in Claude Code are configured handlers that run automatically at lifecycle events such as `PreToolUse`, `UserPromptSubmit`, and `SessionEnd`. A handler can be a shell command, an HTTP endpoint, an MCP tool call, a single-turn model prompt, or a subagent. Hooks can inspect the event, add context, and allow or block the action that follows.

### What is the primary purpose of hooks in Claude Code?

The primary purpose of hooks is deterministic control over agent behavior at points where instructions alone are not reliable. Teams use them to block destructive commands, protect sensitive files, enforce formatting or tests after edits, and log activity. For governance, they are the main control over local actions that never leave the developer's machine.

### Can Claude Code hooks enforce budgets or model access?

No. Hooks run inside one session on one machine and have no view of team-wide spend or credentials. A `PreModelSwitch` hook can block switching models mid-session, but budgets, model allow-lists, and rate limits shared across developers need an AI gateway that sees every request, which is how [virtual keys govern LLM access across large engineering teams](https://www.getmaxim.ai/articles/virtual-keys-explained-how-platform-teams-govern-llm-access-across-100-engineers/).

### How do I stop developers from disabling Claude Code hooks?

Deploy the hooks in managed settings and set `allowManagedHooksOnly` to true. Managed hooks merge with other settings rather than being replaced, and `disableAllHooks` set in user, project, or local settings cannot disable them. Deliver the policy through a system file, MDM profile, or server-managed settings.

### Do Claude Code hooks run in Agent SDK sessions?

Yes. The Claude Agent SDK runs the same engine as Claude Code and supports hooks, both as callbacks in code and from settings files. In `-p` and SDK sessions, Claude Code treats the folder as trusted, so hooks committed to a repository run without a trust prompt. Review repository settings before automating runs against unfamiliar code, and route SDK model calls through the [Bifrost Anthropic SDK integration](https://docs.getbifrost.ai/integrations/anthropic-sdk/overview) so gateway policy still applies.

### Where should Claude Code governance live, in hooks or in a gateway?

It should live in both, split by what each layer can see. Hooks govern local actions: shell commands, file edits, prompts, and settings changes. A gateway governs everything on the network path: credentials, budgets, model access, MCP tool access, guardrails, and the audit log. Pinning the gateway in managed settings connects the two.

## Govern Claude Code at Both Layers with Bifrost

Claude Code hooks are the right tool for stopping risky local actions, and managed settings make them hold across a fleet. Spend, model access, tool access, and audit belong to the [Bifrost AI gateway](https://www.getmaxim.ai/bifrost), which applies one policy to every Claude Code session and every other agent on the same path, as the guide to [governing Claude Code through an AI gateway](https://www.getmaxim.ai/articles/claude-code-governance-securing-agent-access-with-an-ai-gateway/) explains. To see Claude Code hooks and gateway policy working together, [book a Bifrost demo](https://getmaxim.ai/bifrost/book-a-demo).

## Read next

[![Shadow AI in Coding Tools: 5 Ways to Find Unapproved Cursor, Claude Code, and Copilot Usage](https://storage.ghost.io/c/84/03/8403f2f6-141c-411a-8f55-a32d4291533e/content/images/size/w720/2026/10/shadow-ai-in-coding-tools-5-ways-to-find-unapproved-cursor-c-bifrost-1920x1080@2x.png) Shadow AI in coding tools is AI-assisted development that runs outside company approval, through personal plans, personal API keys, or unmanaged installs. This guide covers five ways to find unapproved Cursor, Claude Code, and Copilot usage, and how to route it through governance.](https://www.getmaxim.ai/articles/shadow-ai-coding-tools/)

[![Top 5 AI Data Governance Tools for Controlling What Data Reaches LLMs in 2026](https://storage.ghost.io/c/84/03/8403f2f6-141c-411a-8f55-a32d4291533e/content/images/size/w720/2026/10/top-5-ai-data-governance-tools-for-controlling-what-data-rea-bifrost-1920x1080@2x.png) AI data governance decides which data can reach a language model and what happens when sensitive data tries to. This guide compares five tools for controlling it, including Bifrost, Microsoft Purview, Google Cloud Model Armor, Nightfall, and Cyera.](https://www.getmaxim.ai/articles/ai-data-governance-tools/)

[![Top 5 Tools to Enforce an AI Usage Policy in 2026](https://storage.ghost.io/c/84/03/8403f2f6-141c-411a-8f55-a32d4291533e/content/images/size/w720/2026/10/top-5-tools-to-enforce-an-ai-usage-policy-in-2026-bifrost-1920x1080.png) An AI usage policy defines which AI tools, models, and data employees may use; enforcement turns those rules into runtime checks. This guide compares Bifrost, Netskope One, Microsoft Purview, Akamai Workforce Protector, and WitnessAI by the policy clauses each can enforce.](https://www.getmaxim.ai/articles/top-5-tools-to-enforce-an-ai-usage-policy-in-2026/)

## More in AI Governance

[![Shadow AI in Coding Tools: 5 Ways to Find Unapproved Cursor, Claude Code, and Copilot Usage](https://storage.ghost.io/c/84/03/8403f2f6-141c-411a-8f55-a32d4291533e/content/images/size/w720/2026/10/shadow-ai-in-coding-tools-5-ways-to-find-unapproved-cursor-c-bifrost-1920x1080@2x.png) Shadow AI in coding tools is AI-assisted development that runs outside company approval, through personal plans, personal API keys, or unmanaged installs. This guide covers five ways to find unapproved Cursor, Claude Code, and Copilot usage, and how to route it through governance.](https://www.getmaxim.ai/articles/shadow-ai-coding-tools/)

```json
{
    "@context": "https://schema.org",
    "@type": "Article",
    "publisher": {
        "@type": "Organization",
        "name": "Maxim Articles",
        "url": "https://www.getmaxim.ai/articles/",
        "logo": {
            "@type": "ImageObject",
            "url": "https://storage.ghost.io/c/84/03/8403f2f6-141c-411a-8f55-a32d4291533e/content/images/size/w256h256/2025/08/thumbnail.png",
            "width": 60,
            "height": 60
        }
    },
    "author": {
        "@type": "Person",
        "name": "Kamya Shah",
        "image": {
            "@type": "ImageObject",
            "url": "https://storage.ghost.io/c/84/03/8403f2f6-141c-411a-8f55-a32d4291533e/content/images/2025/09/WhatsApp-Image-2025-08-29-at-17.40.40-1.jpeg",
            "width": 1200,
            "height": 1600
        },
        "url": "https://www.getmaxim.ai/articles/author/kamya/",
        "sameAs": []
    },
    "headline": "Claude Code Hooks for Governance and Gateway Policy",
    "url": "https://www.getmaxim.ai/articles/claude-code-hooks-for-governance-and-gateway-policy/",
    "datePublished": "2026-10-21T20:22:00.000Z",
    "dateModified": "2026-10-22T20:23:18.000Z",
    "image": {
        "@type": "ImageObject",
        "url": "https://storage.ghost.io/c/84/03/8403f2f6-141c-411a-8f55-a32d4291533e/content/images/size/w1200/2026/10/claude-code-hooks-for-governance-and-gateway-policy-bifrost-1920x1080.png",
        "width": 1200,
        "height": 675
    },
    "keywords": "AI Governance",
    "description": "Claude Code hooks are handlers that run at fixed points in a session and can allow, deny, or log what the agent does. This guide shows how to use Claude Code hooks for governance, how to lock them with managed settings, and where an AI gateway enforces identity, budgets, and tool access instead.",
    "mainEntityOfPage": "https://www.getmaxim.ai/articles/claude-code-hooks-for-governance-and-gateway-policy/"
}
```
