---
title: Hooks
---

# Hooks

## What it is

**Hooks** is a panel under **Agent Tools** (next to Skills, MCP Servers, and Browser Logins) for
managing the **Claude Code hooks** Omniscio composes into every session it spawns — both the
**built-in** hooks Omniscio ships and your own **custom** hooks. It's local-only: hooks live in
Omniscio's own database and are never written to your global `~/.claude` config.

It's an **in-development** feature, so it ships **dark** (hidden) until you turn it on in
**Settings → Lab** (`customHooksEnabled`), or `AMC_SHOW_CUSTOM_HOOKS=1`. Once on, it appears as the
**Agent Tools → Hooks** sidebar row. It's **desktop-only** — creating or editing hooks is
human-only and blocked from the phone/web bridge, because a hook runs an arbitrary command in
every matching session.

A Claude Code hook runs a command at a **lifecycle event** during a session — before or after a
tool runs, when the user submits a prompt, when the session starts, when the agent stops, and so
on. Omniscio already injects several of its own hooks into every spawned session (composed into
one session-private settings file). This panel lets you **see** those built-ins and **add your own**.

## Where to find it

### What you see on the screen

Open it from the **Agent Tools → Hooks** sidebar row. It's a **two-pane** surface (like MCP Servers
and Skills): a **list on the left**, the **details of the hook you click on the right**.

The left pane has a **Hooks | Sessions** tab strip. The **Hooks** tab lists your hooks in two groups:

1. **Built-in** — the hooks Omniscio composes automatically, shown read-mostly:
   - **Git Guardrails** (PreToolUse) — blocks risky git/file operations on protected branches;
     its full controls are embedded in its detail (the same toggle as Settings → Features).
   - **Secret Paste Guard** (PreToolUse), **Write-Time Lint** (PostToolUse), **Agent Firewall**
     (PostToolUse) — each shown when its own feature is enabled, managed from Settings → Features.
2. **Your hooks** — the hooks you define, plus an **Add hook** button. Empty until you add one.

Click any row and its detail opens on the right. For a **custom** hook the detail has two sub-tabs,
**Settings** and **Activity**; for a **built-in** hook it's a read-mostly Settings view.

The **Settings** sub-tab shows the hook's event, matcher, command, and timeout with a quick global
on/off, an **Edit** button (edits the fields inline, right in the pane), a **Delete**, and the
per-project overrides.

### Adding a custom hook

**Add hook** opens a form:

- **Name** — a label for the hook.
- **Event** — the lifecycle event (`PreToolUse`, `PostToolUse`, `Stop`, `SubagentStop`,
  `UserPromptSubmit`, `SessionStart`, `SessionEnd`, `Notification`, `PreCompact`).
- **Matcher** — only shown for the tool events (`PreToolUse` / `PostToolUse`); a tool-name pattern
  like `Bash|Edit` (or `*` for all tools).
- **Command** — the shell command Claude Code runs when the event fires.
- **Timeout** — how long the command may run (seconds).
- **Enabled** — the global on/off.

The command runs in the spawned session's own shell (exactly like a hook you'd write by hand in
`~/.claude/settings.json`) — Omniscio just composes it into the session for you.

### Global setting + per-project overrides

Each custom hook has a **global** on/off, plus **per-project overrides** (expand a hook's
"Project overrides"). An override forces the hook on or off for one project path and **wins over
the global setting** — so you can enable a hook everywhere but turn it off for one project, or the
reverse. When a session spawns, Omniscio resolves each hook for that session's project and composes
only the enabled ones.

### The Sessions tab — draft a hook with AI

The left pane's **Sessions** tab hosts AI helper sessions (the same session-host pattern as
Flowchart and the KMS). Start one and it helps you **design and draft** a hook — walking through the
event, matcher, command, and timeout — and hands you a finished spec to save. It **cannot save the
hook itself**: hook creation is human-only, so the helper drafts and you click **Add hook** to save
it. These sessions run in a managed scratch workspace, exactly like the other Agent Tools helpers.

### Activity — where a hook is active

A custom hook's **Activity** sub-tab shows where the hook is currently active: whether it's on
globally, and the list of your **projects** where it resolves enabled (after per-project overrides).
That's the honest, exact reach — every new session Omniscio spawns for one of those projects will
run the hook.

