@scotthuang/agent-knock-knock 0.13.18 → 0.14.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (289) hide show
  1. package/CHANGELOG.md +41 -0
  2. package/CONTRIBUTING.md +212 -0
  3. package/README.md +106 -166
  4. package/connectors/deepseek-harness/LICENSE +21 -0
  5. package/connectors/deepseek-harness/README.md +406 -0
  6. package/connectors/pi/LICENSE +21 -0
  7. package/connectors/pi/README.md +446 -0
  8. package/dist/src/backend-public-progress.d.ts +38 -0
  9. package/dist/src/backend-public-progress.js +106 -0
  10. package/dist/src/backend-public-progress.js.map +1 -0
  11. package/dist/src/backend-recovery-semantic.d.ts +16 -0
  12. package/dist/src/backend-recovery-semantic.js +113 -0
  13. package/dist/src/backend-recovery-semantic.js.map +1 -0
  14. package/dist/src/backend-task-recovery.d.ts +103 -0
  15. package/dist/src/backend-task-recovery.js +143 -0
  16. package/dist/src/backend-task-recovery.js.map +1 -0
  17. package/dist/src/callback-transport.d.ts +8 -0
  18. package/dist/src/callback-transport.js +14 -0
  19. package/dist/src/callback-transport.js.map +1 -1
  20. package/dist/src/cli-core.js +20 -10
  21. package/dist/src/cli-core.js.map +1 -1
  22. package/dist/src/cli-runtime-context.d.ts +5 -0
  23. package/dist/src/cli-runtime-context.js.map +1 -1
  24. package/dist/src/codex-app-server-read-client.d.ts +3 -0
  25. package/dist/src/codex-app-server-read-client.js.map +1 -1
  26. package/dist/src/codex-native-cli-adapter.d.ts +6 -0
  27. package/dist/src/codex-native-cli-adapter.js +303 -0
  28. package/dist/src/codex-native-cli-adapter.js.map +1 -0
  29. package/dist/src/codex-native-client-interactions.d.ts +6 -0
  30. package/dist/src/codex-native-client-interactions.js +124 -0
  31. package/dist/src/codex-native-client-interactions.js.map +1 -0
  32. package/dist/src/codex-native-client-rpc.d.ts +21 -0
  33. package/dist/src/codex-native-client-rpc.js +137 -0
  34. package/dist/src/codex-native-client-rpc.js.map +1 -0
  35. package/dist/src/codex-native-client.d.ts +42 -0
  36. package/dist/src/codex-native-client.js +331 -0
  37. package/dist/src/codex-native-client.js.map +1 -0
  38. package/dist/src/codex-native-identity.d.ts +6 -0
  39. package/dist/src/codex-native-identity.js +42 -0
  40. package/dist/src/codex-native-identity.js.map +1 -0
  41. package/dist/src/codex-native-monitor.d.ts +4 -0
  42. package/dist/src/codex-native-monitor.js +92 -0
  43. package/dist/src/codex-native-monitor.js.map +1 -0
  44. package/dist/src/codex-native-outbox.d.ts +16 -0
  45. package/dist/src/codex-native-outbox.js +120 -0
  46. package/dist/src/codex-native-outbox.js.map +1 -0
  47. package/dist/src/codex-native-public-projection.d.ts +545 -0
  48. package/dist/src/codex-native-public-projection.js +182 -0
  49. package/dist/src/codex-native-public-projection.js.map +1 -0
  50. package/dist/src/codex-native-record-store.d.ts +27 -0
  51. package/dist/src/codex-native-record-store.js +111 -0
  52. package/dist/src/codex-native-record-store.js.map +1 -0
  53. package/dist/src/codex-native-response-service.d.ts +69 -0
  54. package/dist/src/codex-native-response-service.js +244 -0
  55. package/dist/src/codex-native-response-service.js.map +1 -0
  56. package/dist/src/codex-native-runtime.d.ts +46 -0
  57. package/dist/src/codex-native-runtime.js +112 -0
  58. package/dist/src/codex-native-runtime.js.map +1 -0
  59. package/dist/src/codex-native-semantic.d.ts +17 -0
  60. package/dist/src/codex-native-semantic.js +175 -0
  61. package/dist/src/codex-native-semantic.js.map +1 -0
  62. package/dist/src/codex-native-snapshot.d.ts +19 -0
  63. package/dist/src/codex-native-snapshot.js +160 -0
  64. package/dist/src/codex-native-snapshot.js.map +1 -0
  65. package/dist/src/codex-native-state-store.d.ts +61 -0
  66. package/dist/src/codex-native-state-store.js +132 -0
  67. package/dist/src/codex-native-state-store.js.map +1 -0
  68. package/dist/src/codex-native-task-service.d.ts +71 -0
  69. package/dist/src/codex-native-task-service.js +503 -0
  70. package/dist/src/codex-native-task-service.js.map +1 -0
  71. package/dist/src/codex-native-types.d.ts +92 -0
  72. package/dist/src/codex-native-types.js +15 -0
  73. package/dist/src/codex-native-types.js.map +1 -0
  74. package/dist/src/conversation-list.d.ts +12 -0
  75. package/dist/src/conversation-list.js +30 -0
  76. package/dist/src/conversation-list.js.map +1 -0
  77. package/dist/src/conversation-route-dispatch.d.ts +13 -0
  78. package/dist/src/conversation-route-dispatch.js +66 -0
  79. package/dist/src/conversation-route-dispatch.js.map +1 -0
  80. package/dist/src/conversation-route-legacy.d.ts +18 -0
  81. package/dist/src/conversation-route-legacy.js +54 -0
  82. package/dist/src/conversation-route-legacy.js.map +1 -0
  83. package/dist/src/conversation-route-store.d.ts +51 -0
  84. package/dist/src/conversation-route-store.js +126 -0
  85. package/dist/src/conversation-route-store.js.map +1 -0
  86. package/dist/src/conversation-routing-cli-adapter.d.ts +12 -0
  87. package/dist/src/conversation-routing-cli-adapter.js +211 -0
  88. package/dist/src/conversation-routing-cli-adapter.js.map +1 -0
  89. package/dist/src/conversation-routing-commands.d.ts +11 -0
  90. package/dist/src/conversation-routing-commands.js +85 -0
  91. package/dist/src/conversation-routing-commands.js.map +1 -0
  92. package/dist/src/conversation-routing-home.d.ts +26 -0
  93. package/dist/src/conversation-routing-home.js +105 -0
  94. package/dist/src/conversation-routing-home.js.map +1 -0
  95. package/dist/src/conversation-routing-identity.d.ts +40 -0
  96. package/dist/src/conversation-routing-identity.js +174 -0
  97. package/dist/src/conversation-routing-identity.js.map +1 -0
  98. package/dist/src/conversation-runtime-route-store.d.ts +11 -0
  99. package/dist/src/conversation-runtime-route-store.js +118 -0
  100. package/dist/src/conversation-runtime-route-store.js.map +1 -0
  101. package/dist/src/desktop-async-interactions.d.ts +15 -0
  102. package/dist/src/desktop-async-interactions.js +88 -0
  103. package/dist/src/desktop-async-interactions.js.map +1 -0
  104. package/dist/src/desktop-async-state.d.ts +5 -0
  105. package/dist/src/desktop-async-state.js +53 -0
  106. package/dist/src/desktop-async-state.js.map +1 -0
  107. package/dist/src/desktop-cli-adapter.d.ts +7 -0
  108. package/dist/src/desktop-cli-adapter.js +343 -0
  109. package/dist/src/desktop-cli-adapter.js.map +1 -0
  110. package/dist/src/desktop-cli-controls.d.ts +9 -0
  111. package/dist/src/desktop-cli-controls.js +45 -0
  112. package/dist/src/desktop-cli-controls.js.map +1 -0
  113. package/dist/src/desktop-command-presentation.d.ts +2 -0
  114. package/dist/src/desktop-command-presentation.js +31 -0
  115. package/dist/src/desktop-command-presentation.js.map +1 -0
  116. package/dist/src/desktop-control-semantic.d.ts +8 -0
  117. package/dist/src/desktop-control-semantic.js +68 -0
  118. package/dist/src/desktop-control-semantic.js.map +1 -0
  119. package/dist/src/desktop-identity.d.ts +5 -0
  120. package/dist/src/desktop-identity.js +40 -0
  121. package/dist/src/desktop-identity.js.map +1 -0
  122. package/dist/src/desktop-interaction-projection.d.ts +57 -0
  123. package/dist/src/desktop-interaction-projection.js +196 -0
  124. package/dist/src/desktop-interaction-projection.js.map +1 -0
  125. package/dist/src/desktop-interaction-state.d.ts +3 -0
  126. package/dist/src/desktop-interaction-state.js +48 -0
  127. package/dist/src/desktop-interaction-state.js.map +1 -0
  128. package/dist/src/desktop-ipc-async-answer.d.ts +9 -0
  129. package/dist/src/desktop-ipc-async-answer.js +71 -0
  130. package/dist/src/desktop-ipc-async-answer.js.map +1 -0
  131. package/dist/src/desktop-ipc-client.d.ts +47 -0
  132. package/dist/src/desktop-ipc-client.js +400 -0
  133. package/dist/src/desktop-ipc-client.js.map +1 -0
  134. package/dist/src/desktop-ipc-native-operations.d.ts +11 -0
  135. package/dist/src/desktop-ipc-native-operations.js +126 -0
  136. package/dist/src/desktop-ipc-native-operations.js.map +1 -0
  137. package/dist/src/desktop-ipc-transport.d.ts +13 -0
  138. package/dist/src/desktop-ipc-transport.js +123 -0
  139. package/dist/src/desktop-ipc-transport.js.map +1 -0
  140. package/dist/src/desktop-list.d.ts +25 -0
  141. package/dist/src/desktop-list.js +55 -0
  142. package/dist/src/desktop-list.js.map +1 -0
  143. package/dist/src/desktop-metadata-reader.d.ts +30 -0
  144. package/dist/src/desktop-metadata-reader.js +182 -0
  145. package/dist/src/desktop-metadata-reader.js.map +1 -0
  146. package/dist/src/desktop-monitor.d.ts +4 -0
  147. package/dist/src/desktop-monitor.js +101 -0
  148. package/dist/src/desktop-monitor.js.map +1 -0
  149. package/dist/src/desktop-public-projection.d.ts +6 -0
  150. package/dist/src/desktop-public-projection.js +134 -0
  151. package/dist/src/desktop-public-projection.js.map +1 -0
  152. package/dist/src/desktop-request-interactions.d.ts +14 -0
  153. package/dist/src/desktop-request-interactions.js +144 -0
  154. package/dist/src/desktop-request-interactions.js.map +1 -0
  155. package/dist/src/desktop-response-dispatch.d.ts +14 -0
  156. package/dist/src/desktop-response-dispatch.js +19 -0
  157. package/dist/src/desktop-response-dispatch.js.map +1 -0
  158. package/dist/src/desktop-response-evidence.d.ts +4 -0
  159. package/dist/src/desktop-response-evidence.js +19 -0
  160. package/dist/src/desktop-response-evidence.js.map +1 -0
  161. package/dist/src/desktop-response-service.d.ts +11 -0
  162. package/dist/src/desktop-response-service.js +188 -0
  163. package/dist/src/desktop-response-service.js.map +1 -0
  164. package/dist/src/desktop-response-store.d.ts +35 -0
  165. package/dist/src/desktop-response-store.js +58 -0
  166. package/dist/src/desktop-response-store.js.map +1 -0
  167. package/dist/src/desktop-response-types.d.ts +20 -0
  168. package/dist/src/desktop-response-types.js +2 -0
  169. package/dist/src/desktop-response-types.js.map +1 -0
  170. package/dist/src/desktop-response-value.d.ts +6 -0
  171. package/dist/src/desktop-response-value.js +31 -0
  172. package/dist/src/desktop-response-value.js.map +1 -0
  173. package/dist/src/desktop-runtime.d.ts +153 -0
  174. package/dist/src/desktop-runtime.js +88 -0
  175. package/dist/src/desktop-runtime.js.map +1 -0
  176. package/dist/src/desktop-semantic.d.ts +21 -0
  177. package/dist/src/desktop-semantic.js +140 -0
  178. package/dist/src/desktop-semantic.js.map +1 -0
  179. package/dist/src/desktop-session-catalog.d.ts +68 -0
  180. package/dist/src/desktop-session-catalog.js +225 -0
  181. package/dist/src/desktop-session-catalog.js.map +1 -0
  182. package/dist/src/desktop-session-controls.d.ts +145 -0
  183. package/dist/src/desktop-session-controls.js +176 -0
  184. package/dist/src/desktop-session-controls.js.map +1 -0
  185. package/dist/src/desktop-sidebar-metadata.d.ts +27 -0
  186. package/dist/src/desktop-sidebar-metadata.js +83 -0
  187. package/dist/src/desktop-sidebar-metadata.js.map +1 -0
  188. package/dist/src/desktop-sidebar-projects.d.ts +10 -0
  189. package/dist/src/desktop-sidebar-projects.js +31 -0
  190. package/dist/src/desktop-sidebar-projects.js.map +1 -0
  191. package/dist/src/desktop-sidebar-selection.d.ts +28 -0
  192. package/dist/src/desktop-sidebar-selection.js +85 -0
  193. package/dist/src/desktop-sidebar-selection.js.map +1 -0
  194. package/dist/src/desktop-snapshot-details.d.ts +4 -0
  195. package/dist/src/desktop-snapshot-details.js +116 -0
  196. package/dist/src/desktop-snapshot-details.js.map +1 -0
  197. package/dist/src/desktop-snapshot.d.ts +11 -0
  198. package/dist/src/desktop-snapshot.js +281 -0
  199. package/dist/src/desktop-snapshot.js.map +1 -0
  200. package/dist/src/desktop-state-store.d.ts +72 -0
  201. package/dist/src/desktop-state-store.js +269 -0
  202. package/dist/src/desktop-state-store.js.map +1 -0
  203. package/dist/src/desktop-task-interactions.d.ts +10 -0
  204. package/dist/src/desktop-task-interactions.js +93 -0
  205. package/dist/src/desktop-task-interactions.js.map +1 -0
  206. package/dist/src/desktop-task-recovery.d.ts +38 -0
  207. package/dist/src/desktop-task-recovery.js +172 -0
  208. package/dist/src/desktop-task-recovery.js.map +1 -0
  209. package/dist/src/desktop-task-service.d.ts +54 -0
  210. package/dist/src/desktop-task-service.js +442 -0
  211. package/dist/src/desktop-task-service.js.map +1 -0
  212. package/dist/src/desktop-types.d.ts +283 -0
  213. package/dist/src/desktop-types.js +13 -0
  214. package/dist/src/desktop-types.js.map +1 -0
  215. package/dist/src/host-monitor-reconciliation.js +36 -4
  216. package/dist/src/host-monitor-reconciliation.js.map +1 -1
  217. package/dist/src/host-profile-runtime.js +7 -3
  218. package/dist/src/host-profile-runtime.js.map +1 -1
  219. package/dist/src/local-codex-cli-adapter.d.ts +7 -0
  220. package/dist/src/local-codex-cli-adapter.js +13 -0
  221. package/dist/src/local-codex-cli-adapter.js.map +1 -0
  222. package/dist/src/monitor-deadline-policy.d.ts +8 -0
  223. package/dist/src/monitor-deadline-policy.js +16 -0
  224. package/dist/src/monitor-deadline-policy.js.map +1 -0
  225. package/dist/src/openclaw-callback-transport.js +2 -1
  226. package/dist/src/openclaw-callback-transport.js.map +1 -1
  227. package/dist/src/semantic-conversation-target.d.ts +4 -0
  228. package/dist/src/semantic-conversation-target.js +20 -0
  229. package/dist/src/semantic-conversation-target.js.map +1 -0
  230. package/dist/src/semantic-permission-control.js +47 -9
  231. package/dist/src/semantic-permission-control.js.map +1 -1
  232. package/dist/src/semantic-private-authority-offers.d.ts +1 -1
  233. package/dist/src/semantic-private-authority-offers.js +3 -1
  234. package/dist/src/semantic-private-authority-offers.js.map +1 -1
  235. package/dist/src/semantic-tool-command-helpers.d.ts +6 -0
  236. package/dist/src/semantic-tool-command-helpers.js +199 -78
  237. package/dist/src/semantic-tool-command-helpers.js.map +1 -1
  238. package/dist/src/semantic-tool-descriptions.d.ts +2 -1
  239. package/dist/src/semantic-tool-descriptions.js +84 -35
  240. package/dist/src/semantic-tool-descriptions.js.map +1 -1
  241. package/dist/src/semantic-tool-list-projection.js +66 -2
  242. package/dist/src/semantic-tool-list-projection.js.map +1 -1
  243. package/dist/src/semantic-tool-presentation.js +76 -7
  244. package/dist/src/semantic-tool-presentation.js.map +1 -1
  245. package/dist/src/semantic-tool-runtime.js +129 -29
  246. package/dist/src/semantic-tool-runtime.js.map +1 -1
  247. package/dist/src/semantic-tool-schemas.d.ts +410 -27
  248. package/dist/src/semantic-tool-schemas.js +176 -88
  249. package/dist/src/semantic-tool-schemas.js.map +1 -1
  250. package/dist/src/terminal-action-contracts.js +10 -6
  251. package/dist/src/terminal-action-contracts.js.map +1 -1
  252. package/dist/src/terminal-command-cli-adapter.js +4 -4
  253. package/dist/src/terminal-command-cli-adapter.js.map +1 -1
  254. package/dist/src/terminal-command-dispatch-preparation.js +2 -1
  255. package/dist/src/terminal-command-dispatch-preparation.js.map +1 -1
  256. package/dist/src/terminal-list-cli-adapter.d.ts +1 -0
  257. package/dist/src/terminal-list-cli-adapter.js +6 -3
  258. package/dist/src/terminal-list-cli-adapter.js.map +1 -1
  259. package/dist/src/terminal-monitor-decision-policy.d.ts +1 -1
  260. package/dist/src/terminal-monitor-launch-plan.js +3 -2
  261. package/dist/src/terminal-monitor-launch-plan.js.map +1 -1
  262. package/dist/src/terminal-monitor-supervision-cli-adapter.js +2 -2
  263. package/dist/src/terminal-monitor-supervision-cli-adapter.js.map +1 -1
  264. package/dist/src/terminal-submission-retry-reconciliation.js +2 -2
  265. package/dist/src/terminal-submission-retry-reconciliation.js.map +1 -1
  266. package/dist/src/terminal-user-send-intent.d.ts +2 -0
  267. package/dist/src/terminal-user-send-intent.js +11 -3
  268. package/dist/src/terminal-user-send-intent.js.map +1 -1
  269. package/dist/src/terminal-watch-cli-adapter.js +4 -4
  270. package/dist/src/terminal-watch-cli-adapter.js.map +1 -1
  271. package/docs/architecture/current-architecture.md +313 -0
  272. package/docs/architecture/interactive-terminal-response.md +276 -0
  273. package/docs/architecture/issue-126-final-report.md +248 -0
  274. package/docs/architecture/orchestration-refactor-history.md +2987 -0
  275. package/docs/architecture/orchestration-refactor.md +21 -0
  276. package/docs/backend-task-recovery.md +98 -0
  277. package/docs/bidirectional-agent-protocol.md +260 -0
  278. package/docs/codex-cli-native-compatibility.md +246 -0
  279. package/docs/codex-desktop-compatibility.md +414 -0
  280. package/docs/openclaw-operations.md +281 -0
  281. package/docs/openclaw-session-turn-delivery-requirement.md +45 -0
  282. package/docs/operator-guide.md +572 -0
  283. package/docs/storage-and-logging.md +91 -0
  284. package/docs/test-performance-issue-108.md +80 -0
  285. package/docs/test-performance-issue-120.md +226 -0
  286. package/docs/testing.md +628 -0
  287. package/openclaw.plugin.json +8 -4
  288. package/package.json +6 -13
  289. package/templates/openclaw-skills/agent-knock-knock/SKILL.md +66 -15
