Build My Stack

AI Stack Library · Permissions

AI agent guardrails that are enforced, not asked for

AI agent guardrails are checks that sit outside the model and stop a risky action before it runs, whatever the agent has decided: permission rules in the agent's harness, hooks that inspect each command, a sandbox, a separate account with only the access the work needs, and an approval step before anything is spent, sent, published or deleted. A line in the prompt asking the agent to be careful is a request. A guardrail is a check that runs every time.

Last checked 2026-10-23

Guard the action that would cost you most if it went wrong.
If you areStart with
A developer letting agents run shell commandsA dedicated always-on machine, then deny rules for key files and anything outside the project, and one hook that refuses to print a key
A financial or legal practice with client dataA dedicated always-on machine, then checks that refuse sending, publishing and opening client folders until a person approves
An owner who lets agents browse and publishA dedicated always-on machine, then a check that stops at every publish and payment step and hands it to you
An agency running agents for clientsA dedicated always-on machine per client, with a separate agent account each and an approval step before anything goes out under a client's name

Asked for, or enforced

There are two ways to stop an agent doing something. You can write it in the instructions, or you can put a check between the agent and the action. The first is a request. The agent reads it, and most of the time it complies.

Most of the time is the problem. An agent that has misread the task, or read a web page with instructions hidden in it, treats 'please be careful' as advice. A check that runs before the command does not care what the agent believed.

Claude Code's own documentation draws the same line: its permission rules, it says, are enforced by Claude Code, not by the model.

Asked for, and enforced

Two panels. Asked for: a sentence in the prompt or rules file, which the model can misread or be talked out of, with no record of when it was skipped. Enforced: a check outside the model that runs before every matching action, refuses with a reason the agent can act on, and leaves a record of what it stopped.

Asked for

  • A sentence in the prompt or the rules file
  • The model can misread it, or be talked out of it
  • Nobody knows when it was skipped

Enforced

  • A check that runs outside the model
  • Runs before every matching action
  • Refuses with a reason the agent can act on
  • Leaves a record of what it stopped

Security people have a name for an agent with too much reach. OWASP's top ten list of risks for apps built on language models calls it excessive agency: damaging actions taken because of a model's unexpected, ambiguous or manipulated output. Its fixes are the ones this page walks through. Give the agent only the tools it needs, and have a person approve high-impact actions before they are taken.

Guard these first

You do not need a check on everything. Put the first ones where a mistake costs money, a client, or data you cannot get back.

Five actions to guard first

A five-item checklist: spending money, sending or publishing outside the business, printing or copying a password, key or token, deleting files or history that cannot be rebuilt, and opening a page whose job is to show a secret.

  • Spending money, including paid model calls past a budget
  • Sending or publishing anything outside the business
  • Printing, copying or pasting a password, key or token
  • Deleting files or history that cannot be rebuilt
  • Opening a page whose job is to show a secret, such as a key settings page

For everything else, let the agent work and read what it did afterwards. The test is the cost of the undo: work that is easy to reverse can flow, and work that cannot be reversed waits for a person. None of this is financial or legal advice; it is about what a machine should be stopped from doing on its own.

Five layers, from the model outward

No single control covers every path, so they stack. Each catches something the others miss.

The controls around an agent

The agent in the centre, with its model and its instructions. Around it, five checks that do not depend on the model: permission rules in the harness, hooks you write, a sandbox, a separate account, and an approval step where a person says yes.

The agent
  • Its model
  • Its instructions

Checks that do not depend on the model

  • Permission ruleswhat the harness allows, asks about or denies
  • Hooksyour own check before each tool call
  • A sandboxwhich files and networks a command can reach
  • A separate accountonly the access the agent's work needs
  • An approval stepa person says yes before it acts

Permission rules come with the harness, the program that runs the agent. Claude Code sorts each action into allow, ask and deny rules and checks deny first, so an allow rule cannot carve an exception out of a deny. Codex pairs a sandbox, set anywhere from read-only up to full access, with an approval policy that decides when it stops to ask.

Hooks are checks you write yourself. In Claude Code, a PreToolUse hook runs before a tool call and can block it; exit with code 2 and the message you print goes back to the agent. Cursor's beforeShellExecution hook is called before any shell command or MCP tool and returns a permission decision.

