crewship hooks
Manage the lifecycle-hook registry — shell commands, HTTP webhooks, or subagents that fire on platform events (pre_agent_start, post_agent_stop, on_approval_requested, …). See the Hooks guide for the full 14-event catalog and the three handler kinds. There is no pre_tool_call — the platform has no interception point before a tool runs. Every one of the 14 catalog events, including post_tool_call, now dispatches from a real call site — see Currently-dispatched events below.
Every write requires
OWNER or ADMIN. Creating or editing a shell
hook requires OWNER — a shell handler runs its command on the
crewshipd host, outside container isolation.Subcommands
hooks list, create, and update honour the global --format flag
(json/yaml/ndjson) — see Output Formats.
crewship hooks list
Sample output:
handler_config: the URL for http, the command for shell, the agent for subagent, truncated to 40 characters.
crewship hooks create
--event and --handler, plus a target for that handler kind.
New hooks are enabled unless you pass --disabled.
crewship hooks update <id>
create, all optional. Only the flags you pass are sent — an omitted flag keeps its current server-side value. If a blocking pre_* hook is changed to a post_* or on_* event, explicitly pass --blocking=false; the server refuses an observation event that retains the old blocking flag. Passing no flags at all is an error rather than an empty patch.
Converting a hook to --handler shell, or editing one that is already shell, requires OWNER.
crewship hooks delete <id>
Without
--yes the command refuses and points at crewship hooks disable, which stops the hook firing while keeping its definition.
crewship hooks enable <id>
OWNER or ADMIN (403 otherwise). Emits system.hook_toggled into the Crew Journal with the actor’s user ID.
crewship hooks disable <id>
Errors
Currently-dispatched events
Which events actually fire
Which events actually fire
All 14 events in the
--event catalog now dispatch from a real call
site — see the
Hooks guide coverage table for the
call site behind each one. internal/hooks/dispatch_site_test.go
enforces this as an invariant: a source-scan test fails CI if an event
is ever added to AllEvents without a matching hooks.Dispatch call
reachable from outside the hooks package.pre_tool_call used to be exactly the opposite trap — an event that
registered cleanly and never fired, with no “wire it up” path on the
roadmap — and was removed from the valid event list rather than left
there: it is the one event name that is now a 400, not a silently-dead
201.