Follow Discord
Sweep 02 Oct 2026 · 18:55Z Build v2.1.288 509 read Stable v2.1.285 Latest v2.1.288 Next v2.1.288 Feeds RSS JSON llms.txt llms-full.txt Unofficial
One change · claude-code

React to events with a mod changedplugins/mods/events

Nearest release: v2.1.287, published 11 hours before upstream edited the page. Shown because the two are within 24 hours of each other. Nothing here says the release caused the edit.

Upstream edited this page at 2 Oct 2026 04:34 UTC, give or take a minute or two: the time comes from Anthropic’s own sitemap rather than from a commit. This site recorded the change at 2 Oct 2026 04:37 UTC.

Upstream edited
Recorded here
Lines+14added
Lines−12removed
From line 42 where the diff opens
First seen 1 Oct 2026 this site's first read of the page
Recorded edits3to this page, all time

### Hook the settings hook events

The whole hunk

from line 42, old and new numbered
/
lines
from line 42
4242 
4343### Rewrite an event
4444 
45To change what Claude Code acts on, such as the text of a prompt, call `next` with a modified copy of the event. The event itself is immutable: it's frozen at every depth, and assigning to a field throws. This hook trims each prompt before it's sent:
45To change what Claude Code acts on, such as the text of a prompt, call `next` with a modified copy of the event. The event itself is immutable: it's deeply frozen, and assigning to a field throws. This hook trims each prompt before it's sent:
4646 
4747```javascript theme={null}
4848on('prompt.submit', async ($, e, next) => {
from line 83
8383 
8484`hook` runs once for a Bash, Edit, or Write call, and once for a call to a tool whose name starts with `mcp__github__`. A call to any other tool, such as Read, matches none of the three, so `hook` doesn't run for it.
8585 
86The event name can be a wildcard. `'classic.*'` matches every [settings hook event](#hook-the-settings-hook-events). `'*'` matches every event except the [telemetry events](/docs/en/plugins/mods/reference#telemetry), which you hook by name or as `'telemetry.*'`.
86The event name can be a wildcard. `'classic.*'` matches every [settings hook event](#hook-the-settings-hook-events). `'*'` matches every event except the [telemetry events](/docs/en/plugins/mods/reference#telemetry), which take their own name and a `{ to: 'collector' }` filter.
8787 
8888Register each event once per matcher. If you call `on` twice for `session.start` with no matcher, the module fails to load with `on("session.start") is registered twice without a matcher`. Put everything your mod does at session start in one hook.
8989 
9090## Hook what Claude is doing
9191 
92Hook these events to see or change a tool call, a prompt, or a turn as it happens. For every event and what a hook can return, see the [events reference](/docs/en/plugins/mods/reference#events).
92Handle these events to see or change a tool call, a prompt, or a turn as it happens. For every event and what a hook can return, see the [events reference](/docs/en/plugins/mods/reference#events).
9393 
9494### Guard or change a tool call
9595 
from line 168
168168* **The user types an answer**: `$.ui.ask` resolves to the typed text. The hook compares it with `Run it`, so any other text refuses the command.
169169* **Nobody answers**: `$.ui.ask` rejects when the user dismisses the question or picks **Chat about this**, and in a `claude -p` run, so the `catch` block leaves the answer at `Refuse`
170170 
171Keep the wait inside a mods API call such as `$.ui.ask`, because that time doesn't count against the hook's [10-second time limit](/docs/en/plugins/mods/reference#limits). Time spent awaiting a promise of your own does count. Claude Code skips a hook that times out, so the held command would run.
171Keep the wait inside a mods API call such as `$.ui.ask`, because that time doesn't count against the hook's [time limit](/docs/en/plugins/mods/reference#limits). Time spent awaiting a promise of your own does count. Claude Code skips a hook that times out, so the held command would run.
172172 
173173#### Approve or refuse a tool call before the user is asked
174174 
from line 193
193193 
194194The hook matches the text of the command, so treat it as a reminder for Claude. To block pushes to `main` for everyone, protect the branch on your Git host.
195195 
196A hook can return any of the three decisions, so it can also approve a call that a `PreToolUse` hook outside managed settings blocked. [Extend permissions with hooks](/docs/en/permissions#extend-permissions-with-hooks) lists which decisions hold over a mod.
196A hook can return `allow`, `ask`, or `deny`, so it can also approve a call that a `PreToolUse` hook outside managed settings blocked. [Extend permissions with hooks](/docs/en/permissions#extend-permissions-with-hooks) lists which decisions hold over a mod.
197197 
198198### Rewrite or add to a prompt
199199 
from line 225
225225 
226226### Follow a turn
227227 
228A turn is everything Claude does in answer to one prompt. Hook `turn.start`, `turn.step`, and `turn.complete` to follow one:
228A turn is everything Claude does in answer to one prompt. Handle `turn.start`, `turn.step`, and `turn.complete` to follow one:
229229 
230230| Event | When it fires | What a hook can do |
231231| :- | :- | :- |
from line 251
251251 
252252Claude's response streams to the screen as it does without the mod. After each request finishes, a dim line in the transcript gives the number of tokens read from the cache and the number written to it. A turn with tool calls has several requests, so it adds several lines.
253253 
254`result.usage` holds the four token counts the Claude API reports for a request, plus the `model` that answered: `input_tokens`, `output_tokens`, `cache_read_input_tokens`, and `cache_creation_input_tokens`. The hook runs for subagents' requests too, so check `e.agentId` when you want only the main conversation.
254`result.usage` holds the token counts the Claude API reports for a request, plus the `model` that answered: `input_tokens`, `output_tokens`, `cache_read_input_tokens`, and `cache_creation_input_tokens`. The hook runs for subagents' requests too, so check `e.agentId` when you want only the main conversation.
255255 
256### Hook the settings hook events
256<h3 id="hook-the-settings-hook-events">
257 Handle the settings hook events
258</h3>
257259 
258260Settings hooks are the command, HTTP, prompt, and agent hooks you configure in settings files. Each [settings hook event](/docs/en/hooks#hook-events), such as `Stop`, `SessionEnd`, or `PostToolUse`, is also an event named `classic.` followed by the settings hook event's name, such as `classic.Stop`. `e` is the JSON a settings hook receives on stdin, including `transcript_path`.
259261 
from line 274
272274 
273275## Run alongside other mods
274276 
275Several mods can hook the same event, and any one of them can fail. If your mod blocks tool calls, check its position in the chain and what happens when its hook fails.
277Several mods can handle the same event, and any one of them can fail. If your mod blocks tool calls, check its position in the chain and what happens when its hook fails.
276278 
277279### The order mods run in
278280 
from line 317
315317})
316318```
317319 
318While `guard` works, the handler never runs. When `guard` throws or times out on a Bash call, Claude Code calls the handler with the same event. The handler returns `{ deny }`, so the command doesn't run, and Claude reads the text with `throw` or `timeout` at the end. Without the handler, Claude Code would skip `guard` and run the command. The handler has [one second](/docs/en/plugins/mods/reference#limits) to answer.
320While `guard` works, the handler never runs. When `guard` throws or times out on a Bash call, Claude Code calls the handler with the same event. The handler returns `{ deny }`, so the command doesn't run, and Claude reads the text with `throw` or `timeout` at the end. Without the handler, Claude Code would skip `guard` and run the command. The handler has a shorter [time limit](/docs/en/plugins/mods/reference#limits) of its own.
319321 
320322## Next steps
321323 
322324* [Use the mods API](/docs/en/plugins/mods/api): add commands and tools, call a model, and run work on a timer
323325* [Draw in the interface](/docs/en/plugins/mods/interface): show what your hooks collect in a pane or above the prompt
324* [Test a mod](/docs/en/plugins/mods/test): raise any of these events from a test
326* [Test a mod](/docs/en/plugins/mods/test): fire any of these events from a test
325327* [Mods reference](/docs/en/plugins/mods/reference): every event, every mods API method, and the limits
326328 
Feedback