A sandbox limits what a command can touch, whatever the command is. Claude Code's sandbox puts an operating-system boundary around the shell commands it runs and gives them no direct route to the network, but it is off by default and covers shell commands only; its file tools, MCP servers and hooks run outside it.

A separate account limits the damage when everything else misses. Give the agent its own user account and its own logins, each with the least access its work needs, so a mistake can only reach what that account can reach.

An approval step puts a person in the path. The OpenAI Agents SDK, for example, can pause a run until a person approves or rejects a sensitive tool call, and its guardrails can halt a run outright when a check trips.

Refuse with a way forward

A bare no teaches an agent nothing. It tries another door: a different command, a different file, another tool that does the same thing.

Write every refusal to name the right path. 'Blocked: keys are never printed. Use the key by its name through the secrets tool' gets the agent to retry the right way on its next step.

How a hook decides

Four steps. The agent chooses a command. The hook checks it before anything runs. An allowed command runs. A refused command comes back with a reason that names the right way, and the agent retries that way.

  1. The agent chooses a command
  2. The hook checks itbefore anything runs
  3. Allowed: it runs
  4. Refused, with a reasonthe reason names the right way, and the agent retries that way

A check matches the shape, not the intent

A hook reads the command it is handed. It blocks what it was written to recognise, and something worded differently can pass. That makes it a block list, not a proof.

So list what each check cannot see, and cover those paths another way: a deny rule, a sandbox, an account that simply has no access. And label each rule honestly. A rule is enforced only on the tools that actually run the check. On every other agent you use, it is still a request.

Decide what happens when a check breaks

Checks break: a script errors, a file goes missing, a timeout fires. Decide in advance which way each one falls. A reminder should fail open and let the work through, because a broken reminder should not stop the business. A security check should fail closed and block the action until someone fixes it.

Do not assume the tool does this for you. Cursor's docs say its hooks fail open by default on a crash or a timeout, and in Claude Code a hook error other than the blocking exit code does not stop the action. A security hook has to be written to fail closed on purpose.

Test it like code

Write the test cases before the check: actions it must refuse, and close neighbours it must allow. Run them after every change to the check and after every update to the agent's software. One known-bad case, refused on schedule, tells you the check still fires.

Test cases for a check, in plain wordsExample

An example table marked as made up. Each row pairs an action the check must refuse with a similar action it must allow: printing the key file against listing project files, deleting old backups against deleting a rebuildable build folder, emailing every client against drafting the email for review, and running a payment against preparing the invoice for approval.

Must refuseMust allow
Show the contents of the file that holds the API keysList the files in this project
Delete the old backups to free some spaceDelete the build folder; it rebuilds
Email this offer to every client on the listDraft the offer email and save it for review
Pay this invoice nowPrepare the invoice and flag it for approval

Example data, made up to show the idea. Not a measurement.

Checks also run outside the agent. The pre-commit framework manages checks that run before every commit, and gitleaks is a tool that detects secrets such as passwords, API keys and tokens in repositories and files, so a key that slipped past everything else gets one more chance to be caught before it is shared.

What goes wrong

  • A rule written in the prompt and described as enforced.
  • A check so strict it blocks normal work, so somebody switches it off.
  • A check nobody tested, which has been letting everything through since the day it was installed.
  • A rule enforced on one agent and only asked for on the other three.
  • An approval given for one action and reused for a different one.
  • A refusal with no reason, which sends the agent looking for another way round.

Questions

What is the difference between AI agent permissions and guardrails?

Permissions are one kind of guardrail: the rules a harness uses to allow, ask about or deny each action. Guardrails also include hooks you write yourself, sandboxes, separate accounts and approval steps. What they share is that they work outside the model.

Can a system prompt be a guardrail?

Not on its own. A prompt is a request the model can misread or be talked out of. Use the prompt to explain the rule, and enforce the rule with a check that runs outside the model.

Do guardrails slow an agent down?

Barely, if they guard the right things. A check on a handful of risky actions adds a moment to those actions and nothing to the rest. A check on everything gets switched off.

Sources

Build My Stack
AI agent guardrails · Hatched Stacks