Lifecycle Hooks
BMO exposes hook planes:
runloophooks run inside the BMO engine around inference and tool uselifecyclehooks run around session and agent-turn envelope eventsoutcomeshooks run after arena accept, stitch, verified file merge, arena workflow step completion, andorchestrate_workflow/execute_dagterminals (advisory only)options.automation.rulesis the canonical in-process follow-on layer for structured automation. Use reaction-style actions (run_recipe,notify,enqueue_job) for lightweight glue and activation-style actions for typed orchestration.
Hooks are external shell callbacks. Structured automation rules are separate from hooks and stay in-process.
For the broader orchestration map, see Workflow map and Staged Workflow.
For contributors: Deeper event-graph semantics live in the repository topics
reactions.mdandactivation-graph.md.
Hooks are shell commands. Blocking behavior depends on the specific hook event; it is not uniform across the whole surface.
Configuration
Section titled “Configuration”[options.hooks.runloop] [[options.hooks.runloop.pre_tool_use]] type = "command" command = "check-tool-policy" timeout = 30
[[options.hooks.runloop.post_tool_use]] type = "command" command = "audit-log-tool"
[[options.hooks.runloop.pre_inference]] type = "command" command = "check-budget"
[[options.hooks.runloop.post_inference]] type = "command" command = "log-tokens"
[options.hooks.lifecycle] [[options.hooks.lifecycle.session_start]] type = "command" command = "notify-start"
[[options.hooks.lifecycle.session_end]] type = "command" command = "notify-end"
[[options.hooks.lifecycle.before_agent]] type = "command" command = "validate-context"
[[options.hooks.lifecycle.after_agent]] type = "command" command = "summarize-turn"
[options.hooks.outcomes] [[options.hooks.outcomes.arena_accepted]] type = "command" command = "jq . >&2" timeout = 30
[[options.hooks.outcomes.arena_stitched]] type = "command" command = "jq . >&2"
[[options.hooks.outcomes.arena_merged]] type = "command" command = "jq . >&2"
[[options.hooks.outcomes.arena_workflow_step_completed]] type = "command" command = "jq . >&2"
[[options.hooks.outcomes.workflow_completed]] type = "command" command = "jq . >&2"
[[options.hooks.outcomes.workflow_failed]] type = "command" command = "jq . >&2"Configure hooks only through the nested runloop and lifecycle sections.
Runloop Hooks
Section titled “Runloop Hooks”These hooks are converted into the BMO engine runloop hook chain.
| Hook | Blocking | Description |
|---|---|---|
pre_tool_use | Yes | Runs before each tool call; exit 2 blocks the call and stderr becomes the tool result |
post_tool_use | No | Runs after each tool call; best-effort |
pre_inference | No | Runs before each LLM inference call; command failures are advisory |
post_inference | No | Runs after each LLM inference call; command failures are advisory |
Lifecycle Hooks
Section titled “Lifecycle Hooks”These hooks stay outside the BMO engine and wrap session or turn lifecycle.
| Hook | Blocking | Description |
|---|---|---|
session_start | No | Runs when a session is created; advisory, non-blocking |
session_end | No | Runs when a session is deleted; best-effort |
before_agent | Yes | Runs at the start of each agent turn; exit 2 blocks the turn |
after_agent | No | Runs at the end of each agent turn; best-effort |
Outcome hooks (arena, arena workflow, DAG tools)
Section titled “Outcome hooks (arena, arena workflow, DAG tools)”These run after the corresponding coordinator success paths, in a background goroutine (they do not delay accept/stitch/merge in the UI). Exit code 2 does not block BMO; it is logged like any other non-zero exit.
| Hook | Blocking | Description |
|---|---|---|
arena_accepted | No | After a successful arena candidate accept |
arena_stitched | No | After a successful arena prose stitch |
arena_merged | No | After a successful verified arena file merge (arena_merge / HTTP / MCP) |
arena_workflow_step_completed | No | After an arena workflow step is marked completed |
workflow_completed | No | After orchestrate_workflow or execute_dag finishes with all nodes completed |
workflow_failed | No | After those tools finish with failures, skipped nodes, or an executor error |
Stdin JSON includes schema_version (currently 1), event (e.g. arena_accepted, arena_merged, workflow_completed), session_id, and event-specific fields (user_message_id, model_key, candidate_id, assistant_message_id, candidate_ids, merge_signature, merged_paths, workflow_id, step_id, phase, workflow_run_id, workflow_tool, workflow_source, etc.). See the generated configuration reference for the full field list.
Hook Entry Fields
Section titled “Hook Entry Fields”| Field | Required | Description |
|---|---|---|
type | Yes | Always "command" |
command | Yes | Shell command to execute |
timeout | No | Timeout in seconds (default: 30) |
Hook Input
Section titled “Hook Input”Hooks inherit the normal BMO process environment. BMO-specific hook context is
passed on stdin as JSON.
Runloop hook input includes event-specific fields such as:
- inference hooks:
hook_event,model - tool hooks:
hook_event,tool_name,tool_id,arguments
Lifecycle hook input includes event-specific fields such as:
session_start:hook_event,session_id,cwd,titlesession_end:hook_event,session_id,cwdbefore_agent:hook_event,session_id,cwd,prompt_previewafter_agent:hook_event,session_id,cwd,completed,error_preview
Team Lifecycle Hooks
Section titled “Team Lifecycle Hooks”For team quality gates, use team_hooks instead:
[[options.team_hooks.teammate_idle]]type = "command"command = "validate-output"
[[options.team_hooks.task_completed]]type = "command"command = "run-acceptance-tests"| Hook | Description |
|---|---|
teammate_idle | Runs when a teammate finishes its turn; exit 2 blocks idle and re-injects stderr |
task_completed | Runs when a task is marked completed; exit 2 blocks completion |
Use Cases
Section titled “Use Cases”- Audit logging — record every tool call to a file or external system
- Budget checks —
pre_inferencehook records or warns on budget state before inference - Policy gates —
pre_tool_usehook blocks destructive operations in production environments - Notifications —
session_start/session_endhooks send Slack or webhook messages
Related
Section titled “Related”- Configuration — hook tables, automation rules, and compatibility aliases
- Workflow map — how hooks sit alongside staged workflows, mesh, and compaction
- How BMO thinks and acts — system-level coordination model