@@ -0,0 +1,21 @@
1
+ # Orchestration architecture documents
2
+
3
+ This path is a stable index. It intentionally contains no current tool count,
4
+ Store protocol number, action-contract version, or module-size snapshot.
5
+
6
+ Use these documents according to purpose:
7
+
8
+ - [Current architecture and health budget](./current-architecture.md) is the
9
+ only authoritative description of the source tree and public surface now.
10
+ - [Issue #126 orchestration refactor history](./orchestration-refactor-history.md)
11
+ is an immutable chronological record of the v0.12 refactor baseline, phase
12
+ reports, and later issue addenda. Numbers such as 14 or 16 tools, Watch v2,
13
+ and writer protocol 6 describe their explicitly dated historical snapshot;
14
+ they are not current product documentation.
15
+ - [Issue #126 final report](./issue-126-final-report.md) records that refactor's
16
+ closeout evidence.
17
+ - [Interactive terminal response](./interactive-terminal-response.md) describes
18
+ the dedicated questionnaire-response architecture.
19
+
20
+ For operator workflows and the current semantic-tool surface, use the
21
+ [operator guide](../operator-guide.md) and the canonical packaged Skill.
@@ -0,0 +1,98 @@
1
+ # Backend task recovery
2
+
3
+ AKK 0.14.0 introduces exact-task recovery for its backend adapters. See the
4
+ [README](../README.md) for installation and the first-task workflow.
5
+
6
+ Codex CLI direct connections and Codex Desktop use persisted exact task identities
7
+ for recovery. These operations do not require tmux or Herdr and do not send task
8
+ text, slash commands, approvals, cancellation, or lifecycle commands to Codex.
9
+
10
+ ## Management and observation
11
+
12
+ A backend Send creates a managed task with automatic observation. Its response
13
+ includes `turn_id` and `watch_id` identifying that same stored record. A standalone
14
+ Watch observes an existing task and does not acquire Send management. Inspect
15
+ `task_kind`, `management_state`, and `observation_state` separately.
16
+
17
+ | Operation | Meaning |
18
+ | --- | --- |
19
+ | `unwatch({watch_id})` | Stop observation and withdraw notifications not yet dispatched. A managed Send stays managed. |
20
+ | `close({turn_id})` | Close a managed Send, stop observation, and release its AKK management. A standalone Watch must use Unwatch. |
21
+ | `renew({watch_id, minutes})` | Verify the original task and extend observation; an expired or explicitly stopped Watch can resume while that same task is still active. |
22
+ | `recover({watch_id})` | Reconnect/read the original task, reconcile its receipt and state, and supervise eligible monitor work. Does not extend the deadline or resume an explicitly stopped Watch. |
23
+ | `retry_callback({watch_id, notification_id})` | Retry one persisted notification with its original event ID and controller target. Does not rerun the task. |
24
+
25
+ The tool prefix is `agent_knock_knock_`. Native Send `turn_id` is also accepted
26
+ by Recover, Renew, Close, Retry Callback, and Status. Unwatch uses `watch_id`.
27
+ Copy the exact IDs and available actions
28
+ from Send, List or Status. A conversation ID alone cannot select a task to close,
29
+ renew, recover, or retry. Multiple eligible failed notifications require an
30
+ explicit `notification_id`.
31
+
32
+ Starting in AKK 0.14.1, backend Renew with no explicit
33
+ `minutes` uses the Host's `agentHardTimeoutMinutes`, then the shared 720-minute
34
+ default. It sets the deadline to the later of the saved deadline and now plus
35
+ that duration; it does not add the duration to the old deadline. Terminal managed
36
+ Renew still refreshes its inactivity window (default 60 minutes) and cannot
37
+ exceed its original hard lifetime. Recover does not renew either deadline.
38
+ An upgrade alone never extends saved deadlines, revives expired observation or
39
+ replays accepted notifications.
40
+
41
+ Closed management cannot be reopened. Unwatch does not release an unresolved
42
+ Send reservation; Close explicitly releases management without asserting that
43
+ the native submission failed. Reusing the original Send message ID still returns
44
+ its original record and never resends its text. None of these operations cancels
45
+ the actual Codex task or closes its conversation.
46
+
47
+ ## Identity and outcomes
48
+
49
+ Close and Unwatch update the saved AKK record and do not require reconnecting
50
+ to Codex. Recover and Renew read the original native task. Retry Callback reuses
51
+ the saved notification; an interaction notification additionally requires fresh
52
+ confirmation that its original question or approval is still pending. These
53
+ different checks do not rediscover or select another task.
54
+
55
+ Recovery uses the saved Codex home, thread, native turn, original submission
56
+ receipt and client message identity. It never substitutes the latest task, a
57
+ matching project directory, or another terminal. If the original task cannot be
58
+ verified, it remains unknown rather than being rebound. Renewal requires exact
59
+ task evidence; if that task has already settled, its actual outcome is recorded
60
+ instead of declaring it running. Each new observation deadline has its own
61
+ timeout notification generation; old unsent expiry notices are withdrawn.
62
+
63
+ Manual callback retry accepts only a recorded `retryable_failure`, including a
64
+ failure whose automatic attempts were exhausted. It preserves the notification
65
+ body, destination, event ID and cumulative attempt history. It cannot replay an
66
+ accepted notification, an in-flight attempt, an uncertain result, or a withdrawn
67
+ or obsolete interaction. Interaction notifications require fresh evidence that
68
+ the same question or approval is still pending. A closed or unwatched record
69
+ cannot dispatch callbacks. Already in-flight notifications cannot be recalled;
70
+ their eventual acknowledgement remains visible.
71
+
72
+ Callback acceptance means that the controller accepted the notification. It
73
+ does not prove that a downstream channel, such as WeChat, delivered a user-visible
74
+ message. Retry Callback is not a repair for a controller-to-channel failure.
75
+
76
+ ## Terminal recovery remains separate
77
+
78
+ Existing terminal `reconcile_binding`, `identify_foreground`, and
79
+ `repair_model_control` repair or inspect a physical terminal binding or menu.
80
+ They retain their terminal requirements. Backend `recover` reconciles an exact
81
+ stored task; it does not detach a terminal binding or manufacture new authority.
82
+ Native conversation creation, clearing, restoration, model controls, and
83
+ cancellation retain their separately documented provider capabilities.
84
+
85
+ ## Validation boundary
86
+
87
+ The backend recovery paths are covered by the fast regression tier, including
88
+ ownership, exact task retention, expired/stopped observation, duplicate and
89
+ uncertain sends, callback leases and retry identity. This change does not itself
90
+ establish a new live Desktop/CLI or user-visible channel delivery result. Existing
91
+ user sessions and historical notifications must not be used as implicit tests.
92
+
93
+ Development validation on 2026-10-10: `npm run test:fast` passed all 2,788 tests
94
+ and its build/Skill synchronization gates. `npm run validate:architecture` and
95
+ `npm run validate:refactor-evidence` also passed. Full, integration and release
96
+ tiers were not run during that development check, in accordance with the
97
+ repository test policy. This records development evidence, not the separate
98
+ publication gate.
@@ -0,0 +1,260 @@
1
+ # Terminal Handoff Protocol
2
+
3
+ Agent Knock Knock coordinates a controller Host, a local coding agent, and a human through one visible tmux or Herdr terminal.
4
+
5
+ - OpenClaw, Pi, DeepSeek Harness, or another compatible Host is the orchestrator, requirements owner, and final acceptance decision maker.
6
+ - Codex or Claude Code performs the engineering work inside tmux or Herdr.
7
+ - AKK owns terminal delivery, monitoring, lifecycle state, and callbacks.
8
+ - A human can attach to the same terminal at any time, continue directly, and later hand control back to the Host.
9
+ - AKK sends input only after it verifies the selected agent, pane, process, pane/process working directory, approval state, and action-specific composer. Managed paths require idle; an advertised user-explicit physical Send may steer a working mutable composer.
10
+ - AKK labels the evidence behind every notification. Managed Turns and exact-task Watches report completion only from correlated evidence; a user-selected terminal-activity Watch may instead report a clearly marked best-effort stable-idle observation that is not exact task-completion proof.
11
+
12
+ ## Identity Model
13
+
14
+ AKK models shared work as:
15
+
16
+ ```text
17
+ tmux or Herdr terminal / verified process incarnation
18
+ ├─ native Codex or Claude Code session
19
+ │ └─ AKK session (session_id)
20
+ │ ├─ Turn (turn_id)
21
+ │ └─ Turn (turn_id)
22
+ └─ Terminal Watch schema v3 (watch_id + exact task anchor or terminal-activity epoch)
23
+ ```
24
+
25
+ - The terminal is the physical pane and coding-agent process incarnation.
26
+ - The native session is the continuing context owned by Codex or Claude Code.
27
+ - The AKK `session_id` identifies a continuing context and is the strict `session_exact` send target. The physical `terminal_id` is the separate `terminal_follow_current` or user-priority `terminal_user_explicit` send target, exactly as advertised.
28
+ - A `turn_id` identifies exactly one accepted dispatch through its final monitor and callback state.
29
+ - A `watch_id` identifies an independent observation aggregate for a user-selected exact terminal. It prefers one provider-correlated task, may fall back to that terminal/process activity epoch, and may also identify one exact request already delivered through user-explicit unmanaged fallback. It is never a Session, Turn, dispatch receipt, or terminal owner. A new exact Watch may hold a narrowly scoped native-interaction response lease, but only after same-controller Status and fresh exact terminal/native-task revalidation; activity Watches never receive such authority.
30
+ - A terminal binding generation identifies one verified terminal-to-native-thread attachment. Native lifecycle transitions advance it even though they create no Turn.
31
+
32
+ List and Status preserve three independent evidence axes. `screen_state`
33
+ classifies the bounded live TUI, `native_identity_state` reports whether the
34
+ foreground native session is resolved, ambiguous, verified absent, or
35
+ unavailable, and `durable_activity_state` reports exact artifact-backed task
36
+ activity when available. The legacy `activity_state` remains conservative for
37
+ compatibility; it can be `unknown` while the screen is visibly idle because
38
+ native identity or durable activity is ambiguous. These axes are diagnostic
39
+ and never replace a current `available_actions` entry as mutation authority.
40
+
41
+ Human-friendly selectors such as `only`, `codex`, `claude`, and `@short-ref` remain slash-command discovery inputs. The v30 structured model contract carries semantic IDs only and does not expose selectors or opaque authority values. Its core shapes are `send({session_id|terminal_id,request})` with mutually exclusive targets, `watch({terminal_id})`, `model_options({terminal_id})`, the separately advertised Codex-only `repair_model_control({terminal_id})`, followed by `set_model({terminal_id,model,reasoning_effort})`, `native_inspect({terminal_id,inspection})`, `identify_foreground({terminal_id})`, `identify_and_send({terminal_id,request})`, `new_thread({terminal_id})`, `resume_thread({terminal_id,native_thread_id})`, `respond_interaction({turn_id|watch_id,interaction_id,answers,delivery_mode?})` with exactly one subject target and `delivery_mode` present only for an `async_question`, managed `approve({turn_id,decision})` or approve-once-only terminal-scoped `approve({terminal_id})`, and `reconcile_binding({terminal_id,conflicting_session_id})`. Model selection, model-control residue repair, approval, native interaction response, handoff takeover, and reconciliation require explicit user intent and fresh source state. The trusted plugin/CLI privately derives and revalidates terminal, catalog, binding, candidate, prompt, interaction, composer, handoff, revision, and compare-and-swap fences; the model never transports them. Store format remains 1 and writer protocol is 8; Terminal Watch schema is 3.
42
+
43
+ ## Managed Turn Flow
44
+
45
+ This flow describes managed Session/Turn delivery. Codex 0.158.0/0.159.0/0.159.2 physical Send
46
+ uses an independent exact paginated task Watch and returns `watch_id` without
47
+ creating a managed `turn_id`. Its foreground binding, native answer receipts,
48
+ and session-only/new/resume and first-modal limits are described in the
49
+ [0.158.0/0.159.0/0.159.2 compatibility review](codex-0.159.2-compatibility.md).
50
+
51
+ 1. The controller Host calls ordinary send using the exact current listed action and the user-facing request. `session_exact` carries `session_id`; `terminal_follow_current` and `terminal_user_explicit` carry `terminal_id`. Both target fields may be omitted only when AKK must prove one unique send-ready pane. Initial discovery may first resolve one eligible Codex or Claude Code terminal into an AKK session.
52
+ 2. AKK verifies that the session is bound to the expected native session, terminal, and idle coding-agent process.
53
+ 3. AKK creates a unique `turn_id`, writes the request to the verified idle pane, and starts a monitor bound to that Turn, pane, process, and message.
54
+ 4. The coding agent works in the same terminal that the human can inspect or take over.
55
+ 5. AKK sends a structured callback containing both `session_id` and `turn_id` to the originating Host session when it has reliable approval, completion, cancellation, stall, or failure evidence.
56
+ 6. After completion, refresh the terminal list. Another ordinary send through that row's current exact action creates a new Turn without clearing the native coding-agent context.
57
+
58
+ Steps 2–6 describe managed delivery, which may require an exact empty Composer before input. For an advertised `terminal_user_explicit` Send, the selected live terminal/process and direct input-safety checks authorize the one physical Send; rollout, Session, Store, and callback state are sidecar management evidence rather than vetoes. Parsed working activity, an existing draft, and ordinary main-Composer visibility do not veto this user-priority path, but a blocked native approval or a proven input-owning questionnaire, editor, menu, or read-only viewer remains a zero-input boundary. Profiled Codex 0.154.0/0.155.1 exact collapsed async-question summaries remain sendable because the main Composer owns input; their expanded, clipped, or ambiguous async editors do not. Codex clears the current Composer once with `C-u`; Claude Code uses a sentinel-backed native `C-s` stash-clear transaction that is independent of the cursor position and does not interrupt an active turn, then proves the main Composer empty. Each then injects the request, waits through the paste window, and dispatches Enter exactly once. Codex also freezes the complete pre-send open-rollout inventory and scans those candidates together with newly opened roots after submission. One rollout that uniquely accepts the exact request hash is promoted to the managed Session/Turn; zero matches remain pending/unproven, while multiple matches or changed file/process authority become uncertain without replay. After either agent's text injection, no Composer observation may veto Enter.
59
+
60
+ If managed preparation still fails before input, physical-terminal authority performs the same single Send and best-effort persists an exact request-bound Terminal Watch. That Watch supplies completion callbacks. Before exact native acceptance it remains notify-only; after acceptance it can emit an idempotent `interaction_required` wake-up and, through same-controller Status, expose one supported native-interaction response offer. Activity/best-effort or manual-only observations emit `interaction_manual_required` and require direct TUI input. Watch attachment failure is reported without changing or retrying the successful Send. Send output treats transport, native acceptance, management, and observation as separate facts through `terminal_input_dispatched`, `agent_acceptance`, `management_mode`, `observation_mode`, and `capabilities`; legacy delivery fields remain compatibility aliases. Once clear or request input may have occurred, an uncertain result must never be retried automatically.
61
+
62
+ P2 adds an explicit path for an exact-empty idle Codex pane whose foreground
63
+ rollout cannot be selected safely. `identify_foreground({terminal_id})` holds
64
+ the exact terminal lock and dispatches the closed `/status` probe once. It is
65
+ read-only with respect to the AKK Store, but it is terminal input. Its proof is
66
+ bound to the pane, process incarnation, real cwd, agent version, and screen
67
+ generation, expires after 30 seconds, and grants no binding or mutation
68
+ authority after the lock is released. It creates no Session, Turn, receipt,
69
+ monitor, or callback.
70
+
71
+ `identify_and_send({terminal_id,request})` is the atomic actionable form. It
72
+ retains one terminal lock from the probe through the requested task, rechecks
73
+ the live boundary before task input, and still grants durable Session/Turn
74
+ identity only to the rollout that uniquely accepts the exact request. The
75
+ status UUID is provisional evidence, never durable ownership. Probe or boundary
76
+ uncertainty stops before the task and cannot be retried automatically. This
77
+ operation is optional: ordinary human Send continues to follow its independent
78
+ user-priority contract and is never implicitly redirected through these
79
+ identification actions. List never types an identity probe, and exact bound-task
80
+ Status stays read-only. A targeted conversation Status for an unbound, idle
81
+ Codex terminal may use a separate closed routing identity inspection; see
82
+ [Status and native inspection](operator-guide.md#akk-status-and-native-inspection).
83
+ Codex 0.158.0/0.159.0/0.159.2 physical Send
84
+ and exact Watch creation use their separate closed `/status` transaction to
85
+ bind the foreground paginated thread.
86
+
87
+ An ordinary send never targets a completed or historical `turn_id`. If the current Turn is in the compatibility state `waiting_for_openclaw` because the coding agent asked a question, the controller Host uses `respond(turn_id, answer)`; that answer remains inside the same Turn.
88
+
89
+ A native Claude Code or Codex interaction is a separate status-bound flow. In the same owning controller conversation, call Status for the exact managed Turn or exact Watch and present its current `interaction_state` to the user. If that projection is pending and advertises response capability, submit exactly one subject (`turn_id` or `watch_id`) plus only its opaque `interaction_id`, `question_id`, and `option_id` values or bounded typed text. A blocking `questionnaire` owns the input surface and forbids `delivery_mode`. A Codex `async_question` is a parallel pending interaction while terminal activity and its Turn remain `working`; its projection advertises one or both semantic delivery modes, and its response defaults to advertised `steer_current_turn` (or explicitly selects advertised `queue_next_turn`): `steer_current_turn` delivers the answer to the running turn, while `queue_next_turn` queues it for the next turn. One response resolves only the current step; refresh Status before every later question or final confirmation. The callback itself never grants mutation authority. Changed, unprovable, secret-bearing, unsupported, multi-select, manual-required, or uncertain interactions fail closed and must not receive guessed keys, shortcut chords, menu indexes, or automatic retries. Expiry is a freshness boundary: an elapsed offer requires an exact live recapture rather than an unconditional rejection or replay. Codex 0.154.0 and 0.155.1 are separate version-bound TUI profiles; notification and stable-question-identity wrappers added to main after 0.155.1 are not part of either released contract.
90
+
91
+ If no eligible terminal exists, AKK stops and returns an actionable setup message. It does not launch an invisible replacement agent.
92
+
93
+ ### Trusted controller callback boundary
94
+
95
+ Callback routing is an administrator/trusted-host concern, never a model
96
+ argument. The OpenClaw plugin captures its own authenticated controller
97
+ session identity and gives AKK a versioned, secretless `callback_route`; the
98
+ durable outbox freezes that route together with a canonical callback envelope
99
+ before delivery. A transport returns one explicit outcome: accepted,
100
+ retryable failure, permanent failure, or uncertain. Permanent and uncertain
101
+ outcomes are not blindly retried, while an accepted checkpoint remains
102
+ authoritative if a later wake or observation step fails.
103
+
104
+ The core outbox, managed-Turn monitor, stall notification, and Terminal Watch
105
+ use the host-neutral route/envelope/outcome boundary. First-party adapters
106
+ translate that boundary into the Host's own lifecycle: OpenClaw uses its
107
+ Gateway session, while Pi and DeepSeek Harness use a local `command_json_v1`
108
+ callback path. Existing OpenClaw Store fields remain readable and dual-written
109
+ for compatibility; OpenClaw-specific `sessionKey`, Gateway calls, executable
110
+ paths, and credentials stay inside the trusted OpenClaw adapter. No route,
111
+ profile, controller-session identity, token, composer digest, draft text, or
112
+ transport evidence is exposed through the v30 model-facing contract. A new
113
+ controller Host still needs a trusted session-context adapter and runtime
114
+ integration; the protocol boundary is not a standalone supervisor.
115
+
116
+ ## User-Selected Terminal Watch
117
+
118
+ Terminal Watch is the read-only, user-intent-first path for observing an exact visible Codex or Claude Code terminal:
119
+
120
+ 1. The user selects one complete `terminal_id`. A fresh `/akk list` and its advertised `available_actions.watch` are the safest discovery path, but advertisement is not authorization and its absence does not veto an explicit Watch request.
121
+ 2. `agent_knock_knock_watch({terminal_id})`, or `/akk watch <exact-terminal-id>`, observes that exact endpoint/process and attempts to construct one privacy-safe exact task anchor. It does not acquire terminal-input or managed-owner authority.
122
+ 3. If a unique provider task anchor is available, AKK creates `watch_mode="exact_task"`, `confidence="exact"`; missing or mismatched version evidence remains a warning and does not weaken that otherwise exact anchor. If task artifacts, native identity, or task boundaries cannot establish an anchor, AKK records warnings and creates `watch_mode="terminal_activity"`, `confidence="best_effort"` instead.
123
+ 4. Status and cancellation target only the returned ID: `agent_knock_knock_status({watch_id})`, `/akk status <watch-id>`, `agent_knock_knock_unwatch({watch_id})`, or `/akk unwatch <watch-id>`.
124
+ 5. Startup and periodic supervision observe and settle the same Watch, then deliver its durable notification outbox to the originating controller session.
125
+
126
+ Creating a Watch hard-fails only when the exact terminal is absent, its endpoint/process cannot be identified, neither a durable exact-task anchor nor a read-only screen-status activity path exists, or AKK cannot create/write the durable Watch Store. A missing or mismatched coding-agent version, unusable rollout/transcript artifact when screen activity remains observable, existing managed Turn or other ownership record, missing binding metadata, and missing `available_actions.watch` are diagnostics, never Watch vetoes. If the same exact active Watch already exists, AKK may return it rather than treating the request as a conflict. Because Watch is read-only, it can coexist with a managed monitor without adopting, superseding, or changing its Session/Turn; the managed monitor remains preferable when the user wants exact Turn attribution.
127
+
128
+ Every aggregate records a revision, exact terminal endpoint/process epoch, workspace, creation warnings, controller route, timestamps/deadline, lifecycle status, last activity, optional settlement, and an append-only notification outbox. An exact-task Watch additionally stores one privacy-safe provider anchor: Codex binds rollout identity and task request/turn byte boundaries; Claude binds transcript identity, root prompt, and current-turn byte boundaries. Exact durable completion already written to that anchor wins, while later replacement, truncation, successor task, changed boundary or fingerprint, or process/thread/endpoint drift invalidates that exact Watch instead of following a different task.
129
+
130
+ A terminal-activity Watch makes no task-identity claim. Its checkpoint must first observe activity (`working` or `awaiting_approval`) in the selected terminal/process epoch and then observe stable `idle` across consecutive reconciliation sweeps. That transition emits a completion-shaped callback with reason `terminal_activity_became_stably_idle`, but the callback and public status remain labeled `best_effort`: they prove only that observed terminal activity became idle, not that a particular task completed or succeeded. They carry no exact-task completion text. Starting from idle or unknown does not immediately settle; later activity must be seen first.
131
+
132
+ An approval observation appends at most one notification per exact fingerprint and leaves either Watch mode active. It never sends approval keys and never enters automatic approval; a human must inspect and decide in the TUI. Exact-task completion/failure, best-effort stable idle, timeout, invalidation, or explicit `unwatch` settles once and enqueues one terminal notification. Deterministic notification IDs and idempotency keys, append-only receipts, claim leases, and retry timestamps make callback recovery crash-safe: transport is at-least-once, while the idempotency key makes the logical notification effectively at-most-once.
133
+
134
+ The current core Host Adapter surface has 22 registered tools and emits list action-contract v30. Its Watch tools map to four internal CLI entries: `watch-terminal`, `watch-status`, `unwatch-terminal`, and `reconcile-watches`. These entries are an internal adapter boundary, not alternate raw terminal controls. The v30 ordinary Send shape remains `send({session_id|terminal_id,request})`; the agent-neutral user-explicit composer policy is advertised as `replace_current_composer_and_submit`, not as another model-supplied argument. The v28 Codex-named field remains a compatibility alias. The interaction tool consumes only the current same-controller Status projection and never exposes its private prompt fingerprint or terminal-key plan. The two foreground-identification tools are separate, advertised Codex-only operations and are never implicit ordinary-Send preprocessing.
135
+
136
+ ## Native Thread Transitions
137
+
138
+ New/clear and resume are lifecycle transitions, not message types and not ordinary sends:
139
+
140
+ ```text
141
+ verified idle terminal + private current-binding fence
142
+ ├─ new_thread ────> new native thread + new AKK Session
143
+ └─ resume_thread ─> exact historical native thread + restored/new AKK Session
144
+ (no Turn created)
145
+ ```
146
+
147
+ Before either transition, the public action supplies the exact full `terminal_id`; resume additionally supplies the complete `native_thread_id`. AKK then derives a fresh compare-and-swap binding fence and candidate fence privately, and requires a recognized adapter, a complete `x.y.z` agent version, an idle prompt, and no active or unresolved Turn. An exact regression-tested profile is a verification level, not an authorization gate; an unverified version remains callable and carries a compatibility warning. Human-facing numbers and collision-safe short IDs are scoped to a five-minute private runtime snapshot; AKK resolves them to the complete UUID before the structured action and revalidates the entire ordered candidate set, terminal dispatch generation, process, workspace, and binding before input. They are never model arguments or stored as native identity. A replaced or changed transcript/rollout cannot be resumed under stale metadata. `previous` is derived only from the current bound Session's latest committed transition and is advertised only when fresh discovery proves exactly one resumable source; static lineage and recency are not authority. Candidates from another workspace, archived or ambiguous threads, and threads active in another process are not resumable.
148
+
149
+ The lifecycle operation is serialized against send, approval, monitor, cancellation, and recovery work for that pane. AKK records the previous and next native identities, verifies the post-operation identity and idle prompt, creates or reactivates the corresponding AKK Session, and advances the binding generation. It fails closed if any identity or capability evidence is missing or changed. Monitor supervision never reclassifies a historical binding: only a later lifecycle listing may classify one bound historical Session as resumable when its recorded process has conclusively exited, and the resume mutation compare-and-swap detaches that binding before terminal input. Every first-line native slash command is rejected as ordinary task or answer text, including clear/new/resume/status, Codex fork/side-thread commands, and Claude conversation branching; supported context changes must use the lifecycle boundary.
150
+
151
+ For the next ordinary send, refresh `agent_knock_knock_list` and use only the resulting terminal row's advertised action. A `session_exact` action supplies `session_id`; a `terminal_follow_current` action supplies `terminal_id`. Either accepted action creates the context's first new `turn_id`. A callback, monitor, approval, receipt, or recovery action bound to an earlier Session, native identity, terminal incarnation, or binding generation cannot mutate the newly active context.
152
+
153
+ ## Native Status Inspection
154
+
155
+ `agent_knock_knock_status` is an AKK Turn/screen inspection. It does not execute a coding-agent slash command. Native inspection is a separate terminal action advertised when the adapter, terminal identity, private binding fence, idle composer, and ownership state are currently safe. An unverified semantic agent version adds a warning but does not hide the action.
156
+
157
+ The `agent_knock_knock_native_inspect` contract accepts exactly two fields: the full `terminal_id` and `inspection="status"`. The adapter owns the closed command, and AKK derives the fresh binding fence internally; callers cannot supply a command string or opaque authority. Regression-tested profiles cover Codex 0.146.0/0.146.1/0.147.0/0.148.0/0.149.1/0.150.1/0.151.0/0.153.0/0.153.4/0.154.0/0.155.1 and Claude Code 2.1.218/2.1.226/2.1.237/2.1.251/2.1.259/2.1.263/2.1.266/2.1.267/2.1.285. Other complete `x.y.z` versions use the generic runtime profile with a compatibility warning; unchanged UI behavior succeeds, while incompatible behavior fails or is reported uncertain without automatic retry. Claude's modal Status panel must be freshly proven, parsed, dismissed once, and followed by the same idle empty composer. `/usage`, `/cost`, `/stats`, `/usage-credits`, `/model`, `/compact`, and arbitrary slash commands remain unavailable. Bare Codex `/usage` opens an interactive menu whose later Enter can select an account-side usage-limit reset, so it must not be treated as a read-only inspection.
158
+
159
+ Native model control is a separate two-step mutation based on explicit authority
160
+ for one exact physical pane/process. `model_options({terminal_id})` dynamically
161
+ captures the native model/reasoning catalog; `set_model` accepts only one exact
162
+ tuple from that same-controller offer. Profiled Codex 0.154.0/0.155.1 accepts either one exact
163
+ current native Session or a verified-zero-rollout pane, where
164
+ `identify_foreground` is not a prerequisite; Claude Code still requires one
165
+ exact current native Session. Both steps require no active Turn, approval,
166
+ questionnaire/editor, or read-only viewer. `model_options` normally requires
167
+ an idle empty Composer, but current List may bind it to one exact stable Codex
168
+ 0.154 `/model` residual and authorize continuing only that slash command into
169
+ read-only discovery. Every native frame is revalidated under lock. An unproven
170
+ postcondition is `uncertain` and must not be retried automatically. Codex reports
171
+ `current_and_new_sessions` with the existing current-only Ultra exception;
172
+ Claude Code reports `current_session`.
173
+
174
+ A failed profiled Codex 0.154.0/0.155.1 model-control operation can expose both residual-bound
175
+ `model_options({terminal_id})` and the distinct cleanup-only
176
+ `repair_model_control({terminal_id})` action when List proves the same
177
+ exact physical pane/process, an exact profiled `/model` popup or exact bare
178
+ `/model` Composer, no active Turn, and no approval, questionnaire/editor, or
179
+ viewer. The trusted adapter consumes the residual-entry authority at the
180
+ `model_options` Enter boundary. After exact catalog discovery and dismissal to
181
+ an empty Composer, AKK derives a fresh ordinary binding/catalog offer for one
182
+ `set_model` attempt. Neither residual-entry nor repair authority is accepted by
183
+ `set_model`. Repair never presses Enter or accepts raw text/keys; success
184
+ requires an empty Composer. Refresh List and obtain a new model catalog
185
+ afterward. An uncertain repair cannot be retried automatically.
186
+
187
+ Foreground identification is a separate Codex-only capability for a physically
188
+ exact but durably ambiguous pane. `agent_knock_knock_identify_foreground`
189
+ accepts only the advertised `terminal_id`; it sends `/status` once and returns
190
+ a 30-second diagnostic proof while leaving the Store unchanged. That proof is
191
+ not an authority object and cannot be supplied to any later call.
192
+ `agent_knock_knock_identify_and_send` accepts the advertised `terminal_id` and
193
+ one `request`, and consumes the foreground observation only while the same
194
+ terminal lock remains held. It neither weakens exact request acceptance nor
195
+ turns the status UUID into durable identity.
196
+
197
+ Native inspection is serialized against send, lifecycle transition, approval, cancellation, monitoring terminal access, and recovery. It verifies the exact slash composer beyond the versioned Enter-suppression window, sends at most one Enter, proves one fresh bounded/redacted status result, and requires an idle postcondition. It creates no Session, Turn, dispatch receipt, monitor, callback, or response-round state. Any stale private fence, non-empty composer, identity/version drift, unresolved Turn/transition/dispatch, unproven Enter, or ambiguous result fails closed without a blind second Enter.
198
+
199
+ Ordinary `send` and `respond` continue to reject every first-line native slash command. Native inspection is a narrow capability boundary, not a slash-command allowlist.
200
+
201
+ ## Message Types
202
+
203
+ | Type | Purpose |
204
+ | --- | --- |
205
+ | `task` | The controller Host starts a new Turn with work for the coding agent. |
206
+ | `answer` | The controller Host answers a question inside a `waiting_for_openclaw` Turn. |
207
+ | `progress` | AKK reports reliable non-final progress. |
208
+ | `blocked` | AKK reports that the task needs attention. |
209
+ | `done` | AKK reports that the current terminal turn completed. |
210
+ | `error` | AKK reports a terminal, monitor, callback, or protocol failure. |
211
+ | `control` | AKK records Turn-level control such as cancellation or timeout. |
212
+
213
+ The coding agent does not run a callback command and does not need an AKK-specific hook or plugin. AKK's terminal monitor owns callback delivery.
214
+
215
+ ## Terminal Identity
216
+
217
+ Each managed Turn is bound to a concrete identity, including:
218
+
219
+ - coding agent (`codex` or `claude`)
220
+ - canonical working directory captured for this pane and Turn
221
+ - terminal provider endpoint and pane target
222
+ - pane and agent process identity
223
+ - native session evidence, AKK `session_id`, `turn_id`, and message identity
224
+ - terminal binding ID and generation, including the transition that established it
225
+ - monitor owner and lease
226
+
227
+ AKK revalidates that identity before sending tasks, interrupt keys, or approval input. Stale, changed, ambiguous, or replayed actions are rejected.
228
+
229
+ Approval authorization is prompt-scoped. Managed approval carries only `turn_id`; terminal-scoped approval carries only `terminal_id`, and both require explicit user confirmation. An adapter isolates one complete bounded approval region and keeps its exact unredacted bytes and fingerprint local. The plugin/CLI retains the private confirmation offer, recaptures it under lock, and rejects before an approval key if any prompt, choice, command/secret, process, cwd, owner, or request evidence changed. Missing or ambiguous prompt evidence is never downgraded to whole-screen or parsed-display authority. No prompt fingerprint or terminal token crosses the model-facing boundary.
230
+
231
+ The active Host runtime supervises eligible terminal monitors and Terminal Watches
232
+ independently of interactive commands. At startup and in one non-overlapping
233
+ five-second cycle, it runs managed-Turn monitor reconciliation and Terminal
234
+ Watch reconciliation as separate coordination steps with separate error
235
+ boundaries; a failure in either step does not starve the other. Managed monitor
236
+ reconciliation distinguishes a transient Store-lock timeout from proven binding
237
+ supersession and preserves the Turn's exactly-once completion claim across
238
+ monitor replacement. Watch reconciliation restores observation and retries its
239
+ durable idempotent callback outbox. Codex managed completion first scans the
240
+ exact accepted native turn in the rollout bound to the Turn; it does not fall
241
+ back to another same-workspace rollout after that exact detector reports an
242
+ identity or integrity failure. Detector limitations are retained in the Turn
243
+ event history for diagnosis.
244
+
245
+ ## Human Handoff
246
+
247
+ The tmux or Herdr pane remains the source of visible truth:
248
+
249
+ - Attach to the shared terminal to inspect or continue the work yourself.
250
+ - Use AKK status for a bounded remote view.
251
+ - Send the next request to `session_id` only when AKK verifies the pane is idle; this creates a new Turn.
252
+ - Answer an in-flight agent question only through `respond(turn_id, answer)`.
253
+ - Interrupt the current turn without closing the pane.
254
+ - Renew monitoring only when the same live task remains in that pane.
255
+
256
+ This makes handoff reversible: the controller Host and the human operate the same coding-agent session instead of creating parallel, hidden conversations.
257
+
258
+ If a human context switch conflicts with an active Turn, AKK presents a decision rather than redirecting automatically. After explicit takeover confirmation, the model calls `agent_knock_knock_close({turn_id,reason:"superseded_by_human_context_switch"})`; the plugin/CLI privately resolves and revalidates the exact advertised handoff decision, so no live native UUID or handoff token is transported. Low-level binding repair is similarly explicit: `reconcile_binding({terminal_id,conflicting_session_id})` carries no Session revision, binding ID/generation, or token. Reconciliation only detaches the proven stale binding; it neither adopts the live thread nor sends terminal input.
259
+
260
+ Native clear/new/resume operations are separate Session-lifecycle features. Ordinary send and Turn creation do not invoke them; successful lifecycle transitions create no Turn.