@fitchmultz/pi-subagents 0.44.6 → 0.45.0

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 (947) hide show
  1. package/CHANGELOG.md +265 -7
  2. package/LICENSE +1 -0
  3. package/README.md +58 -1483
  4. package/agents/context-builder.md +19 -1
  5. package/agents/debugger.md +10 -3
  6. package/agents/delegate.md +1 -0
  7. package/agents/fixer.md +4 -1
  8. package/agents/oracle.md +13 -2
  9. package/agents/planner.md +14 -3
  10. package/agents/researcher.md +11 -2
  11. package/agents/reviewer-claude.md +11 -2
  12. package/agents/reviewer-gpt.md +12 -2
  13. package/agents/reviewer-ponytail.md +11 -1
  14. package/agents/reviewer-security.md +13 -2
  15. package/agents/reviewer.md +12 -3
  16. package/agents/scout.md +12 -1
  17. package/agents/ui-designer.md +10 -3
  18. package/agents/watcher.md +1 -0
  19. package/agents/worker.md +8 -2
  20. package/agents/writer.md +6 -3
  21. package/dist/agents/agent-defaults.js +9 -0
  22. package/dist/agents/agent-definition.js +196 -0
  23. package/dist/agents/agent-management.js +64 -905
  24. package/dist/agents/agent-scope.js +4 -2
  25. package/dist/agents/agent-selection.js +10 -5
  26. package/dist/agents/agent-serializer.js +55 -67
  27. package/dist/agents/agents.js +75 -716
  28. package/dist/agents/builtin-overrides.js +218 -0
  29. package/dist/agents/chain-serializer.js +3 -367
  30. package/dist/agents/config-values.js +52 -0
  31. package/dist/agents/discovery-paths.js +91 -0
  32. package/dist/agents/frontmatter.js +15 -5
  33. package/dist/agents/identity.js +25 -8
  34. package/dist/agents/json-chain.js +254 -0
  35. package/dist/agents/management-config.js +332 -0
  36. package/dist/agents/management-format.js +231 -0
  37. package/dist/agents/management-persistence.js +287 -0
  38. package/dist/agents/management-targets.js +136 -0
  39. package/dist/agents/management-warnings.js +81 -0
  40. package/dist/agents/markdown-chain.js +210 -0
  41. package/dist/agents/package-agents.js +154 -0
  42. package/dist/agents/skill-files.js +157 -0
  43. package/dist/agents/skill-search-paths.js +246 -0
  44. package/dist/agents/skill-types.js +1 -0
  45. package/dist/agents/skills.js +54 -499
  46. package/dist/extension/acceptance-schema.js +55 -0
  47. package/dist/extension/build-info.js +1 -1
  48. package/dist/extension/chain-schema.js +196 -0
  49. package/dist/extension/child-runtime.js +237 -0
  50. package/dist/extension/compact-tools.js +122 -51
  51. package/dist/extension/config-schema.js +29 -0
  52. package/dist/extension/config.js +27 -11
  53. package/dist/extension/control-notice-schema.js +37 -0
  54. package/dist/extension/control-notices.js +13 -6
  55. package/dist/extension/delegation-bridges.js +43 -0
  56. package/dist/extension/doctor.js +48 -25
  57. package/dist/extension/everyday-schemas.js +207 -0
  58. package/dist/extension/fanout-child.js +18 -319
  59. package/dist/extension/index.js +8 -563
  60. package/dist/extension/message-renderers.js +225 -0
  61. package/dist/extension/nested-control-inbox.js +154 -0
  62. package/dist/extension/parent-runtime.js +339 -0
  63. package/dist/extension/primary-tool.js +69 -0
  64. package/dist/extension/result-snapshot.js +22 -0
  65. package/dist/extension/runtime-reload.js +62 -0
  66. package/dist/extension/runtime-storage.js +43 -0
  67. package/dist/extension/schema-overrides.js +75 -0
  68. package/dist/extension/schemas.js +265 -336
  69. package/dist/extension/tool-input.js +27 -12
  70. package/dist/extension/tool-result.js +19 -4
  71. package/dist/history/answer-texts.js +57 -0
  72. package/dist/history/canonical-result.js +76 -43
  73. package/dist/history/canonical-selection.js +40 -0
  74. package/dist/history/database-generation.js +82 -0
  75. package/dist/history/database.js +57 -33
  76. package/dist/history/entry-ingestion.js +61 -0
  77. package/dist/history/index.js +242 -97
  78. package/dist/history/ingest.js +168 -331
  79. package/dist/history/output-digests.js +40 -0
  80. package/dist/history/preview.js +210 -0
  81. package/dist/history/prune.js +33 -0
  82. package/dist/history/queries.js +60 -349
  83. package/dist/history/query-scope.js +190 -0
  84. package/dist/history/rows.js +77 -0
  85. package/dist/history/run-projection.js +137 -0
  86. package/dist/history/run-queries.js +153 -0
  87. package/dist/history/schema.js +31 -0
  88. package/dist/history/search-queries.js +163 -0
  89. package/dist/history/selected-record.js +108 -0
  90. package/dist/history/source-file.js +45 -0
  91. package/dist/history/source-watches.js +141 -0
  92. package/dist/history/store.js +164 -153
  93. package/dist/history/text-chunks.js +169 -0
  94. package/dist/history/text.js +35 -0
  95. package/dist/history/transcript-queries.js +177 -0
  96. package/dist/history/types.js +5 -1
  97. package/dist/history/values.js +36 -0
  98. package/dist/history/wire-inputs.js +122 -0
  99. package/dist/history/wire-models.js +38 -0
  100. package/dist/history/worker-runtime.js +441 -0
  101. package/dist/history/worker.js +66 -462
  102. package/dist/intercom/intercom-bridge.js +48 -20
  103. package/dist/intercom/live-intercom.js +80 -23
  104. package/dist/intercom/nested-result-tree.js +163 -0
  105. package/dist/intercom/result-delivery.js +40 -0
  106. package/dist/intercom/result-intercom.js +178 -261
  107. package/dist/pi-intercom/agent-dir.js +7 -3
  108. package/dist/pi-intercom/async.js +27 -0
  109. package/dist/pi-intercom/bridge-ask.js +57 -0
  110. package/dist/pi-intercom/bridge-config.js +79 -0
  111. package/dist/pi-intercom/bridge-http.js +86 -0
  112. package/dist/pi-intercom/bridge-protocol.js +106 -0
  113. package/dist/pi-intercom/bridge-routes.js +64 -0
  114. package/dist/pi-intercom/bridge-session.js +416 -0
  115. package/dist/pi-intercom/bridge.js +182 -603
  116. package/dist/pi-intercom/broker/broker.js +236 -244
  117. package/dist/pi-intercom/broker/client.js +189 -304
  118. package/dist/pi-intercom/broker/connection.js +165 -0
  119. package/dist/pi-intercom/broker/framing.js +5 -3
  120. package/dist/pi-intercom/broker/paths.js +4 -1
  121. package/dist/pi-intercom/broker/pid.js +53 -25
  122. package/dist/pi-intercom/broker/snapshot-reader.js +78 -0
  123. package/dist/pi-intercom/broker/snapshots.js +188 -0
  124. package/dist/pi-intercom/broker/spawn.js +36 -25
  125. package/dist/pi-intercom/config.js +85 -71
  126. package/dist/pi-intercom/connection.js +297 -0
  127. package/dist/pi-intercom/identity.js +58 -0
  128. package/dist/pi-intercom/inbound-delivery.js +356 -0
  129. package/dist/pi-intercom/inbound-journal.js +303 -0
  130. package/dist/pi-intercom/inbound-record.js +113 -0
  131. package/dist/pi-intercom/inbound.js +179 -0
  132. package/dist/pi-intercom/index.js +79 -2933
  133. package/dist/pi-intercom/inspection.js +62 -0
  134. package/dist/pi-intercom/interview.js +236 -0
  135. package/dist/pi-intercom/lifecycle.js +168 -0
  136. package/dist/pi-intercom/message-format.js +69 -0
  137. package/dist/pi-intercom/outbound.js +304 -0
  138. package/dist/pi-intercom/peer-awareness.js +66 -0
  139. package/dist/pi-intercom/reply-tracker.js +62 -43
  140. package/dist/pi-intercom/reply-wait.js +201 -0
  141. package/dist/pi-intercom/runtime-types.js +3 -0
  142. package/dist/pi-intercom/session-events.js +180 -0
  143. package/dist/pi-intercom/session-targets.js +42 -34
  144. package/dist/pi-intercom/subagent-events.js +238 -0
  145. package/dist/pi-intercom/subagent-live-events.js +129 -86
  146. package/dist/pi-intercom/supervisor.js +282 -0
  147. package/dist/pi-intercom/tool-arguments.js +74 -0
  148. package/dist/pi-intercom/tool-registration.js +95 -0
  149. package/dist/pi-intercom/tool-results.js +38 -0
  150. package/dist/pi-intercom/tool-schemas.js +82 -0
  151. package/dist/pi-intercom/tools.js +51 -0
  152. package/dist/pi-intercom/topic-actions.js +177 -0
  153. package/dist/pi-intercom/topics.js +177 -92
  154. package/dist/pi-intercom/transport.js +1 -0
  155. package/dist/pi-intercom/types.js +151 -114
  156. package/dist/pi-intercom/ui/compose-paste.js +93 -0
  157. package/dist/pi-intercom/ui/compose.js +121 -143
  158. package/dist/pi-intercom/ui/inline-message.js +59 -59
  159. package/dist/pi-intercom/ui/message-renderers.js +147 -0
  160. package/dist/pi-intercom/ui/overlay.js +181 -0
  161. package/dist/pi-intercom/ui/session-format.js +124 -0
  162. package/dist/pi-intercom/ui/session-list.js +76 -43
  163. package/dist/pi-intercom/ui/tool-renderers.js +110 -0
  164. package/dist/pi-intercom/ui/topic-view.js +88 -0
  165. package/dist/pi-intercom/validation.js +59 -0
  166. package/dist/runs/background/async-chain-plan.js +265 -0
  167. package/dist/runs/background/async-control.js +134 -58
  168. package/dist/runs/background/async-execution.js +136 -633
  169. package/dist/runs/background/async-job-admission.js +40 -0
  170. package/dist/runs/background/async-job-projection.js +169 -0
  171. package/dist/runs/background/async-job-tracker.js +297 -327
  172. package/dist/runs/background/async-launch.js +216 -0
  173. package/dist/runs/background/async-plan.js +116 -0
  174. package/dist/runs/background/async-result-file.js +47 -23
  175. package/dist/runs/background/async-resume.js +195 -253
  176. package/dist/runs/background/async-run-discovery.js +213 -0
  177. package/dist/runs/background/async-run-location.js +135 -0
  178. package/dist/runs/background/async-run-record.js +1 -0
  179. package/dist/runs/background/async-run-repair.js +223 -0
  180. package/dist/runs/background/async-run-summary.js +1 -0
  181. package/dist/runs/background/async-single-plan.js +105 -0
  182. package/dist/runs/background/async-status-projection.js +155 -0
  183. package/dist/runs/background/async-status-render.js +117 -0
  184. package/dist/runs/background/async-status-validation.js +181 -0
  185. package/dist/runs/background/async-status.js +3 -442
  186. package/dist/runs/background/async-value.js +21 -0
  187. package/dist/runs/background/completion-dedupe.js +36 -12
  188. package/dist/runs/background/completion-delivery.js +211 -205
  189. package/dist/runs/background/completion-receipts.js +237 -0
  190. package/dist/runs/background/legacy-status-acceptance.js +34 -0
  191. package/dist/runs/background/notify.js +96 -48
  192. package/dist/runs/background/parallel-groups.js +36 -19
  193. package/dist/runs/background/result-payload.js +178 -0
  194. package/dist/runs/background/result-watcher.js +348 -339
  195. package/dist/runs/background/run-id-resolver.js +53 -33
  196. package/dist/runs/background/run-schemas.js +189 -0
  197. package/dist/runs/background/run-status-contracts.js +14 -0
  198. package/dist/runs/background/run-status-render.js +270 -0
  199. package/dist/runs/background/run-status.js +231 -339
  200. package/dist/runs/background/runner-attempt-output.js +155 -0
  201. package/dist/runs/background/runner-attempt.js +263 -0
  202. package/dist/runs/background/runner-child-executor.js +166 -0
  203. package/dist/runs/background/runner-child-observer.js +192 -0
  204. package/dist/runs/background/runner-completion-summary.js +71 -0
  205. package/dist/runs/background/runner-completion.js +211 -0
  206. package/dist/runs/background/runner-config.js +1 -0
  207. package/dist/runs/background/runner-contract.js +1 -0
  208. package/dist/runs/background/runner-dynamic.js +121 -0
  209. package/dist/runs/background/runner-finalization.js +149 -0
  210. package/dist/runs/background/runner-graph.js +68 -0
  211. package/dist/runs/background/runner-initial-status.js +60 -0
  212. package/dist/runs/background/runner-lifecycle.js +142 -0
  213. package/dist/runs/background/runner-monitor.js +309 -0
  214. package/dist/runs/background/runner-parallel.js +204 -0
  215. package/dist/runs/background/runner-prepare-step.js +86 -0
  216. package/dist/runs/background/runner-reporting.js +153 -0
  217. package/dist/runs/background/runner-status.js +148 -0
  218. package/dist/runs/background/runner-step-output.js +92 -0
  219. package/dist/runs/background/runner-step-record.js +45 -0
  220. package/dist/runs/background/runner-step.js +112 -0
  221. package/dist/runs/background/runner-streaming.js +173 -0
  222. package/dist/runs/background/runner-workflow.js +213 -0
  223. package/dist/runs/background/stale-run-reconciler.js +155 -292
  224. package/dist/runs/background/subagent-runner-launcher.js +33 -13
  225. package/dist/runs/background/subagent-runner.js +51 -1842
  226. package/dist/runs/background/top-level-async.js +2 -1
  227. package/dist/runs/foreground/chain-clarify.js +293 -1017
  228. package/dist/runs/foreground/clarification-draft.js +87 -0
  229. package/dist/runs/foreground/clarify-contracts.js +1 -0
  230. package/dist/runs/foreground/clarify-invocation.js +129 -38
  231. package/dist/runs/foreground/clarify-text-editor.js +210 -0
  232. package/dist/runs/foreground/clarify-view.js +167 -0
  233. package/dist/runs/foreground/execution-input.js +226 -353
  234. package/dist/runs/foreground/execution-routing.js +33 -0
  235. package/dist/runs/foreground/execution-timeout.js +81 -0
  236. package/dist/runs/foreground/foreground-control.js +222 -763
  237. package/dist/runs/foreground/foreground-memory.js +99 -0
  238. package/dist/runs/foreground/invocation-context.js +55 -0
  239. package/dist/runs/foreground/invocation-execution.js +331 -0
  240. package/dist/runs/foreground/invocation-expansion.js +48 -0
  241. package/dist/runs/foreground/management-actions.js +295 -0
  242. package/dist/runs/foreground/nested-control.js +179 -0
  243. package/dist/runs/foreground/question-continuation.js +78 -0
  244. package/dist/runs/foreground/question-control.js +155 -50
  245. package/dist/runs/foreground/resume-target.js +221 -0
  246. package/dist/runs/foreground/revival-launch-policy.js +58 -0
  247. package/dist/runs/foreground/run-async-path.js +190 -178
  248. package/dist/runs/foreground/run-interrupt.js +164 -0
  249. package/dist/runs/foreground/run-nudge.js +278 -0
  250. package/dist/runs/foreground/saved-revival.js +251 -0
  251. package/dist/runs/foreground/subagent-executor.js +135 -424
  252. package/dist/runs/foreground/subagent-params.js +67 -30
  253. package/dist/runs/foreground/wait-observation.js +104 -0
  254. package/dist/runs/foreground/wait-registration.js +17 -0
  255. package/dist/runs/foreground/wait-run.js +283 -123
  256. package/dist/runs/shared/acceptance-contract.js +193 -99
  257. package/dist/runs/shared/acceptance-defaults.js +1 -0
  258. package/dist/runs/shared/acceptance-evaluation.js +201 -181
  259. package/dist/runs/shared/acceptance-finalization.js +256 -180
  260. package/dist/runs/shared/acceptance-outcome.js +53 -0
  261. package/dist/runs/shared/acceptance-reports.js +137 -72
  262. package/dist/runs/shared/acceptance-submission.js +167 -0
  263. package/dist/runs/shared/acceptance-verification.js +100 -0
  264. package/dist/runs/shared/chain-outputs.js +80 -52
  265. package/dist/runs/shared/child-attempt-types.js +1 -0
  266. package/dist/runs/shared/child-attempt.js +314 -667
  267. package/dist/runs/shared/child-boundaries.js +173 -0
  268. package/dist/runs/shared/child-context-filter.js +44 -0
  269. package/dist/runs/shared/child-event-observer.js +390 -0
  270. package/dist/runs/shared/child-execution-cwd.js +73 -43
  271. package/dist/runs/shared/child-execution-outcome.js +72 -0
  272. package/dist/runs/shared/child-invocation.js +54 -0
  273. package/dist/runs/shared/child-message-validation.js +215 -0
  274. package/dist/runs/shared/child-native-accounting.js +106 -0
  275. package/dist/runs/shared/child-native-observation.js +69 -0
  276. package/dist/runs/shared/child-observation-spool.js +164 -0
  277. package/dist/runs/shared/child-observations.js +157 -76
  278. package/dist/runs/shared/child-presence.js +3 -0
  279. package/dist/runs/shared/child-route-env.js +119 -0
  280. package/dist/runs/shared/child-stream-observer.js +221 -0
  281. package/dist/runs/shared/child-stream-projection.js +137 -0
  282. package/dist/runs/shared/child-structured-tool.js +27 -0
  283. package/dist/runs/shared/claude-code.js +121 -158
  284. package/dist/runs/shared/claude-model.js +42 -0
  285. package/dist/runs/shared/claude-session.js +83 -0
  286. package/dist/runs/shared/claude-types.js +1 -0
  287. package/dist/runs/shared/completion-guard.js +18 -18
  288. package/dist/runs/shared/control-event-policy.js +8 -0
  289. package/dist/runs/shared/control-notification-owner.js +13 -0
  290. package/dist/runs/shared/dynamic-fanout.js +188 -173
  291. package/dist/runs/shared/dynamic-item.js +102 -0
  292. package/dist/runs/shared/history-index.js +62 -36
  293. package/dist/runs/shared/legacy-async-recovery.js +114 -0
  294. package/dist/runs/shared/legacy-output-recovery.js +148 -0
  295. package/dist/runs/shared/mcp-config-schema.js +36 -0
  296. package/dist/runs/shared/mcp-direct-tool-allowlist.js +147 -116
  297. package/dist/runs/shared/model-fallback.js +97 -38
  298. package/dist/runs/shared/mutating-tool-guard.js +128 -88
  299. package/dist/runs/shared/native-finalization-types.js +1 -0
  300. package/dist/runs/shared/native-finalization.js +155 -76
  301. package/dist/runs/shared/native-usage.js +238 -98
  302. package/dist/runs/shared/nested-control-records.js +128 -0
  303. package/dist/runs/shared/nested-events.js +8 -700
  304. package/dist/runs/shared/nested-path.js +32 -28
  305. package/dist/runs/shared/nested-projection.js +155 -0
  306. package/dist/runs/shared/nested-protocol.js +18 -0
  307. package/dist/runs/shared/nested-registry.js +191 -0
  308. package/dist/runs/shared/nested-render.js +106 -58
  309. package/dist/runs/shared/nested-route.js +220 -0
  310. package/dist/runs/shared/nested-validation.js +216 -0
  311. package/dist/runs/shared/owned-child-evidence.js +125 -0
  312. package/dist/runs/shared/owned-run-list.js +146 -0
  313. package/dist/runs/shared/owned-run-observation.js +267 -0
  314. package/dist/runs/shared/owned-run-progress.js +109 -0
  315. package/dist/runs/shared/owned-run-read-state.js +1 -0
  316. package/dist/runs/shared/owned-run-results.js +202 -0
  317. package/dist/runs/shared/owned-run-status.js +180 -0
  318. package/dist/runs/shared/owned-run-view.js +51 -0
  319. package/dist/runs/shared/owned-workflow-details.js +17 -0
  320. package/dist/runs/shared/owner-output.js +43 -0
  321. package/dist/runs/shared/parallel-utils.js +36 -28
  322. package/dist/runs/shared/parent-receipts.js +90 -32
  323. package/dist/runs/shared/parent-usage.js +169 -57
  324. package/dist/runs/shared/pi-args.js +108 -201
  325. package/dist/runs/shared/pi-launch-input.js +1 -0
  326. package/dist/runs/shared/pi-session-launch.js +86 -0
  327. package/dist/runs/shared/pi-spawn.js +35 -21
  328. package/dist/runs/shared/run-history-queries.js +126 -35
  329. package/dist/runs/shared/run-history.js +101 -35
  330. package/dist/runs/shared/run-metadata-paths.js +14 -0
  331. package/dist/runs/shared/run-metadata.js +158 -0
  332. package/dist/runs/shared/run-persistence.js +131 -0
  333. package/dist/runs/shared/run-records.js +9 -679
  334. package/dist/runs/shared/run-restoration.js +338 -0
  335. package/dist/runs/shared/run-state-owner.js +26 -0
  336. package/dist/runs/shared/session-cwd-preload.js +27 -18
  337. package/dist/runs/shared/single-output.js +148 -70
  338. package/dist/runs/shared/stable-value.js +15 -0
  339. package/dist/runs/shared/streaming-text.js +23 -12
  340. package/dist/runs/shared/structured-output.js +25 -13
  341. package/dist/runs/shared/subagent-control.js +167 -100
  342. package/dist/runs/shared/subagent-prompt-runtime.js +27 -130
  343. package/dist/runs/shared/subagent-tool-loop-guard.js +81 -52
  344. package/dist/runs/shared/supervisor-question-state.js +145 -0
  345. package/dist/runs/shared/supervisor-questions.js +185 -254
  346. package/dist/runs/shared/workflow-graph.js +259 -167
  347. package/dist/runs/shared/workflow-policy.js +120 -48
  348. package/dist/runs/shared/worktree-contract.js +1 -0
  349. package/dist/runs/shared/worktree-hook.js +138 -0
  350. package/dist/runs/shared/worktree-location.js +47 -0
  351. package/dist/runs/shared/worktree-preservation.js +8 -0
  352. package/dist/runs/shared/worktree-process.js +107 -0
  353. package/dist/runs/shared/worktree.js +183 -322
  354. package/dist/shared/agent-context-policy.js +34 -44
  355. package/dist/shared/agent-dir.js +14 -0
  356. package/dist/shared/artifacts.js +30 -12
  357. package/dist/shared/atomic-json.js +4 -1
  358. package/dist/shared/chain-files.js +72 -0
  359. package/dist/shared/concurrency.js +18 -0
  360. package/dist/shared/content-preview.js +115 -0
  361. package/dist/shared/cooperative.js +5 -2
  362. package/dist/shared/execution-cwd.js +13 -5
  363. package/dist/shared/file-coalescer.js +2 -1
  364. package/dist/shared/fork-context.js +10 -12
  365. package/dist/shared/formatters.js +45 -19
  366. package/dist/shared/journal-frames.js +164 -0
  367. package/dist/shared/journal-projections.js +121 -0
  368. package/dist/shared/journal-reader.js +6 -407
  369. package/dist/shared/json-projection.js +191 -0
  370. package/dist/shared/lazy-tools.js +19 -8
  371. package/dist/shared/message-output.js +116 -0
  372. package/dist/shared/model-info.js +31 -14
  373. package/dist/shared/native-import.js +20 -0
  374. package/dist/shared/native-journal.js +140 -0
  375. package/dist/shared/native-session.js +5 -2
  376. package/dist/shared/native-tui.js +7 -2
  377. package/dist/shared/native-typebox.js +15 -3
  378. package/dist/shared/output-page.js +63 -0
  379. package/dist/shared/post-exit-stdio-guard.js +128 -88
  380. package/dist/shared/prompt-sections.js +2 -0
  381. package/dist/shared/session-entries.js +70 -35
  382. package/dist/shared/session-identity.js +5 -3
  383. package/dist/shared/settings.js +62 -192
  384. package/dist/shared/status-format.js +97 -37
  385. package/dist/shared/task-file-policy.js +24 -0
  386. package/dist/shared/temp-root.js +44 -15
  387. package/dist/shared/types/acceptance.js +1 -0
  388. package/dist/shared/types/async.js +1 -0
  389. package/dist/shared/types/config.js +1 -0
  390. package/dist/shared/types/details.js +1 -0
  391. package/dist/shared/types/history.js +1 -0
  392. package/dist/shared/types/inputs.js +1 -0
  393. package/dist/shared/types/intercom.js +1 -0
  394. package/dist/shared/types/launch.js +1 -0
  395. package/dist/shared/types/messages.js +1 -0
  396. package/dist/shared/types/nested.js +1 -0
  397. package/dist/shared/types/owned-runs.js +1 -0
  398. package/dist/shared/types/progress.js +1 -0
  399. package/dist/shared/types/questions.js +1 -0
  400. package/dist/shared/types/results.js +1 -0
  401. package/dist/shared/types/state.js +1 -0
  402. package/dist/shared/types/usage.js +1 -0
  403. package/dist/shared/types/workflow.js +1 -0
  404. package/dist/shared/types.js +75 -30
  405. package/dist/shared/unknown.js +52 -0
  406. package/dist/shared/utils.js +54 -260
  407. package/dist/slash/command-discovery.js +82 -0
  408. package/dist/slash/command-input.js +190 -0
  409. package/dist/slash/prompt-template-bridge.js +94 -270
  410. package/dist/slash/prompt-template-contract.js +77 -0
  411. package/dist/slash/prompt-template-results.js +125 -0
  412. package/dist/slash/request-protocol.js +68 -0
  413. package/dist/slash/result-delivery.js +237 -0
  414. package/dist/slash/saved-chain.js +78 -0
  415. package/dist/slash/slash-bridge.js +123 -89
  416. package/dist/slash/slash-commands.js +101 -572
  417. package/dist/slash/slash-live-state.js +68 -47
  418. package/dist/tui/action-hints.js +50 -22
  419. package/dist/tui/activity-lines.js +32 -0
  420. package/dist/tui/agent-browser.js +290 -0
  421. package/dist/tui/agent-controls.js +289 -0
  422. package/dist/tui/agent-conversation.js +444 -0
  423. package/dist/tui/agent-dock.js +171 -0
  424. package/dist/tui/agent-history.js +50 -183
  425. package/dist/tui/agent-model.js +62 -0
  426. package/dist/tui/agent-picker.js +262 -0
  427. package/dist/tui/agent-view.js +232 -1537
  428. package/dist/tui/compact-results.js +193 -0
  429. package/dist/tui/conversation-details.js +190 -0
  430. package/dist/tui/conversation-frame.js +135 -0
  431. package/dist/tui/conversation-history.js +201 -0
  432. package/dist/tui/conversation-menu.js +78 -0
  433. package/dist/tui/conversation-notices.js +79 -0
  434. package/dist/tui/conversation-selection.js +58 -0
  435. package/dist/tui/conversation-viewport.js +129 -0
  436. package/dist/tui/direction-message.js +27 -0
  437. package/dist/tui/display.js +282 -0
  438. package/dist/tui/editor-viewport.js +18 -0
  439. package/dist/tui/expanded-content.js +87 -0
  440. package/dist/tui/expanded-multi.js +170 -0
  441. package/dist/tui/expanded-single.js +65 -0
  442. package/dist/tui/history-cards.js +216 -0
  443. package/dist/tui/history-display.js +238 -0
  444. package/dist/tui/history-json.js +16 -0
  445. package/dist/tui/history-metadata.js +152 -0
  446. package/dist/tui/history-record.js +251 -0
  447. package/dist/tui/history-text.js +34 -0
  448. package/dist/tui/indexed-history.js +116 -0
  449. package/dist/tui/nested-widget.js +120 -0
  450. package/dist/tui/picker-page.js +59 -0
  451. package/dist/tui/render.js +58 -1501
  452. package/dist/tui/result-facts.js +64 -0
  453. package/dist/tui/task-observation.js +59 -0
  454. package/dist/tui/task-store.js +366 -0
  455. package/dist/tui/text-values.js +16 -0
  456. package/dist/tui/view-connections.js +47 -0
  457. package/dist/tui/view-model.js +94 -0
  458. package/dist/tui/view-persistence.js +51 -0
  459. package/dist/tui/view-ports.js +1 -0
  460. package/dist/tui/view-session.js +37 -0
  461. package/dist/tui/widget-details.js +144 -0
  462. package/dist/tui/widget-status.js +245 -0
  463. package/dist/tui/widget.js +145 -0
  464. package/dist/tui/workflow-labels.js +223 -0
  465. package/dist/tui/workflow-outcomes.js +124 -0
  466. package/docs/code-quality.md +38 -0
  467. package/docs/development.md +99 -0
  468. package/docs/intercom-bridge.md +23 -18
  469. package/docs/intercom.md +132 -106
  470. package/docs/performance.md +19 -17
  471. package/docs/reference.md +1472 -0
  472. package/generated/RunValidators.d.ts +28 -0
  473. package/generated/RunValidators.js +2 -0
  474. package/package.json +27 -6
  475. package/prompts/parallel-cleanup.md +3 -0
  476. package/prompts/parallel-context-build.md +3 -0
  477. package/prompts/parallel-handoff-plan.md +6 -0
  478. package/prompts/parallel-research.md +4 -0
  479. package/prompts/parallel-review.md +2 -0
  480. package/prompts/review-loop.md +2 -0
  481. package/scripts/build.mjs +129 -85
  482. package/scripts/check-compat.mjs +48 -11
  483. package/scripts/compat-host.mjs +35 -7
  484. package/scripts/generate-run-schemas.mjs +210 -0
  485. package/scripts/intercom-bridge-credentials.mjs +155 -28
  486. package/scripts/intercom-remote.mjs +175 -50
  487. package/scripts/local-install-smoke.mjs +47 -37
  488. package/scripts/native-package-smoke.mjs +135 -25
  489. package/scripts/package-smoke.mjs +360 -140
  490. package/scripts/prepare.mjs +54 -34
  491. package/scripts/real-pi-processes.mjs +261 -0
  492. package/scripts/real-pi-smoke.mjs +432 -351
  493. package/scripts/run-tests.mjs +29 -15
  494. package/skills/pi-intercom/SKILL.md +11 -11
  495. package/skills/pi-intercom/references/peer-sessions.md +7 -2
  496. package/skills/pi-subagents/SKILL.md +1 -1
  497. package/skills/pi-subagents/references/full-orchestration-guide.md +254 -112
  498. package/src/agents/agent-defaults.ts +13 -0
  499. package/src/agents/agent-definition.ts +253 -0
  500. package/src/agents/agent-management.ts +111 -808
  501. package/src/agents/agent-scope.ts +7 -3
  502. package/src/agents/agent-selection.ts +26 -16
  503. package/src/agents/agent-serializer.ts +84 -93
  504. package/src/agents/agents.ts +199 -906
  505. package/src/agents/builtin-overrides.ts +297 -0
  506. package/src/agents/chain-serializer.ts +3 -329
  507. package/src/agents/config-values.ts +57 -0
  508. package/src/agents/discovery-paths.ts +134 -0
  509. package/src/agents/frontmatter.ts +35 -17
  510. package/src/agents/identity.ts +49 -18
  511. package/src/agents/json-chain.ts +305 -0
  512. package/src/agents/management-config.ts +342 -0
  513. package/src/agents/management-format.ts +243 -0
  514. package/src/agents/management-persistence.ts +408 -0
  515. package/src/agents/management-targets.ts +260 -0
  516. package/src/agents/management-warnings.ts +115 -0
  517. package/src/agents/markdown-chain.ts +237 -0
  518. package/src/agents/package-agents.ts +231 -0
  519. package/src/agents/skill-files.ts +182 -0
  520. package/src/agents/skill-search-paths.ts +289 -0
  521. package/src/agents/skill-types.ts +31 -0
  522. package/src/agents/skills.ts +152 -610
  523. package/src/extension/acceptance-schema.ts +88 -0
  524. package/src/extension/chain-schema.ts +276 -0
  525. package/src/extension/child-runtime.ts +302 -0
  526. package/src/extension/compact-tools.ts +259 -102
  527. package/src/extension/config-schema.ts +59 -0
  528. package/src/extension/config.ts +39 -17
  529. package/src/extension/control-notice-schema.ts +55 -0
  530. package/src/extension/control-notices.ts +57 -33
  531. package/src/extension/delegation-bridges.ts +59 -0
  532. package/src/extension/doctor.ts +171 -135
  533. package/src/extension/everyday-schemas.ts +252 -0
  534. package/src/extension/fanout-child.ts +29 -308
  535. package/src/extension/index.ts +17 -642
  536. package/src/extension/message-renderers.ts +334 -0
  537. package/src/extension/nested-control-inbox.ts +196 -0
  538. package/src/extension/parent-runtime.ts +405 -0
  539. package/src/extension/primary-tool.ts +130 -0
  540. package/src/extension/result-snapshot.ts +35 -0
  541. package/src/extension/runtime-reload.ts +72 -0
  542. package/src/extension/runtime-storage.ts +49 -0
  543. package/src/extension/schema-overrides.ts +114 -0
  544. package/src/extension/schemas.ts +451 -418
  545. package/src/extension/tool-input.ts +40 -13
  546. package/src/extension/tool-result.ts +45 -14
  547. package/src/history/answer-texts.ts +74 -0
  548. package/src/history/canonical-result.ts +127 -51
  549. package/src/history/canonical-selection.ts +54 -0
  550. package/src/history/database-generation.ts +86 -0
  551. package/src/history/database.ts +86 -48
  552. package/src/history/entry-ingestion.ts +129 -0
  553. package/src/history/index.ts +426 -148
  554. package/src/history/ingest.ts +372 -342
  555. package/src/history/output-digests.ts +41 -0
  556. package/src/history/preview.ts +235 -0
  557. package/src/history/prune.ts +48 -0
  558. package/src/history/queries.ts +122 -256
  559. package/src/history/query-scope.ts +278 -0
  560. package/src/history/rows.ts +118 -0
  561. package/src/history/run-projection.ts +164 -0
  562. package/src/history/run-queries.ts +199 -0
  563. package/src/history/schema.ts +34 -0
  564. package/src/history/search-queries.ts +216 -0
  565. package/src/history/selected-record.ts +140 -0
  566. package/src/history/source-file.ts +51 -0
  567. package/src/history/source-watches.ts +156 -0
  568. package/src/history/store.ts +310 -197
  569. package/src/history/text-chunks.ts +181 -0
  570. package/src/history/text.ts +43 -0
  571. package/src/history/transcript-queries.ts +251 -0
  572. package/src/history/types.ts +27 -164
  573. package/src/history/values.ts +36 -0
  574. package/src/history/wire-inputs.ts +141 -0
  575. package/src/history/wire-models.ts +51 -0
  576. package/src/history/worker-runtime.ts +502 -0
  577. package/src/history/worker.ts +94 -336
  578. package/src/intercom/intercom-bridge.ts +136 -69
  579. package/src/intercom/live-intercom.ts +197 -92
  580. package/src/intercom/nested-result-tree.ts +213 -0
  581. package/src/intercom/result-delivery.ts +56 -0
  582. package/src/intercom/result-intercom.ts +364 -382
  583. package/src/pi-intercom/agent-dir.ts +9 -3
  584. package/src/pi-intercom/async.ts +33 -0
  585. package/src/pi-intercom/bridge-ask.ts +64 -0
  586. package/src/pi-intercom/bridge-config.ts +101 -0
  587. package/src/pi-intercom/bridge-http.ts +97 -0
  588. package/src/pi-intercom/bridge-protocol.ts +123 -0
  589. package/src/pi-intercom/bridge-routes.ts +90 -0
  590. package/src/pi-intercom/bridge-session.ts +506 -0
  591. package/src/pi-intercom/bridge.ts +258 -547
  592. package/src/pi-intercom/broker/broker.ts +326 -263
  593. package/src/pi-intercom/broker/client.ts +273 -354
  594. package/src/pi-intercom/broker/connection.ts +192 -0
  595. package/src/pi-intercom/broker/framing.ts +11 -6
  596. package/src/pi-intercom/broker/paths.ts +28 -25
  597. package/src/pi-intercom/broker/pid.ts +68 -24
  598. package/src/pi-intercom/broker/snapshot-reader.ts +91 -0
  599. package/src/pi-intercom/broker/snapshots.ts +241 -0
  600. package/src/pi-intercom/broker/spawn.ts +58 -34
  601. package/src/pi-intercom/config.ts +113 -108
  602. package/src/pi-intercom/connection.ts +346 -0
  603. package/src/pi-intercom/identity.ts +71 -0
  604. package/src/pi-intercom/inbound-delivery.ts +450 -0
  605. package/src/pi-intercom/inbound-journal.ts +350 -0
  606. package/src/pi-intercom/inbound-record.ts +141 -0
  607. package/src/pi-intercom/inbound.ts +237 -0
  608. package/src/pi-intercom/index.ts +86 -2923
  609. package/src/pi-intercom/inspection.ts +82 -0
  610. package/src/pi-intercom/interview.ts +295 -0
  611. package/src/pi-intercom/lifecycle.ts +183 -0
  612. package/src/pi-intercom/message-format.ts +77 -0
  613. package/src/pi-intercom/outbound.ts +418 -0
  614. package/src/pi-intercom/peer-awareness.ts +84 -0
  615. package/src/pi-intercom/reply-tracker.ts +121 -59
  616. package/src/pi-intercom/reply-wait.ts +247 -0
  617. package/src/pi-intercom/runtime-types.ts +97 -0
  618. package/src/pi-intercom/session-events.ts +247 -0
  619. package/src/pi-intercom/session-targets.ts +124 -72
  620. package/src/pi-intercom/subagent-events.ts +299 -0
  621. package/src/pi-intercom/subagent-live-events.ts +212 -109
  622. package/src/pi-intercom/supervisor.ts +362 -0
  623. package/src/pi-intercom/tool-arguments.ts +120 -0
  624. package/src/pi-intercom/tool-registration.ts +121 -0
  625. package/src/pi-intercom/tool-results.ts +54 -0
  626. package/src/pi-intercom/tool-schemas.ts +134 -0
  627. package/src/pi-intercom/tools.ts +80 -0
  628. package/src/pi-intercom/topic-actions.ts +243 -0
  629. package/src/pi-intercom/topics.ts +267 -121
  630. package/src/pi-intercom/transport.ts +14 -0
  631. package/src/pi-intercom/types.ts +288 -190
  632. package/src/pi-intercom/ui/compose-paste.ts +109 -0
  633. package/src/pi-intercom/ui/compose.ts +173 -157
  634. package/src/pi-intercom/ui/inline-message.ts +80 -62
  635. package/src/pi-intercom/ui/message-renderers.ts +182 -0
  636. package/src/pi-intercom/ui/overlay.ts +238 -0
  637. package/src/pi-intercom/ui/session-format.ts +146 -0
  638. package/src/pi-intercom/ui/session-list.ts +145 -62
  639. package/src/pi-intercom/ui/tool-renderers.ts +148 -0
  640. package/src/pi-intercom/ui/topic-view.ts +107 -0
  641. package/src/pi-intercom/validation.ts +69 -0
  642. package/src/runs/background/async-chain-plan.ts +451 -0
  643. package/src/runs/background/async-control.ts +201 -71
  644. package/src/runs/background/async-execution.ts +206 -829
  645. package/src/runs/background/async-job-admission.ts +54 -0
  646. package/src/runs/background/async-job-projection.ts +225 -0
  647. package/src/runs/background/async-job-tracker.ts +416 -360
  648. package/src/runs/background/async-launch.ts +319 -0
  649. package/src/runs/background/async-plan.ts +285 -0
  650. package/src/runs/background/async-result-file.ts +79 -37
  651. package/src/runs/background/async-resume.ts +338 -285
  652. package/src/runs/background/async-run-discovery.ts +270 -0
  653. package/src/runs/background/async-run-location.ts +194 -0
  654. package/src/runs/background/async-run-record.ts +14 -0
  655. package/src/runs/background/async-run-repair.ts +307 -0
  656. package/src/runs/background/async-run-summary.ts +71 -0
  657. package/src/runs/background/async-single-plan.ts +168 -0
  658. package/src/runs/background/async-status-projection.ts +188 -0
  659. package/src/runs/background/async-status-render.ts +164 -0
  660. package/src/runs/background/async-status-validation.ts +238 -0
  661. package/src/runs/background/async-status.ts +9 -481
  662. package/src/runs/background/async-value.ts +29 -0
  663. package/src/runs/background/completion-dedupe.ts +103 -54
  664. package/src/runs/background/completion-delivery.ts +313 -187
  665. package/src/runs/background/completion-receipts.ts +309 -0
  666. package/src/runs/background/legacy-status-acceptance.ts +38 -0
  667. package/src/runs/background/notify.ts +167 -106
  668. package/src/runs/background/parallel-groups.ts +95 -46
  669. package/src/runs/background/result-payload.ts +268 -0
  670. package/src/runs/background/result-watcher.ts +484 -387
  671. package/src/runs/background/run-id-resolver.ts +126 -57
  672. package/src/runs/background/run-schemas.ts +240 -0
  673. package/src/runs/background/run-status-contracts.ts +46 -0
  674. package/src/runs/background/run-status-render.ts +364 -0
  675. package/src/runs/background/run-status.ts +338 -356
  676. package/src/runs/background/runner-attempt-output.ts +281 -0
  677. package/src/runs/background/runner-attempt.ts +354 -0
  678. package/src/runs/background/runner-child-executor.ts +232 -0
  679. package/src/runs/background/runner-child-observer.ts +270 -0
  680. package/src/runs/background/runner-completion-summary.ts +106 -0
  681. package/src/runs/background/runner-completion.ts +274 -0
  682. package/src/runs/background/runner-config.ts +52 -0
  683. package/src/runs/background/runner-contract.ts +51 -0
  684. package/src/runs/background/runner-dynamic.ts +185 -0
  685. package/src/runs/background/runner-finalization.ts +203 -0
  686. package/src/runs/background/runner-graph.ts +91 -0
  687. package/src/runs/background/runner-initial-status.ts +72 -0
  688. package/src/runs/background/runner-lifecycle.ts +159 -0
  689. package/src/runs/background/runner-monitor.ts +399 -0
  690. package/src/runs/background/runner-parallel.ts +280 -0
  691. package/src/runs/background/runner-prepare-step.ts +128 -0
  692. package/src/runs/background/runner-reporting.ts +192 -0
  693. package/src/runs/background/runner-status.ts +220 -0
  694. package/src/runs/background/runner-step-output.ts +158 -0
  695. package/src/runs/background/runner-step-record.ts +76 -0
  696. package/src/runs/background/runner-step.ts +150 -0
  697. package/src/runs/background/runner-streaming.ts +220 -0
  698. package/src/runs/background/runner-workflow.ts +284 -0
  699. package/src/runs/background/stale-run-reconciler.ts +279 -336
  700. package/src/runs/background/subagent-runner-launcher.ts +67 -35
  701. package/src/runs/background/subagent-runner.ts +80 -2048
  702. package/src/runs/background/top-level-async.ts +9 -7
  703. package/src/runs/foreground/chain-clarify.ts +499 -1334
  704. package/src/runs/foreground/clarification-draft.ts +92 -0
  705. package/src/runs/foreground/clarify-contracts.ts +33 -0
  706. package/src/runs/foreground/clarify-invocation.ts +192 -65
  707. package/src/runs/foreground/clarify-text-editor.ts +229 -0
  708. package/src/runs/foreground/clarify-view.ts +222 -0
  709. package/src/runs/foreground/execution-input.ts +358 -424
  710. package/src/runs/foreground/execution-routing.ts +41 -0
  711. package/src/runs/foreground/execution-timeout.ts +92 -0
  712. package/src/runs/foreground/foreground-control.ts +333 -812
  713. package/src/runs/foreground/foreground-memory.ts +132 -0
  714. package/src/runs/foreground/invocation-context.ts +88 -0
  715. package/src/runs/foreground/invocation-execution.ts +465 -0
  716. package/src/runs/foreground/invocation-expansion.ts +58 -0
  717. package/src/runs/foreground/management-actions.ts +360 -0
  718. package/src/runs/foreground/nested-control.ts +248 -0
  719. package/src/runs/foreground/question-continuation.ts +112 -0
  720. package/src/runs/foreground/question-control.ts +297 -70
  721. package/src/runs/foreground/resume-target.ts +330 -0
  722. package/src/runs/foreground/revival-launch-policy.ts +112 -0
  723. package/src/runs/foreground/run-async-path.ts +307 -223
  724. package/src/runs/foreground/run-interrupt.ts +202 -0
  725. package/src/runs/foreground/run-nudge.ts +355 -0
  726. package/src/runs/foreground/saved-revival.ts +356 -0
  727. package/src/runs/foreground/subagent-executor.ts +195 -493
  728. package/src/runs/foreground/subagent-params.ts +314 -242
  729. package/src/runs/foreground/wait-observation.ts +160 -0
  730. package/src/runs/foreground/wait-registration.ts +18 -0
  731. package/src/runs/foreground/wait-run.ts +361 -119
  732. package/src/runs/shared/acceptance-contract.ts +410 -209
  733. package/src/runs/shared/acceptance-defaults.ts +1 -0
  734. package/src/runs/shared/acceptance-evaluation.ts +314 -240
  735. package/src/runs/shared/acceptance-finalization.ts +447 -305
  736. package/src/runs/shared/acceptance-outcome.ts +69 -0
  737. package/src/runs/shared/acceptance-reports.ts +220 -126
  738. package/src/runs/shared/acceptance-submission.ts +251 -0
  739. package/src/runs/shared/acceptance-verification.ts +118 -0
  740. package/src/runs/shared/acceptance.ts +25 -25
  741. package/src/runs/shared/chain-outputs.ts +190 -98
  742. package/src/runs/shared/child-attempt-types.ts +118 -0
  743. package/src/runs/shared/child-attempt.ts +372 -608
  744. package/src/runs/shared/child-boundaries.ts +217 -0
  745. package/src/runs/shared/child-context-filter.ts +53 -0
  746. package/src/runs/shared/child-event-observer.ts +496 -0
  747. package/src/runs/shared/child-execution-cwd.ts +139 -68
  748. package/src/runs/shared/child-execution-outcome.ts +103 -0
  749. package/src/runs/shared/child-invocation.ts +74 -0
  750. package/src/runs/shared/child-message-validation.ts +233 -0
  751. package/src/runs/shared/child-native-accounting.ts +154 -0
  752. package/src/runs/shared/child-native-observation.ts +79 -0
  753. package/src/runs/shared/child-observation-spool.ts +188 -0
  754. package/src/runs/shared/child-observations.ts +219 -89
  755. package/src/runs/shared/child-presence.ts +6 -0
  756. package/src/runs/shared/child-route-env.ts +142 -0
  757. package/src/runs/shared/child-stream-observer.ts +302 -0
  758. package/src/runs/shared/child-stream-projection.ts +160 -0
  759. package/src/runs/shared/child-structured-tool.ts +38 -0
  760. package/src/runs/shared/claude-code.ts +201 -228
  761. package/src/runs/shared/claude-model.ts +67 -0
  762. package/src/runs/shared/claude-session.ts +124 -0
  763. package/src/runs/shared/claude-types.ts +31 -0
  764. package/src/runs/shared/completion-guard.ts +35 -26
  765. package/src/runs/shared/control-event-policy.ts +15 -0
  766. package/src/runs/shared/control-notification-owner.ts +20 -0
  767. package/src/runs/shared/dynamic-fanout.ts +402 -238
  768. package/src/runs/shared/dynamic-item.ts +114 -0
  769. package/src/runs/shared/history-index.ts +112 -51
  770. package/src/runs/shared/legacy-async-recovery.ts +153 -0
  771. package/src/runs/shared/legacy-output-recovery.ts +214 -0
  772. package/src/runs/shared/mcp-config-schema.ts +46 -0
  773. package/src/runs/shared/mcp-direct-tool-allowlist.ts +396 -307
  774. package/src/runs/shared/model-fallback.ts +302 -180
  775. package/src/runs/shared/mutating-tool-guard.ts +259 -158
  776. package/src/runs/shared/native-finalization-types.ts +29 -0
  777. package/src/runs/shared/native-finalization.ts +233 -109
  778. package/src/runs/shared/native-usage.ts +379 -96
  779. package/src/runs/shared/nested-control-records.ts +178 -0
  780. package/src/runs/shared/nested-events.ts +45 -752
  781. package/src/runs/shared/nested-path.ts +47 -34
  782. package/src/runs/shared/nested-projection.ts +230 -0
  783. package/src/runs/shared/nested-protocol.ts +67 -0
  784. package/src/runs/shared/nested-registry.ts +273 -0
  785. package/src/runs/shared/nested-render.ts +198 -100
  786. package/src/runs/shared/nested-route.ts +292 -0
  787. package/src/runs/shared/nested-validation.ts +291 -0
  788. package/src/runs/shared/owned-child-evidence.ts +184 -0
  789. package/src/runs/shared/owned-run-list.ts +187 -0
  790. package/src/runs/shared/owned-run-observation.ts +368 -0
  791. package/src/runs/shared/owned-run-progress.ts +172 -0
  792. package/src/runs/shared/owned-run-read-state.ts +7 -0
  793. package/src/runs/shared/owned-run-results.ts +289 -0
  794. package/src/runs/shared/owned-run-status.ts +239 -0
  795. package/src/runs/shared/owned-run-view.ts +65 -0
  796. package/src/runs/shared/owned-workflow-details.ts +24 -0
  797. package/src/runs/shared/owner-output.ts +73 -0
  798. package/src/runs/shared/parallel-utils.ts +93 -129
  799. package/src/runs/shared/parent-receipts.ts +177 -50
  800. package/src/runs/shared/parent-usage.ts +314 -91
  801. package/src/runs/shared/pi-args.ts +241 -311
  802. package/src/runs/shared/pi-launch-input.ts +48 -0
  803. package/src/runs/shared/pi-session-launch.ts +94 -0
  804. package/src/runs/shared/pi-spawn.ts +57 -33
  805. package/src/runs/shared/run-history-queries.ts +189 -38
  806. package/src/runs/shared/run-history.ts +197 -76
  807. package/src/runs/shared/run-id-ambiguity.ts +7 -3
  808. package/src/runs/shared/run-metadata-paths.ts +17 -0
  809. package/src/runs/shared/run-metadata.ts +240 -0
  810. package/src/runs/shared/run-persistence.ts +181 -0
  811. package/src/runs/shared/run-records.ts +19 -607
  812. package/src/runs/shared/run-restoration.ts +455 -0
  813. package/src/runs/shared/run-state-owner.ts +31 -0
  814. package/src/runs/shared/session-cwd-preload.ts +39 -19
  815. package/src/runs/shared/single-output.ts +358 -205
  816. package/src/runs/shared/stable-value.ts +15 -0
  817. package/src/runs/shared/streaming-text.ts +39 -12
  818. package/src/runs/shared/structured-output.ts +76 -46
  819. package/src/runs/shared/subagent-control.ts +330 -197
  820. package/src/runs/shared/subagent-prompt-runtime.ts +92 -174
  821. package/src/runs/shared/subagent-tool-loop-guard.ts +118 -68
  822. package/src/runs/shared/supervisor-question-state.ts +221 -0
  823. package/src/runs/shared/supervisor-questions.ts +396 -401
  824. package/src/runs/shared/workflow-graph.ts +400 -198
  825. package/src/runs/shared/workflow-policy.ts +245 -110
  826. package/src/runs/shared/worktree-contract.ts +29 -0
  827. package/src/runs/shared/worktree-hook.ts +181 -0
  828. package/src/runs/shared/worktree-location.ts +61 -0
  829. package/src/runs/shared/worktree-preservation.ts +10 -0
  830. package/src/runs/shared/worktree-process.ts +132 -0
  831. package/src/runs/shared/worktree.ts +459 -587
  832. package/src/shared/agent-context-policy.ts +176 -145
  833. package/src/shared/agent-dir.ts +15 -0
  834. package/src/shared/artifacts.ts +99 -68
  835. package/src/shared/atomic-json.ts +14 -11
  836. package/src/shared/chain-files.ts +72 -0
  837. package/src/shared/concurrency.ts +27 -0
  838. package/src/shared/content-preview.ts +117 -0
  839. package/src/shared/cooperative.ts +17 -13
  840. package/src/shared/execution-cwd.ts +34 -9
  841. package/src/shared/file-coalescer.ts +24 -22
  842. package/src/shared/fork-context.ts +52 -48
  843. package/src/shared/formatters.ts +88 -47
  844. package/src/shared/journal-frames.ts +197 -0
  845. package/src/shared/journal-projections.ts +133 -0
  846. package/src/shared/journal-reader.ts +18 -333
  847. package/src/shared/json-projection.ts +224 -0
  848. package/src/shared/lazy-tools.ts +76 -27
  849. package/src/shared/message-output.ts +146 -0
  850. package/src/shared/model-info.ts +94 -58
  851. package/src/shared/native-import.ts +25 -0
  852. package/src/shared/native-journal.ts +172 -0
  853. package/src/shared/native-session.ts +8 -3
  854. package/src/shared/native-tui.ts +13 -3
  855. package/src/shared/native-typebox.ts +18 -3
  856. package/src/shared/output-page.ts +76 -0
  857. package/src/shared/post-exit-stdio-guard.ts +232 -172
  858. package/src/shared/prompt-sections.ts +13 -7
  859. package/src/shared/session-entries.ts +103 -44
  860. package/src/shared/session-identity.ts +17 -10
  861. package/src/shared/settings.ts +182 -367
  862. package/src/shared/status-format.ts +207 -98
  863. package/src/shared/stream-json.d.ts +10 -0
  864. package/src/shared/task-file-policy.ts +35 -0
  865. package/src/shared/temp-root.ts +122 -71
  866. package/src/shared/types/acceptance.ts +149 -0
  867. package/src/shared/types/async.ts +247 -0
  868. package/src/shared/types/config.ts +139 -0
  869. package/src/shared/types/details.ts +104 -0
  870. package/src/shared/types/history.ts +217 -0
  871. package/src/shared/types/inputs.ts +4 -0
  872. package/src/shared/types/intercom.ts +57 -0
  873. package/src/shared/types/launch.ts +39 -0
  874. package/src/shared/types/messages.ts +104 -0
  875. package/src/shared/types/nested.ts +153 -0
  876. package/src/shared/types/owned-runs.ts +148 -0
  877. package/src/shared/types/progress.ts +106 -0
  878. package/src/shared/types/questions.ts +103 -0
  879. package/src/shared/types/results.ts +119 -0
  880. package/src/shared/types/state.ts +56 -0
  881. package/src/shared/types/usage.ts +36 -0
  882. package/src/shared/types/workflow.ts +187 -0
  883. package/src/shared/types.ts +222 -1161
  884. package/src/shared/ui-mode.ts +1 -1
  885. package/src/shared/unknown.ts +59 -0
  886. package/src/shared/utils.ts +111 -305
  887. package/src/slash/command-discovery.ts +109 -0
  888. package/src/slash/command-input.ts +232 -0
  889. package/src/slash/prompt-template-bridge.ts +153 -400
  890. package/src/slash/prompt-template-contract.ts +152 -0
  891. package/src/slash/prompt-template-results.ts +189 -0
  892. package/src/slash/request-protocol.ts +87 -0
  893. package/src/slash/result-delivery.ts +312 -0
  894. package/src/slash/saved-chain.ts +115 -0
  895. package/src/slash/slash-bridge.ts +202 -156
  896. package/src/slash/slash-commands.ts +176 -598
  897. package/src/slash/slash-live-state.ts +287 -229
  898. package/src/tui/action-hints.ts +147 -61
  899. package/src/tui/activity-lines.ts +40 -0
  900. package/src/tui/agent-browser.ts +354 -0
  901. package/src/tui/agent-controls.ts +355 -0
  902. package/src/tui/agent-conversation.ts +514 -0
  903. package/src/tui/agent-dock.ts +250 -0
  904. package/src/tui/agent-history.ts +78 -203
  905. package/src/tui/agent-model.ts +78 -0
  906. package/src/tui/agent-picker.ts +325 -0
  907. package/src/tui/agent-view.ts +391 -1310
  908. package/src/tui/compact-results.ts +342 -0
  909. package/src/tui/conversation-details.ts +206 -0
  910. package/src/tui/conversation-frame.ts +184 -0
  911. package/src/tui/conversation-history.ts +246 -0
  912. package/src/tui/conversation-menu.ts +119 -0
  913. package/src/tui/conversation-notices.ts +116 -0
  914. package/src/tui/conversation-selection.ts +66 -0
  915. package/src/tui/conversation-viewport.ts +169 -0
  916. package/src/tui/direction-message.ts +35 -0
  917. package/src/tui/display.ts +409 -0
  918. package/src/tui/editor-viewport.ts +19 -0
  919. package/src/tui/expanded-content.ts +134 -0
  920. package/src/tui/expanded-multi.ts +264 -0
  921. package/src/tui/expanded-single.ts +92 -0
  922. package/src/tui/history-cards.ts +316 -0
  923. package/src/tui/history-display.ts +334 -0
  924. package/src/tui/history-json.ts +17 -0
  925. package/src/tui/history-metadata.ts +177 -0
  926. package/src/tui/history-record.ts +321 -0
  927. package/src/tui/history-text.ts +34 -0
  928. package/src/tui/indexed-history.ts +149 -0
  929. package/src/tui/nested-widget.ts +192 -0
  930. package/src/tui/picker-page.ts +80 -0
  931. package/src/tui/render.ts +100 -1546
  932. package/src/tui/result-facts.ts +99 -0
  933. package/src/tui/task-observation.ts +96 -0
  934. package/src/tui/task-store.ts +432 -0
  935. package/src/tui/text-values.ts +20 -0
  936. package/src/tui/view-connections.ts +64 -0
  937. package/src/tui/view-model.ts +181 -0
  938. package/src/tui/view-persistence.ts +57 -0
  939. package/src/tui/view-ports.ts +55 -0
  940. package/src/tui/view-session.ts +42 -0
  941. package/src/tui/widget-details.ts +220 -0
  942. package/src/tui/widget-status.ts +331 -0
  943. package/src/tui/widget.ts +208 -0
  944. package/src/tui/workflow-labels.ts +340 -0
  945. package/src/tui/workflow-outcomes.ts +150 -0
  946. package/tsconfig.build.json +11 -10
  947. package/tsconfig.json +30 -17
