---
title: "Now You Can Make Claude Code Follow Your Rules, Every Time"
description: "A late night YouTube binge dropped Claude Code function hooks in my lap. They turn the rules you keep repeating to your AI into rules it cannot skip. Here is what that opens up, and the ideas I want you to steal."
date: 2026-09-05
author: "Gabi Udrescu"
tags: ["claude-code", "ai", "function-hooks", "plugins", "agentic-coding", "open-source"]
source: https://productowner.ro/blog/make-claude-code-follow-your-rules/
---

# Now You Can Make Claude Code Follow Your Rules, Every Time

import HookMechanism from '../../../components/HookMechanism.astro';
import HookMatrix from '../../../components/HookMatrix.astro';
import HookStack from '../../../components/HookStack.astro';
import RepoCTA from '../../../components/RepoCTA.astro';

It was past midnight, I was three autoplays deep into YouTube, and the algorithm handed me [a video from Ray Amjad](https://www.youtube.com/watch?v=B-YQANvDOq0) titled "Anthropic Just Dropped the Biggest Claude Code Update Yet." That title made me curious. I watched the whole thing, and I was mindblown.

Function hooks. Anthropic shipped them in Claude Code 2.1.261, barely two days before I wrote this, and they are the most interesting thing to land in this tool all year. So far. This is hot out of the oven, so expect the surface to move under you.

<iframe width="100%" height="400" src="https://www.youtube.com/embed/B-YQANvDOq0" frameborder="0" allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture; web-share" referrerpolicy="strict-origin-when-cross-origin" allowfullscreen title="Anthropic Just Dropped the Biggest Claude Code Update Yet"></iframe>

## Express middleware, but for your agent

Here is the whole idea. Every time Claude Code is about to do something, your code gets to stand in the doorway first.

<HookMechanism />

You are not writing a config file that says yes or no. You are standing in the middle of the conversation between Claude and your machine, and you decide what gets through, what gets rewritten, and what never happens.

If you have ever written Express or Koa middleware, you already know this shape. And that is exactly the point: [the proposal itself](https://github.com/anthropics/claude-code/issues/91870) says so out loud. It is worth opening, by the way. Anthropic put a dozen short demo videos in that thread, from the basics up to case studies, and they show the feature better than any screenshot I could take.

Before this, a plugin could run a shell command at a fixed point and say yes or no. That was the ceiling.

<HookMatrix rows={[
  { label: 'block a command', shell: true, fn: true },
  { label: 'rewrite the command', shell: false, fn: true },
  { label: 'rewrite your prompt', shell: false, fn: true },
  { label: 'add context to the session', shell: false, fn: true },
  { label: 'draw: status, rows, buttons', shell: false, fn: true },
  { label: 'ask you a question', shell: false, fn: true },
  { label: 'add a tool, edit a description', shell: false, fn: true },
  { label: 'call a model', shell: false, fn: true },
  { label: 'remember across sessions', shell: false, fn: true },
  { label: 'stack with other plugins', shell: false, fn: true },
]} />

That last row is the one people underestimate. Hooks nest. Several plugins wrap the same action, one inside the next, and each one decides what the ones beneath it get to see. Same prompt, same model, different answer depending on whose hook sits on top.

<HookStack />

That is a very different conversation with a security team than "we wrote it in a markdown file and asked nicely."

I woke up this morning still thinking about it, so instead of reading more blog posts about the feature I went straight to the type declarations. Claude Code generates them for you with `/plugin-types`: twenty events, the whole engine interface, the input schema of every built-in tool. I read them and wrote everything down before lunch, and that became [a repo](https://github.com/productowner-ro/claude-function-hooks) with a reference for the whole surface and [a file per event](https://github.com/productowner-ro/claude-function-hooks/tree/main/examples). Written against 2.1.261, from the declarations, not from vibes.

## The part I actually cannot stop thinking about

Reading the events felt less like learning an API and more like being handed a box of parts. Here are the things I want to exist. A shell hook could block some of them. None of them were practical to build until now.

**Secrets that never enter your transcript.** Redact on the way in, hand the model a placeholder, then put the real value back in the split second before the tool runs. The model does the work and never sees the key. Nothing to rotate afterwards, because nothing leaked. That is the worked example in the README, and it was the first thing I built.

**Your CLAUDE.md, but it actually holds.** Every rule in that file is a polite request that fades as the context fills up. "Never run destructive commands." "Always use pnpm." Move those to [`tool.call`](https://github.com/productowner-ro/claude-function-hooks/blob/main/examples/tool-call.md) and they stop being requests. The command gets blocked, or quietly rewritten to the right one, every single time.

**Rules that live on the tool, not in a file.** Here is the one that keeps biting me. Our test suite only passes on CI when it runs one worker at a time, so every parallel run comes back red and Claude spends ten minutes debugging a flake that is not real. With [`tool.describe`](https://github.com/productowner-ro/claude-function-hooks/blob/main/examples/tool-describe.md) I can staple "in this repo, always run tests with a single worker" onto the description of the tool that runs them. Claude reads it at the exact moment it reaches for that tool, every time, instead of on line 340 of a document it skimmed an hour ago.

**The UI is yours now.** [`ui.render`](https://github.com/productowner-ro/claude-function-hooks/blob/main/examples/ui-render.md) hands you the component tree. Ray puts his live deploy status in a row above the prompt. I want a fat red banner that says PRODUCTION when I am pointed at production, and a quiet one when I am not. I have made that mistake, and a banner is cheaper than the mistake.

**A gate with a brain.** A hook can call a model. So before Claude opens a pull request, it can generate three questions about the diff and refuse to continue until I answer them correctly. Not a confirm dialog. An actual check that I understood what I am about to ship.

**A real audit trail.** Hook every event, ship it to your log store. If you work anywhere near healthcare, payments, or a regulator, that is the difference between using agents and being able to prove what they did.

## Go break something this week

Start Claude Code with the flag on. In your terminal:

```bash
CLAUDE_CODE_ENABLE_FUNCTION_HOOKS=1 claude
```

Then, at the Claude Code prompt, two slash commands:

```
/plugin-types
/plugin-authoring
```

The first writes the type declarations into `.claude/types/` so you can read the real surface. The second is a built-in skill that writes hooks for you. Describe what you want in plain language, let it interview you, and you will have something running before your coffee goes cold. Do that today, with the dumbest rule you keep repeating to your agent.

And when you get stuck, the notes I took this morning are already online. Twenty events, one page each, written against the real type declarations rather than from memory.

<RepoCTA
  href="https://github.com/productowner-ro/claude-function-hooks"
  repo="productowner-ro/claude-function-hooks"
  heading="Take the whole reference. It is free."
  blurb="Every event, every method, the matchers, the failure policy, and a worked example that hides a secret from the model while still letting it use the secret. Start with the README, then open the event you need."
  cta="Open the repo on GitHub"
  secondaryHref="https://github.com/productowner-ro/claude-function-hooks/issues/new"
  secondaryLabel="Or send me your idea"
/>

I have a page full of ideas and I have built a handful of them. The interesting ones will come from people using this in places I have never worked: a hospital, a trading desk, a factory floor. If you build one, open an issue and tell me. I would much rather this becomes a shared cookbook than my personal notes.

---

Thanks Ray, for the video that cost me a night of sleep and gave me the most fun I have had with a dev tool in months.