It does **not** show a log of individual firings. A Claude Code hook runs *inside* the spawned
session's own process, so Omniscio never sees each time it fires — surfacing that would mean adding a
command to your hook (slowing your sessions), which Omniscio deliberately does not do. The Activity
view is derived purely from your current hook configuration, so it costs nothing and never touches
your hook command.

## How it behaves

### Key facts

- **Omniscio-managed, local-only.** Custom hooks live in Omniscio's database and apply to the
  sessions Omniscio spawns. Your global `~/.claude/settings.json` is never read or written.
- **Composed into the one session settings file.** Custom hooks are appended to the same
  session-private `--settings` file Omniscio already uses for its built-in hooks — with a guarantee
  that a session with no custom hooks gets a byte-identical file to before (built-in behavior
  unchanged).
- **Human-only.** Only your full-trust action can create or edit a hook; an agent's scoped token
  can't, and the panel is blocked from the phone/web bridge — a hook can run any command, so this
  is a safety boundary.
- **Ships dark.** Hidden until enabled in Settings → Lab; landing the feature changes nothing for
  anyone until that toggle flips.
- **Built-ins are read-mostly.** The panel surfaces the built-in hooks and their live state;
  Git Guardrails is toggled inline (its existing human-only control), the others from
  Settings → Features.

## For agents

### Under the hood (for agents)

- Renderer (two-pane): [HooksSubSidebar.tsx](../../src/renderer/src/features/hooks/HooksSubSidebar.tsx)
  (Hooks|Sessions tabs) → [HooksList.tsx](../../src/renderer/src/features/hooks/HooksList.tsx) +
  [HooksSessionsList.tsx](../../src/renderer/src/features/hooks/HooksSessionsList.tsx); the detail
  pane [HooksView.tsx](../../src/renderer/src/features/hooks/HooksView.tsx) →
  [HookDetailSettings.tsx](../../src/renderer/src/features/hooks/HookDetailSettings.tsx) +
  [HookActivity.tsx](../../src/renderer/src/features/hooks/HookActivity.tsx) (custom) /
  [BuiltinHookDetail.tsx](../../src/renderer/src/features/hooks/BuiltinHookDetail.tsx) (built-in). The
  add/edit form + inline editor share [HookFormFields.tsx](../../src/renderer/src/features/hooks/HookFormFields.tsx)
  + [useHookFormState.ts](../../src/renderer/src/features/hooks/useHookFormState.ts). Store:
  [hooks-store.ts](../../src/renderer/src/stores/hooks-store.ts) (+ pure keys
  [hooks-keys.ts](../../src/renderer/src/stores/hooks-keys.ts)). The `hooks` integration manifest
  ([integrations/hooks.ts](../../src/shared/integrations/hooks.ts), `parentGroupId: 'agent-tools'`)
  registers `sidebarComponent` + `panelComponent` (not `panelOwnsLayout`); the `HOOKS_PROJECT_ID`
  (`__hooks__`) virtual project is gated by the `custom-hooks` unreleased-feature via
  `UNRELEASED_PROJECT_GATES`.
- Sessions tab: `HOOKS_PROJECT_ID` is spawnable (`SPAWNABLE_VIRTUAL_PROJECT_SENTINELS` +
  `MANAGED_WORKDIRS` → `<userData>/hooks-agent`), reached through the session-host seam
  (`useProjectSessionHost`, source `hooks-session-host`). The helper only drafts — mutation stays
  human-only.
- Activity: [custom-hook-activity.ts](../../src/main/services/hooks/custom-hook-activity.ts) resolves
  per-project reach via the canonical `resolveEnabledForProject`; exposed by the read-only
  `CUSTOM_HOOKS_ACTIVITY` IPC (web/WS-blocked, desktop-only). Derived, zero-capture — the composer is
  untouched.
- Composer: custom hooks are appended in
  [session-hooks-settings.ts](../../src/main/process/session-hooks-settings.ts) and resolved
  per-project at spawn ([spawn-cluster-manager.ts](../../src/main/process/spawn-cluster-manager.ts)).
- Data/service: [queries-custom-hooks.ts](../../src/main/db/queries-custom-hooks.ts) +
  [custom-hooks-service.ts](../../src/main/services/hooks/custom-hooks-service.ts).
- CLI: `/custom-hooks` routes (mutations require the full-trust token; the activity read has no CLI
  route). Behavior is locked by
  [hooks-panel-contract.md](../../.claude/memory/contracts/hooks-panel-contract.md).

## Related

The other agent-tool panels sit beside this one — Skills, MCP Servers and Browser Logins — and each has its own page in this library.