@@ -1,271 +1,369 @@
1
+ import {
2
+ finiteNumber,
3
+ isRecord,
4
+ isUnknownArray,
5
+ optionalBoolean,
6
+ optionalFiniteNumber,
7
+ optionalLabel,
8
+ safeLabel,
9
+ safeText,
10
+ } from "./validation.ts";
11
+
1
12
  export interface SessionInfo {
2
- id: string;
3
- name?: string;
4
- cwd: string;
5
- model: string;
13
+ readonly id: string;
14
+ readonly name?: string;
15
+ readonly cwd: string;
16
+ readonly model: string;
6
17
  /** Opaque same-repository/worktree identity used for ambient peer awareness. */
7
- projectId?: string;
8
- status?: string;
9
- /** Last time the broker observed any activity from this session (liveness). */
10
- lastSeen?: number;
11
- /** Last time this session exchanged an intercom message (send/receive). */
12
- lastIntercomActivity?: number;
13
- /** Number of inbound asks this session still owes a reply to. */
14
- pendingAsks?: number;
15
- /** Whether this session is currently willing/able to answer asks. */
16
- acceptsAsks?: boolean;
17
- subscriptions?: TopicSubscription[];
18
- topics?: TopicUpdate[];
18
+ readonly projectId?: string;
19
+ readonly status?: string;
20
+ readonly lastSeen?: number;
21
+ readonly lastIntercomActivity?: number;
22
+ readonly pendingAsks?: number;
23
+ readonly acceptsAsks?: boolean;
24
+ readonly subscriptions?: readonly TopicSubscription[];
25
+ readonly topics?: readonly TopicUpdate[];
19
26
  }
