mirror of
https://github.com/openai/codex.git
synced 2026-05-21 03:33:41 +00:00
# What <img width="1792" height="1024" alt="image" src="https://github.com/user-attachments/assets/8f81d232-5813-4994-a61d-e42a05a93a3e" /> `SubagentStop` runs when a thread-spawned subagent turn is about to finish. Thread-spawned subagents use `SubagentStop` instead of the normal root-agent `Stop` hook. Configured handlers match on `agent_type`. Hook input includes the normal stop fields plus: - `agent_id`: the child thread id. - `agent_type`: the resolved subagent type. - `agent_transcript_path`: the child subagent transcript path. - `transcript_path`: the parent thread transcript path. - `last_assistant_message`: the final assistant message from the child turn, when available. - `stop_hook_active`: `true` when the child is already continuing because an earlier stop-like hook blocked completion. `SubagentStop` shares the same completion-control semantics as `Stop`, scoped to the child turn: - No decision allows the child turn to finish. - `decision: "block"` with a non-empty `reason` records that reason as hook feedback and continues the child with that prompt. - `continue: false` stops the child turn. If `stopReason` is present, Codex surfaces it as the stop reason. # Lifecycle Scope Only thread-spawned subagents run `SubagentStop`. Internal/system subagents such as Review, Compact, MemoryConsolidation, and Other do not run normal `Stop` hooks and do not run `SubagentStop`. This avoids exposing synthetic matcher labels for internal implementation paths. # Stack 1. #22782: add `SubagentStart`. 2. This PR: add `SubagentStop`. 3. #22882: add subagent identity to normal hook inputs.
194 lines
4.1 KiB
JSON
Generated
194 lines
4.1 KiB
JSON
Generated
{
|
|
"$schema": "http://json-schema.org/draft-07/schema#",
|
|
"definitions": {
|
|
"AbsolutePathBuf": {
|
|
"description": "A path that is guaranteed to be absolute and normalized (though it is not guaranteed to be canonicalized or exist on the filesystem).\n\nIMPORTANT: When deserializing an `AbsolutePathBuf`, a base path must be set using [AbsolutePathBufGuard::new]. If no base path is set, the deserialization will fail unless the path being deserialized is already absolute.",
|
|
"type": "string"
|
|
},
|
|
"HookErrorInfo": {
|
|
"properties": {
|
|
"message": {
|
|
"type": "string"
|
|
},
|
|
"path": {
|
|
"type": "string"
|
|
}
|
|
},
|
|
"required": [
|
|
"message",
|
|
"path"
|
|
],
|
|
"type": "object"
|
|
},
|
|
"HookEventName": {
|
|
"enum": [
|
|
"preToolUse",
|
|
"permissionRequest",
|
|
"postToolUse",
|
|
"preCompact",
|
|
"postCompact",
|
|
"sessionStart",
|
|
"userPromptSubmit",
|
|
"subagentStart",
|
|
"subagentStop",
|
|
"stop"
|
|
],
|
|
"type": "string"
|
|
},
|
|
"HookHandlerType": {
|
|
"enum": [
|
|
"command",
|
|
"prompt",
|
|
"agent"
|
|
],
|
|
"type": "string"
|
|
},
|
|
"HookMetadata": {
|
|
"properties": {
|
|
"command": {
|
|
"type": [
|
|
"string",
|
|
"null"
|
|
]
|
|
},
|
|
"currentHash": {
|
|
"type": "string"
|
|
},
|
|
"displayOrder": {
|
|
"format": "int64",
|
|
"type": "integer"
|
|
},
|
|
"enabled": {
|
|
"type": "boolean"
|
|
},
|
|
"eventName": {
|
|
"$ref": "#/definitions/HookEventName"
|
|
},
|
|
"handlerType": {
|
|
"$ref": "#/definitions/HookHandlerType"
|
|
},
|
|
"isManaged": {
|
|
"type": "boolean"
|
|
},
|
|
"key": {
|
|
"type": "string"
|
|
},
|
|
"matcher": {
|
|
"type": [
|
|
"string",
|
|
"null"
|
|
]
|
|
},
|
|
"pluginId": {
|
|
"type": [
|
|
"string",
|
|
"null"
|
|
]
|
|
},
|
|
"source": {
|
|
"$ref": "#/definitions/HookSource"
|
|
},
|
|
"sourcePath": {
|
|
"$ref": "#/definitions/AbsolutePathBuf"
|
|
},
|
|
"statusMessage": {
|
|
"type": [
|
|
"string",
|
|
"null"
|
|
]
|
|
},
|
|
"timeoutSec": {
|
|
"format": "uint64",
|
|
"minimum": 0.0,
|
|
"type": "integer"
|
|
},
|
|
"trustStatus": {
|
|
"$ref": "#/definitions/HookTrustStatus"
|
|
}
|
|
},
|
|
"required": [
|
|
"currentHash",
|
|
"displayOrder",
|
|
"enabled",
|
|
"eventName",
|
|
"handlerType",
|
|
"isManaged",
|
|
"key",
|
|
"source",
|
|
"sourcePath",
|
|
"timeoutSec",
|
|
"trustStatus"
|
|
],
|
|
"type": "object"
|
|
},
|
|
"HookSource": {
|
|
"enum": [
|
|
"system",
|
|
"user",
|
|
"project",
|
|
"mdm",
|
|
"sessionFlags",
|
|
"plugin",
|
|
"cloudRequirements",
|
|
"legacyManagedConfigFile",
|
|
"legacyManagedConfigMdm",
|
|
"unknown"
|
|
],
|
|
"type": "string"
|
|
},
|
|
"HookTrustStatus": {
|
|
"enum": [
|
|
"managed",
|
|
"untrusted",
|
|
"trusted",
|
|
"modified"
|
|
],
|
|
"type": "string"
|
|
},
|
|
"HooksListEntry": {
|
|
"properties": {
|
|
"cwd": {
|
|
"type": "string"
|
|
},
|
|
"errors": {
|
|
"items": {
|
|
"$ref": "#/definitions/HookErrorInfo"
|
|
},
|
|
"type": "array"
|
|
},
|
|
"hooks": {
|
|
"items": {
|
|
"$ref": "#/definitions/HookMetadata"
|
|
},
|
|
"type": "array"
|
|
},
|
|
"warnings": {
|
|
"items": {
|
|
"type": "string"
|
|
},
|
|
"type": "array"
|
|
}
|
|
},
|
|
"required": [
|
|
"cwd",
|
|
"errors",
|
|
"hooks",
|
|
"warnings"
|
|
],
|
|
"type": "object"
|
|
}
|
|
},
|
|
"properties": {
|
|
"data": {
|
|
"items": {
|
|
"$ref": "#/definitions/HooksListEntry"
|
|
},
|
|
"type": "array"
|
|
}
|
|
},
|
|
"required": [
|
|
"data"
|
|
],
|
|
"title": "HooksListResponse",
|
|
"type": "object"
|
|
} |