20
27
 
21
- export interface TopicSubscription { topic: string; awaitRelease?: boolean }
28
+ export interface TopicSubscription {
29
+ readonly topic: string;
30
+ readonly awaitRelease?: boolean;
31
+ }
22
32
  export interface TopicUpdate {
23
- topic: string;
24
- text: string;
25
- event: "update" | "blocker" | "decision" | "release";
26
- resource?: string;
27
- ownership?: "held" | "released";
28
- revision: number;
29
- updatedAt: number;
33
+ readonly topic: string;
34
+ readonly text: string;
35
+ readonly event: "update" | "blocker" | "decision" | "release";
36
+ readonly resource?: string;
37
+ readonly ownership?: "held" | "released";
38
+ readonly revision: number;
39
+ readonly updatedAt: number;
30
40
  }
31
41
 
32
42
  export function isTopicSubscription(value: unknown): value is TopicSubscription {
33
- if (!value || typeof value !== "object") return false;
34
- const item = value as Record<string, unknown>;
35
- return typeof item.topic === "string" && safeLabel(item.topic.trim()) && (item.awaitRelease === undefined || typeof item.awaitRelease === "boolean");
43
+ return (
44
+ isRecord(value) &&
45
+ typeof value.topic === "string" &&
46
+ safeLabel(value.topic.trim()) &&
47
+ optionalBoolean(value.awaitRelease)
48
+ );
49
+ }
50
+
51
+ function validTopicOwnership(item: Readonly<Record<string, unknown>>): boolean {
52
+ if (!optionalLabel(item.resource)) {
53
+ return false;
54
+ }
55
+ if (item.ownership === undefined) {
56
+ return true;
57
+ }
58
+ return (
59
+ typeof item.resource === "string" &&
60
+ (item.ownership === "held" || (item.ownership === "released" && item.event === "release"))
61
+ );
62
+ }
63
+
64
+ function validRevision(value: number): boolean {
65
+ return Number.isSafeInteger(value) && value > 0;
36
66
  }
37
67
  export function isTopicUpdate(value: unknown): value is TopicUpdate {
38
- if (!value || typeof value !== "object") return false;
39
- const item = value as Record<string, unknown>;
40
- return typeof item.topic === "string" && safeLabel(item.topic.trim()) && typeof item.text === "string" && safeText(item.text)
41
- && ["update", "blocker", "decision", "release"].includes(String(item.event))
42
- && typeof item.revision === "number" && Number.isSafeInteger(item.revision) && item.revision > 0
43
- && typeof item.updatedAt === "number" && Number.isFinite(item.updatedAt)
44
- && (item.ownership !== "released" || item.event === "release")
45
- && (item.resource === undefined || typeof item.resource === "string" && safeLabel(item.resource))
46
- && (item.ownership === undefined || typeof item.resource === "string" && (item.ownership === "held" || item.ownership === "released"));
68
+ if (!isRecord(value) || typeof value.topic !== "string" || !safeLabel(value.topic.trim())) {
69
+ return false;
70
+ }
71
+ return (
72
+ safeText(value.text) &&
73
+ typeof value.event === "string" &&
74
+ ["update", "blocker", "decision", "release"].includes(value.event) &&
75
+ finiteNumber(value.revision) &&
76
+ validRevision(value.revision) &&
77
+ finiteNumber(value.updatedAt) &&
78
+ validTopicOwnership(value)
79
+ );
47
80
  }
48
81
 
49
82
  export type MessageDelivery = "queue" | "steer" | "passive";
50
83
  export type QueueMode = "stack" | "replace";
51
-
52
84
  export interface HumanMessageOrigin {
53
- ownerSessionId: string;
54
- runId: string;
55
- index: number;
85
+ readonly ownerSessionId: string;
86
+ readonly runId: string;
87
+ readonly index: number;
56
88
  }
57
-
58
89
  export function isHumanMessageOrigin(value: unknown): value is HumanMessageOrigin {
59
- if (!value || typeof value !== "object") return false;
60
- const origin = value as Record<string, unknown>;
61
- return typeof origin.ownerSessionId === "string" && /^[a-zA-Z0-9_-]+$/.test(origin.ownerSessionId)
62
- && typeof origin.runId === "string" && /^[a-zA-Z0-9_-]+$/.test(origin.runId)
63
- && typeof origin.index === "number" && Number.isSafeInteger(origin.index) && origin.index >= 0;
90
+ if (!isRecord(value)) {
91
+ return false;
92
+ }
93
+ return (
94
+ typeof value.ownerSessionId === "string" &&
95
+ /^[a-zA-Z0-9_-]+$/.test(value.ownerSessionId) &&
96
+ typeof value.runId === "string" &&
97
+ /^[a-zA-Z0-9_-]+$/.test(value.runId) &&
98
+ finiteNumber(value.index) &&
99
+ Number.isSafeInteger(value.index) &&
100
+ value.index >= 0
101
+ );
64
102
  }
65
103
 
66
104
  export interface Message {
67
- id: string;
68
- timestamp: number;
69
- replyTo?: string;
70
- expectsReply?: boolean;
71
- /** Only the owning parent's human UI sets this; recipients verify ownership before elevating it. */
72
- human?: HumanMessageOrigin;
73
- topic?: TopicUpdate;
74
- /** Active-recipient behavior. Omitted delivery defaults to steer unless expectsReply is true. */
75
- delivery?: MessageDelivery;
76
- /** For delivery="queue": stack normally, or replace older undelivered messages in the same thread. */
77
- queueMode?: QueueMode;
78
- /** Stable topic key for queueMode="replace". */
79
- threadId?: string;
80
- /** If true, render without waking the recipient model. Discouraged for agent-to-agent messages. */
81
- passive?: boolean;
82
- content: {
83
- text: string;
84
- attachments?: Attachment[];
105
+ readonly id: string;
106
+ readonly timestamp: number;
107
+ readonly replyTo?: string;
108
+ readonly expectsReply?: boolean;
109
+ /** Recipients verify parent ownership before elevating human origin. */
110
+ readonly human?: HumanMessageOrigin;
111
+ readonly topic?: TopicUpdate;
112
+ readonly delivery?: MessageDelivery;
113
+ readonly queueMode?: QueueMode;
114
+ readonly threadId?: string;
115
+ readonly passive?: boolean;
116
+ readonly content: {
117
+ readonly text: string;
118
+ readonly attachments?: readonly Attachment[];
85
119
  };
86
120
  }
87
-
88
- const UNSAFE_TEXT_CONTROLS = /[\u0000-\u0008\u000b\u000c\u000e-\u001f\u007f-\u009f]/;
89
- const UNSAFE_LABEL_CONTROLS = /[\u0000-\u001f\u007f-\u009f]/;
90
-
91
- function safeText(value: string): boolean {
92
- return !UNSAFE_TEXT_CONTROLS.test(value);
93
- }
94
-
95
- function safeLabel(value: string): boolean {
96
- return value.length > 0 && !UNSAFE_LABEL_CONTROLS.test(value);
97
- }
98
-
99
121
  export interface Attachment {
100
- type: "file" | "snippet" | "context";
101
- name: string;
102
- content: string;
103
- language?: string;
122
+ readonly type: "file" | "snippet" | "context";
123
+ readonly name: string;
124
+ readonly content: string;
125
+ readonly language?: string;
104
126
  }
105
-
106
127
  export function isAttachment(value: unknown): value is Attachment {
107
- if (typeof value !== "object" || value === null) {
108
- return false;
109
- }
110
-
111
- const attachment = value as Record<string, unknown>;
112
-
113
- if (
114
- attachment.type !== "file"
115
- && attachment.type !== "snippet"
116
- && attachment.type !== "context"
117
- ) {
128
+ if (!isRecord(value)) {
118
129
  return false;
119
130
  }
120
-
121
- if (typeof attachment.name !== "string" || !safeLabel(attachment.name) || typeof attachment.content !== "string" || !safeText(attachment.content)) return false;
122
- return attachment.language === undefined || (typeof attachment.language === "string" && safeLabel(attachment.language));
123
- }
124
-
125
- export function normalizeSessionInfo(value: unknown): SessionInfo | null {
126
- if (typeof value !== "object" || value === null || typeof (value as { id?: unknown }).id !== "string") return null;
127
- if (isSessionRegistration(value)) return value as SessionInfo;
128
- if (!("projectId" in value)) return null;
129
- const { projectId: _projectId, ...withoutProjectId } = value as Record<string, unknown>;
130
- return isSessionRegistration(withoutProjectId) ? withoutProjectId as unknown as SessionInfo : null;
131
+ const validType = value.type === "file" || value.type === "snippet" || value.type === "context";
132
+ return (
133
+ validType && safeLabel(value.name) && safeText(value.content) && optionalLabel(value.language)
134
+ );
131
135
  }
132
136
 
133
- export function isMessage(value: unknown): value is Message {
134
- if (typeof value !== "object" || value === null) {
135
- return false;
136
- }
137
-
138
- const message = value as Record<string, unknown>;
139
-
140
- if (typeof message.id !== "string" || !safeLabel(message.id) || typeof message.timestamp !== "number" || !Number.isFinite(message.timestamp)) {
137
+ function validMessageOrigin(message: Readonly<Record<string, unknown>>): boolean {
138
+ if (message.human !== undefined && !isHumanMessageOrigin(message.human)) {
141
139
  return false;
142
140
  }
143
-
144
- if (message.replyTo !== undefined && (typeof message.replyTo !== "string" || !safeLabel(message.replyTo))) {
145
- return false;
146
- }
147
-
148
- if (message.human !== undefined && !isHumanMessageOrigin(message.human)) return false;
149
- if (message.topic !== undefined && (!isTopicUpdate(message.topic) || message.human !== undefined || message.expectsReply || message.replyTo)) return false;
150
-
151
- if (message.expectsReply !== undefined && typeof message.expectsReply !== "boolean") {
152
- return false;
141
+ if (message.topic === undefined) {
142
+ return true;
153
143
  }
144
+ return (
145
+ isTopicUpdate(message.topic) &&
146
+ message.human === undefined &&
147
+ (message.expectsReply === undefined || message.expectsReply === false) &&
148
+ message.replyTo === undefined
149
+ );
150
+ }
154
151
 
155
- if (message.passive !== undefined && typeof message.passive !== "boolean") {
152
+ function validDelivery(message: Readonly<Record<string, unknown>>): boolean {
153
+ if (
154
+ message.delivery !== undefined &&
155
+ message.delivery !== "queue" &&
156
+ message.delivery !== "steer" &&
157
+ message.delivery !== "passive"
158
+ ) {
156
159
  return false;
157
160
  }
158
-
159
161
  if (
160
- message.delivery !== undefined
161
- && message.delivery !== "queue"
162
- && message.delivery !== "steer"
163
- && message.delivery !== "passive"
162
+ message.passive === true &&
163
+ message.delivery !== undefined &&
164
+ message.delivery !== "passive"
164
165
  ) {
165
166
  return false;
166
167
  }
168
+ return !(
169
+ (message.passive === true || message.delivery === "passive") &&
170
+ message.expectsReply === true
171
+ );
172
+ }
167
173
 
174
+ function validQueue(message: Readonly<Record<string, unknown>>): boolean {
168
175
  if (
169
- message.queueMode !== undefined
170
- && message.queueMode !== "stack"
171
- && message.queueMode !== "replace"
176
+ message.queueMode !== undefined &&
177
+ message.queueMode !== "stack" &&
178
+ message.queueMode !== "replace"
172
179
  ) {
173
180
  return false;
174
181
  }
175
-
176
- if (message.threadId !== undefined && (typeof message.threadId !== "string" || !safeLabel(message.threadId.trim()))) {
182
+ if (message.queueMode !== undefined && message.delivery !== "queue") {
177
183
  return false;
178
184
  }
179
-
180
- if (message.passive === true && message.delivery !== undefined && message.delivery !== "passive") {
185
+ if (message.queueMode === "replace" && typeof message.threadId !== "string") {
181
186
  return false;
182
187
  }
183
-
184
- if ((message.passive === true || message.delivery === "passive") && message.expectsReply === true) {
185
- return false;
188
+ if (message.threadId === undefined) {
189
+ return true;
186
190
  }
191
+ return validThread(message);
192
+ }
187
193
 
188
- if (message.queueMode !== undefined && message.delivery !== "queue") {
189
- return false;
190
- }
194
+ function validThread(message: Readonly<Record<string, unknown>>): boolean {
195
+ return (
196
+ typeof message.threadId === "string" &&
197
+ safeLabel(message.threadId.trim()) &&
198
+ message.queueMode === "replace"
199
+ );
200
+ }
191
201
 
192
- if (message.queueMode === "replace" && typeof message.threadId !== "string") {
202
+ function validContent(value: unknown): boolean {
203
+ if (!isRecord(value) || !safeText(value.text)) {
193
204
  return false;
194
205
  }
206
+ return (
207
+ value.attachments === undefined ||
208
+ (isUnknownArray(value.attachments) && value.attachments.every(isAttachment))
209
+ );
210
+ }
195
211
 
196
- if (message.threadId !== undefined && message.queueMode !== "replace") {
212
+ export function isMessage(value: unknown): value is Message {
213
+ if (!isRecord(value) || !safeLabel(value.id) || !finiteNumber(value.timestamp)) {
197
214
  return false;
198
215
  }
216
+ return (
217
+ optionalLabel(value.replyTo) &&
218
+ optionalBoolean(value.expectsReply) &&
219
+ optionalBoolean(value.passive) &&
220
+ validMessageOrigin(value) &&
221
+ validDelivery(value) &&
222
+ validQueue(value) &&
223
+ validContent(value.content)
224
+ );
225
+ }
199
226
 
200
- if (typeof message.content !== "object" || message.content === null) {
227
+ function validSessionHealth(session: Readonly<Record<string, unknown>>): boolean {
228
+ if (
229
+ !optionalFiniteNumber(session.lastSeen) ||
230
+ !optionalFiniteNumber(session.lastIntercomActivity) ||
231
+ !optionalBoolean(session.acceptsAsks)
232
+ ) {
201
233
  return false;
202
234
  }
235
+ return (
236
+ session.pendingAsks === undefined ||
237
+ (finiteNumber(session.pendingAsks) &&
238
+ Number.isInteger(session.pendingAsks) &&
239
+ session.pendingAsks >= 0)
240
+ );
241
+ }
242
+
243
+ function validSessionTopics(session: Readonly<Record<string, unknown>>): boolean {
244
+ return (
245
+ (session.subscriptions === undefined ||
246
+ (isUnknownArray(session.subscriptions) &&
247
+ session.subscriptions.every(isTopicSubscription))) &&
248
+ (session.topics === undefined ||
249
+ (isUnknownArray(session.topics) && session.topics.every(isTopicUpdate)))
250
+ );
251
+ }
203
252
 
204
- const content = message.content as Record<string, unknown>;
205
- if (typeof content.text !== "string" || !safeText(content.text)) {
253
+ export function isSessionRegistration(value: unknown): value is Omit<SessionInfo, "id"> {
254
+ if (!isRecord(value) || !safeLabel(value.cwd) || !safeLabel(value.model)) {
206
255
  return false;
207
256
  }
208
-
209
- return content.attachments === undefined
210
- || (Array.isArray(content.attachments) && content.attachments.every(isAttachment));
257
+ const validProject =
258
+ value.projectId === undefined ||
259
+ (typeof value.projectId === "string" && /^[a-f0-9]{64}$/.test(value.projectId));
260
+ return (
261
+ optionalLabel(value.name) &&
262
+ optionalLabel(value.status) &&
263
+ validProject &&
264
+ validSessionHealth(value) &&
265
+ validSessionTopics(value)
266
+ );
211
267
  }
212
268
 
213
- export function isSessionRegistration(value: unknown): value is Omit<SessionInfo, "id"> {
214
- if (typeof value !== "object" || value === null || Array.isArray(value)) return false;
215
- const session = value as Record<string, unknown>;
216
- if (typeof session.cwd !== "string" || !safeLabel(session.cwd) || typeof session.model !== "string" || !safeLabel(session.model)) return false;
217
- if (session.name !== undefined && (typeof session.name !== "string" || !safeLabel(session.name))) return false;
218
- if (session.projectId !== undefined && (typeof session.projectId !== "string" || !/^[a-f0-9]{64}$/.test(session.projectId))) return false;
219
- if (session.status !== undefined && (typeof session.status !== "string" || !safeLabel(session.status))) return false;
220
- if (session.lastSeen !== undefined && (typeof session.lastSeen !== "number" || !Number.isFinite(session.lastSeen))) return false;
221
- if (session.lastIntercomActivity !== undefined && (typeof session.lastIntercomActivity !== "number" || !Number.isFinite(session.lastIntercomActivity))) return false;
222
- if (session.pendingAsks !== undefined && (typeof session.pendingAsks !== "number" || !Number.isInteger(session.pendingAsks) || session.pendingAsks < 0)) return false;
223
- if (session.subscriptions !== undefined && (!Array.isArray(session.subscriptions) || !session.subscriptions.every(isTopicSubscription))) return false;
224
- if (session.topics !== undefined && (!Array.isArray(session.topics) || !session.topics.every(isTopicUpdate))) return false;
225
- return session.acceptsAsks === undefined || typeof session.acceptsAsks === "boolean";
269
+ export function normalizeSessionInfo(value: unknown): SessionInfo | null {
270
+ if (!isRecord(value) || typeof value.id !== "string") {
271
+ return null;
272
+ }
273
+ const id = value.id;
274
+ if (isSessionRegistration(value)) {
275
+ return { ...value, id };
276
+ }
277
+ if (!("projectId" in value)) {
278
+ return null;
279
+ }
280
+ const { projectId: _projectId, ...withoutProjectId } = value;
281
+ return isSessionRegistration(withoutProjectId) ? { ...withoutProjectId, id } : null;
226
282
  }
227
283
 
228
284
  export interface SendResult {
229
- id: string;
230
- accepted: boolean;
231
- delivered: boolean;
232
- queued?: boolean;
233
- reason?: string;
285
+ readonly id: string;
286
+ readonly accepted: boolean;
287
+ readonly delivered: boolean;
288
+ readonly queued?: boolean;
289
+ readonly reason?: string;
234
290
  }
235
-
236
291
  export type TopicChange =
237
- | { action: "publish" | "restore"; topic: TopicUpdate }
238
- | { action: "subscribe" | "restore"; subscription: TopicSubscription }
239
- | { action: "unsubscribe"; topic: string };
292
+ | { readonly action: "publish" | "restore"; readonly topic: TopicUpdate }
293
+ | { readonly action: "subscribe" | "restore"; readonly subscription: TopicSubscription }
294
+ | { readonly action: "unsubscribe"; readonly topic: string };
240
295
  export interface SessionSnapshot {
241
- sessions: SessionInfo[];
242
- receipts: Array<SendResult & { to: string }>;
296
+ readonly sessions: readonly SessionInfo[];
297
+ readonly receipts: readonly (SendResult & { readonly to: string })[];
243
298
  }
244
299
 
300
+ type CompactTopicMessage = Omit<Message, "topic"> & {
301
+ readonly topic?: Omit<TopicUpdate, "text"> & { readonly text?: string };
302
+ };
245
303
  /** Topic text and the standard coalescing key need only one copy on the wire. */
246
- export function compactTopicMessage(message: Message) {
247
- if (!message.topic) return message;
248
- return { ...message,
249
- topic: message.topic.text === message.content.text ? { ...message.topic, text: undefined } : message.topic,
250
- threadId: message.queueMode === "replace" && message.threadId === `topic:${message.topic.topic}` ? undefined : message.threadId,
304
+ export function compactTopicMessage(message: Message): CompactTopicMessage {
305
+ if (!message.topic) {
306
+ return message;
307
+ }
308
+ return {
309
+ ...message,
310
+ topic:
311
+ message.topic.text === message.content.text
312
+ ? { ...message.topic, text: undefined }
313
+ : message.topic,
314
+ threadId:
315
+ message.queueMode === "replace" && message.threadId === `topic:${message.topic.topic}`
316
+ ? undefined
317
+ : message.threadId,
251
318
  };
252
319
  }
253
320
 
254
321
  export function normalizeMessage(value: unknown): Message | null {
255
- if (isMessage(value)) return value;
256
- if (!value || typeof value !== "object") return null;
257
- const message = value as Partial<Message>;
258
- if (!message.topic || typeof message.topic !== "object" || !message.content) return null;
259
- const restored = { ...message, topic: { ...message.topic, text: message.topic.text === undefined ? message.content.text : message.topic.text },
260
- ...(message.queueMode === "replace" && message.threadId === undefined ? { threadId: `topic:${message.topic.topic}` } : {}) };
322
+ if (isMessage(value)) {
323
+ return value;
324
+ }
325
+ if (
326
+ !isRecord(value) ||
327
+ !isRecord(value.topic) ||
328
+ !isRecord(value.content) ||
329
+ typeof value.topic.topic !== "string"
330
+ ) {
331
+ return null;
332
+ }
333
+ const restored = {
334
+ ...value,
335
+ topic: {
336
+ ...value.topic,
337
+ text: value.topic.text === undefined ? value.content.text : value.topic.text,
338
+ },
339
+ ...(value.queueMode === "replace" && value.threadId === undefined
340
+ ? { threadId: `topic:${value.topic.topic}` }
341
+ : {}),
342
+ };
261
343
  return isMessage(restored) ? restored : null;
262
344
  }
263
345
 
264
346
  export type BrokerMessage =
265
- | { type: "registered"; sessionId: string; topicsSupported?: true; topicFrames?: true }
266
- | { type: "sessions"; requestId: string; sessions: Array<Partial<SessionInfo> & Pick<SessionInfo, "id">>; more?: boolean; receipts?: SessionSnapshot["receipts"]; error?: string }
267
- | { type: "message"; from: SessionInfo; message: Message | ReturnType<typeof compactTopicMessage> }
268
- | { type: "session_left"; sessionId: string }
269
- | { type: "delivered"; messageId: string }
270
- | { type: "delivery_queued"; messageId: string; reason: string }
271
- | { type: "delivery_failed"; messageId: string; reason: string };
347
+ | {
348
+ readonly type: "registered";
349
+ readonly sessionId: string;
350
+ readonly topicsSupported?: true;
351
+ readonly topicFrames?: true;
352
+ }
353
+ | {
354
+ readonly type: "sessions";
355
+ readonly requestId: string;
356
+ readonly sessions: readonly (Partial<SessionInfo> & Pick<SessionInfo, "id">)[];
357
+ readonly more?: boolean;
358
+ readonly receipts?: SessionSnapshot["receipts"];
359
+ readonly error?: string;
360
+ }
361
+ | {
362
+ readonly type: "message";
363
+ readonly from: SessionInfo;
364
+ readonly message: Message | CompactTopicMessage;
365
+ }
366
+ | { readonly type: "session_left"; readonly sessionId: string }
367
+ | { readonly type: "delivered"; readonly messageId: string }
368
+ | { readonly type: "delivery_queued"; readonly messageId: string; readonly reason: string }
369
+ | { readonly type: "delivery_failed"; readonly messageId: string; readonly reason: string };
@@ -0,0 +1,109 @@
1
+ const START = "\x1b[200~";
2
+ const END = "\x1b[201~";
3
+ const MAX_PASTE_CHARS = 1_000_000;
4
+ const IDLE_MS = 200;
5
+ export const PASTE_RENDER_TAIL_CHARS = 8192;
6
+
7
+ export function printableInput(text: string): string {
8
+ return Array.from(text)
9
+ .filter((character) => character >= " " || character === "\n" || character === "\t")
10
+ .join("");
11
+ }
12
+
13
+ interface PasteHandlers {
14
+ readonly flush: (text: string) => void;
15
+ readonly escape: (prefix: string) => void;
16
+ readonly render: () => void;
17
+ }
18
+
19
+ /** Owns split bracketed-paste prefixes, bounded buffering and the idle fallback timer. */
20
+ export class ComposePaste {
21
+ private buffer: string | null = null;
22
+ private prefix = "";
23
+ private timer: NodeJS.Timeout | null = null;
24
+
25
+ private readonly handlers: PasteHandlers;
26
+
27
+ constructor(handlers: PasteHandlers) {
28
+ this.handlers = handlers;
29
+ }
30
+
31
+ dispose(): void {
32
+ this.clearTimer();
33
+ }
34
+ get busy(): boolean {
35
+ return this.buffer !== null || this.prefix.length > 0;
36
+ }
37
+ get preview(): string {
38
+ return printableInput(this.buffer?.slice(-PASTE_RENDER_TAIL_CHARS) ?? "");
39
+ }
40
+
41
+ private clearTimer(): void {
42
+ if (this.timer) {
43
+ clearTimeout(this.timer);
44
+ }
45
+ this.timer = null;
46
+ }
47
+
48
+ private waitForBody(): void {
49
+ this.clearTimer();
50
+ this.timer = setTimeout(() => {
51
+ this.timer = null;
52
+ if (this.buffer === null) {
53
+ return;
54
+ }
55
+ const text = printableInput(this.buffer.replace(/\r\n?/g, "\n"));
56
+ this.buffer = null;
57
+ this.handlers.flush(text);
58
+ }, IDLE_MS);
59
+ this.timer.unref();
60
+ this.handlers.render();
61
+ }
62
+
63
+ private waitForPrefix(text: string): void {
64
+ this.prefix = text;
65
+ this.timer = setTimeout(() => {
66
+ this.timer = null;
67
+ const prefix = this.prefix;
68
+ this.prefix = "";
69
+ if (prefix === "\x1b") {
70
+ this.handlers.escape(prefix);
71
+ }
72
+ }, IDLE_MS);
73
+ this.timer.unref();
74
+ }
75
+
76
+ private consumeBody(body: string): string | undefined {
77
+ const end = body.indexOf(END);
78
+ if (end === -1 && body.length <= MAX_PASTE_CHARS) {
79
+ this.buffer = body;
80
+ this.waitForBody();
81
+ return;
82
+ }
83
+ this.buffer = null;
84
+ this.clearTimer();
85
+ const text = end === -1 ? body : body.slice(0, end) + body.slice(end + END.length);
86
+ return text.replace(/\r\n?/g, "\n");
87
+ }
88
+
89
+ consume(input: string): { readonly text: string; readonly pasted: boolean } | undefined {
90
+ if (this.buffer !== null) {
91
+ const text = this.consumeBody(this.buffer + input);
92
+ return text === undefined ? undefined : { text, pasted: true };
93
+ }
94
+ const text = this.prefix + input;
95
+ if (this.prefix.length > 0) {
96
+ this.clearTimer();
97
+ this.prefix = "";
98
+ }
99
+ if (text !== START && START.startsWith(text)) {
100
+ this.waitForPrefix(text);
101
+ return;
102
+ }
103
+ if (text.startsWith(START)) {
104
+ const body = this.consumeBody(text.slice(START.length));
105
+ return body === undefined ? undefined : { text: body, pasted: true };
106
+ }
107
+ return { text: text.replaceAll(END, ""), pasted: false };
108
+ }
109
+ }