@ashx-j/lunr 0.2.19 → 0.2.21

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 (259) hide show
  1. package/CHANGELOG.md +36 -1
  2. package/README.md +2 -2
  3. package/dist/builtin-extensions/index.d.ts.map +1 -1
  4. package/dist/builtin-extensions/index.js +0 -2
  5. package/dist/builtin-extensions/index.js.map +1 -1
  6. package/dist/builtin-extensions/lunr-todos.d.ts +6 -5
  7. package/dist/builtin-extensions/lunr-todos.d.ts.map +1 -1
  8. package/dist/builtin-extensions/lunr-todos.js +9 -7
  9. package/dist/builtin-extensions/lunr-todos.js.map +1 -1
  10. package/dist/builtin-extensions/pi-intercom/broker/spawn.d.ts +6 -4
  11. package/dist/builtin-extensions/pi-intercom/broker/spawn.d.ts.map +1 -1
  12. package/dist/builtin-extensions/pi-intercom/broker/spawn.js +114 -61
  13. package/dist/builtin-extensions/pi-intercom/broker/spawn.js.map +1 -1
  14. package/dist/builtin-extensions/pi-intercom/index.d.ts.map +1 -1
  15. package/dist/builtin-extensions/pi-intercom/index.js +360 -351
  16. package/dist/builtin-extensions/pi-intercom/index.js.map +1 -1
  17. package/dist/builtin-extensions/pi-subagents/src/extension/fanout-child.d.ts.map +1 -1
  18. package/dist/builtin-extensions/pi-subagents/src/extension/fanout-child.js +2 -2
  19. package/dist/builtin-extensions/pi-subagents/src/extension/fanout-child.js.map +1 -1
  20. package/dist/builtin-extensions/pi-subagents/src/extension/index.d.ts +8 -6
  21. package/dist/builtin-extensions/pi-subagents/src/extension/index.d.ts.map +1 -1
  22. package/dist/builtin-extensions/pi-subagents/src/extension/index.js +128 -57
  23. package/dist/builtin-extensions/pi-subagents/src/extension/index.js.map +1 -1
  24. package/dist/builtin-extensions/pi-subagents/src/extension/schemas.d.ts +18 -8
  25. package/dist/builtin-extensions/pi-subagents/src/extension/schemas.d.ts.map +1 -1
  26. package/dist/builtin-extensions/pi-subagents/src/extension/schemas.js +38 -13
  27. package/dist/builtin-extensions/pi-subagents/src/extension/schemas.js.map +1 -1
  28. package/dist/builtin-extensions/pi-subagents/src/extension/tool-description.d.ts +4 -3
  29. package/dist/builtin-extensions/pi-subagents/src/extension/tool-description.d.ts.map +1 -1
  30. package/dist/builtin-extensions/pi-subagents/src/extension/tool-description.js +24 -14
  31. package/dist/builtin-extensions/pi-subagents/src/extension/tool-description.js.map +1 -1
  32. package/dist/builtin-extensions/pi-subagents/src/intercom/native-supervisor-channel.d.ts +8 -1
  33. package/dist/builtin-extensions/pi-subagents/src/intercom/native-supervisor-channel.d.ts.map +1 -1
  34. package/dist/builtin-extensions/pi-subagents/src/intercom/native-supervisor-channel.js +247 -18
  35. package/dist/builtin-extensions/pi-subagents/src/intercom/native-supervisor-channel.js.map +1 -1
  36. package/dist/builtin-extensions/pi-subagents/src/intercom/result-intercom.d.ts +1 -0
  37. package/dist/builtin-extensions/pi-subagents/src/intercom/result-intercom.d.ts.map +1 -1
  38. package/dist/builtin-extensions/pi-subagents/src/intercom/result-intercom.js +1 -1
  39. package/dist/builtin-extensions/pi-subagents/src/intercom/result-intercom.js.map +1 -1
  40. package/dist/builtin-extensions/pi-subagents/src/intercom/supervisor-ask.d.ts +29 -0
  41. package/dist/builtin-extensions/pi-subagents/src/intercom/supervisor-ask.d.ts.map +1 -0
  42. package/dist/builtin-extensions/pi-subagents/src/intercom/supervisor-ask.js +179 -0
  43. package/dist/builtin-extensions/pi-subagents/src/intercom/supervisor-ask.js.map +1 -0
  44. package/dist/builtin-extensions/pi-subagents/src/intercom/supervisor-questions.d.ts +89 -0
  45. package/dist/builtin-extensions/pi-subagents/src/intercom/supervisor-questions.d.ts.map +1 -0
  46. package/dist/builtin-extensions/pi-subagents/src/intercom/supervisor-questions.js +541 -0
  47. package/dist/builtin-extensions/pi-subagents/src/intercom/supervisor-questions.js.map +1 -0
  48. package/dist/builtin-extensions/pi-subagents/src/runs/background/async-execution.d.ts +11 -1
  49. package/dist/builtin-extensions/pi-subagents/src/runs/background/async-execution.d.ts.map +1 -1
  50. package/dist/builtin-extensions/pi-subagents/src/runs/background/async-execution.js +38 -12
  51. package/dist/builtin-extensions/pi-subagents/src/runs/background/async-execution.js.map +1 -1
  52. package/dist/builtin-extensions/pi-subagents/src/runs/background/async-job-tracker.d.ts.map +1 -1
  53. package/dist/builtin-extensions/pi-subagents/src/runs/background/async-job-tracker.js +3 -2
  54. package/dist/builtin-extensions/pi-subagents/src/runs/background/async-job-tracker.js.map +1 -1
  55. package/dist/builtin-extensions/pi-subagents/src/runs/background/async-resume.d.ts +2 -1
  56. package/dist/builtin-extensions/pi-subagents/src/runs/background/async-resume.d.ts.map +1 -1
  57. package/dist/builtin-extensions/pi-subagents/src/runs/background/async-resume.js +35 -8
  58. package/dist/builtin-extensions/pi-subagents/src/runs/background/async-resume.js.map +1 -1
  59. package/dist/builtin-extensions/pi-subagents/src/runs/background/notify.d.ts +7 -3
  60. package/dist/builtin-extensions/pi-subagents/src/runs/background/notify.d.ts.map +1 -1
  61. package/dist/builtin-extensions/pi-subagents/src/runs/background/notify.js +26 -4
  62. package/dist/builtin-extensions/pi-subagents/src/runs/background/notify.js.map +1 -1
  63. package/dist/builtin-extensions/pi-subagents/src/runs/background/result-watcher.d.ts +1 -0
  64. package/dist/builtin-extensions/pi-subagents/src/runs/background/result-watcher.d.ts.map +1 -1
  65. package/dist/builtin-extensions/pi-subagents/src/runs/background/result-watcher.js +55 -38
  66. package/dist/builtin-extensions/pi-subagents/src/runs/background/result-watcher.js.map +1 -1
  67. package/dist/builtin-extensions/pi-subagents/src/runs/background/subagent-runner.d.ts +100 -0
  68. package/dist/builtin-extensions/pi-subagents/src/runs/background/subagent-runner.d.ts.map +1 -1
  69. package/dist/builtin-extensions/pi-subagents/src/runs/background/subagent-runner.js +46 -31
  70. package/dist/builtin-extensions/pi-subagents/src/runs/background/subagent-runner.js.map +1 -1
  71. package/dist/builtin-extensions/pi-subagents/src/runs/background/subagent-wait.d.ts +3 -6
  72. package/dist/builtin-extensions/pi-subagents/src/runs/background/subagent-wait.d.ts.map +1 -1
  73. package/dist/builtin-extensions/pi-subagents/src/runs/background/subagent-wait.js +64 -5
  74. package/dist/builtin-extensions/pi-subagents/src/runs/background/subagent-wait.js.map +1 -1
  75. package/dist/builtin-extensions/pi-subagents/src/runs/background/top-level-async.d.ts +15 -2
  76. package/dist/builtin-extensions/pi-subagents/src/runs/background/top-level-async.d.ts.map +1 -1
  77. package/dist/builtin-extensions/pi-subagents/src/runs/background/top-level-async.js +14 -4
  78. package/dist/builtin-extensions/pi-subagents/src/runs/background/top-level-async.js.map +1 -1
  79. package/dist/builtin-extensions/pi-subagents/src/runs/background/wait-tool.d.ts.map +1 -1
  80. package/dist/builtin-extensions/pi-subagents/src/runs/background/wait-tool.js +2 -1
  81. package/dist/builtin-extensions/pi-subagents/src/runs/background/wait-tool.js.map +1 -1
  82. package/dist/builtin-extensions/pi-subagents/src/runs/foreground/chain-execution.d.ts.map +1 -1
  83. package/dist/builtin-extensions/pi-subagents/src/runs/foreground/chain-execution.js +21 -8
  84. package/dist/builtin-extensions/pi-subagents/src/runs/foreground/chain-execution.js.map +1 -1
  85. package/dist/builtin-extensions/pi-subagents/src/runs/foreground/execution.d.ts.map +1 -1
  86. package/dist/builtin-extensions/pi-subagents/src/runs/foreground/execution.js +1 -1
  87. package/dist/builtin-extensions/pi-subagents/src/runs/foreground/execution.js.map +1 -1
  88. package/dist/builtin-extensions/pi-subagents/src/runs/foreground/subagent-executor.d.ts +0 -1
  89. package/dist/builtin-extensions/pi-subagents/src/runs/foreground/subagent-executor.d.ts.map +1 -1
  90. package/dist/builtin-extensions/pi-subagents/src/runs/foreground/subagent-executor.js +71 -25
  91. package/dist/builtin-extensions/pi-subagents/src/runs/foreground/subagent-executor.js.map +1 -1
  92. package/dist/builtin-extensions/pi-subagents/src/runs/shared/acceptance.d.ts +2 -0
  93. package/dist/builtin-extensions/pi-subagents/src/runs/shared/acceptance.d.ts.map +1 -1
  94. package/dist/builtin-extensions/pi-subagents/src/runs/shared/acceptance.js +75 -18
  95. package/dist/builtin-extensions/pi-subagents/src/runs/shared/acceptance.js.map +1 -1
  96. package/dist/builtin-extensions/pi-subagents/src/runs/shared/completion-guard.d.ts +1 -1
  97. package/dist/builtin-extensions/pi-subagents/src/runs/shared/completion-guard.d.ts.map +1 -1
  98. package/dist/builtin-extensions/pi-subagents/src/runs/shared/completion-guard.js +1 -1
  99. package/dist/builtin-extensions/pi-subagents/src/runs/shared/completion-guard.js.map +1 -1
  100. package/dist/builtin-extensions/pi-subagents/src/runs/shared/model-fallback.d.ts +13 -1
  101. package/dist/builtin-extensions/pi-subagents/src/runs/shared/model-fallback.d.ts.map +1 -1
  102. package/dist/builtin-extensions/pi-subagents/src/runs/shared/model-fallback.js +67 -11
  103. package/dist/builtin-extensions/pi-subagents/src/runs/shared/model-fallback.js.map +1 -1
  104. package/dist/builtin-extensions/pi-subagents/src/runs/shared/parallel-utils.d.ts +1 -0
  105. package/dist/builtin-extensions/pi-subagents/src/runs/shared/parallel-utils.d.ts.map +1 -1
  106. package/dist/builtin-extensions/pi-subagents/src/runs/shared/parallel-utils.js.map +1 -1
  107. package/dist/builtin-extensions/pi-subagents/src/runs/shared/pi-args.d.ts +3 -0
  108. package/dist/builtin-extensions/pi-subagents/src/runs/shared/pi-args.d.ts.map +1 -1
  109. package/dist/builtin-extensions/pi-subagents/src/runs/shared/pi-args.js +7 -2
  110. package/dist/builtin-extensions/pi-subagents/src/runs/shared/pi-args.js.map +1 -1
  111. package/dist/builtin-extensions/pi-subagents/src/runs/shared/subagent-prompt-runtime.d.ts.map +1 -1
  112. package/dist/builtin-extensions/pi-subagents/src/runs/shared/subagent-prompt-runtime.js +13 -3
  113. package/dist/builtin-extensions/pi-subagents/src/runs/shared/subagent-prompt-runtime.js.map +1 -1
  114. package/dist/builtin-extensions/pi-subagents/src/runs/shared/task-intent.d.ts +2 -2
  115. package/dist/builtin-extensions/pi-subagents/src/runs/shared/task-intent.d.ts.map +1 -1
  116. package/dist/builtin-extensions/pi-subagents/src/runs/shared/task-intent.js +5 -10
  117. package/dist/builtin-extensions/pi-subagents/src/runs/shared/task-intent.js.map +1 -1
  118. package/dist/builtin-extensions/pi-subagents/src/shared/async-guidance.d.ts +2 -0
  119. package/dist/builtin-extensions/pi-subagents/src/shared/async-guidance.d.ts.map +1 -0
  120. package/dist/builtin-extensions/pi-subagents/src/shared/async-guidance.js +3 -0
  121. package/dist/builtin-extensions/pi-subagents/src/shared/async-guidance.js.map +1 -0
  122. package/dist/builtin-extensions/pi-subagents/src/shared/child-spec.d.ts +3 -0
  123. package/dist/builtin-extensions/pi-subagents/src/shared/child-spec.d.ts.map +1 -1
  124. package/dist/builtin-extensions/pi-subagents/src/shared/child-spec.js +68 -11
  125. package/dist/builtin-extensions/pi-subagents/src/shared/child-spec.js.map +1 -1
  126. package/dist/builtin-extensions/pi-subagents/src/shared/formatters.d.ts +12 -1
  127. package/dist/builtin-extensions/pi-subagents/src/shared/formatters.d.ts.map +1 -1
  128. package/dist/builtin-extensions/pi-subagents/src/shared/formatters.js +21 -2
  129. package/dist/builtin-extensions/pi-subagents/src/shared/formatters.js.map +1 -1
  130. package/dist/builtin-extensions/pi-subagents/src/shared/types.d.ts +21 -4
  131. package/dist/builtin-extensions/pi-subagents/src/shared/types.d.ts.map +1 -1
  132. package/dist/builtin-extensions/pi-subagents/src/shared/types.js +1 -1
  133. package/dist/builtin-extensions/pi-subagents/src/shared/types.js.map +1 -1
  134. package/dist/builtin-extensions/pi-subagents/src/slash/delegation-adapters.d.ts.map +1 -1
  135. package/dist/builtin-extensions/pi-subagents/src/slash/delegation-adapters.js.map +1 -1
  136. package/dist/builtin-extensions/pi-subagents/src/slash/prompt-workflows.d.ts +7 -0
  137. package/dist/builtin-extensions/pi-subagents/src/slash/prompt-workflows.d.ts.map +1 -1
  138. package/dist/builtin-extensions/pi-subagents/src/slash/prompt-workflows.js +11 -7
  139. package/dist/builtin-extensions/pi-subagents/src/slash/prompt-workflows.js.map +1 -1
  140. package/dist/builtin-extensions/pi-subagents/src/slash/slash-commands.d.ts +6 -0
  141. package/dist/builtin-extensions/pi-subagents/src/slash/slash-commands.d.ts.map +1 -1
  142. package/dist/builtin-extensions/pi-subagents/src/slash/slash-commands.js +46 -29
  143. package/dist/builtin-extensions/pi-subagents/src/slash/slash-commands.js.map +1 -1
  144. package/dist/builtin-extensions/pi-subagents/src/tui/render.d.ts +46 -4
  145. package/dist/builtin-extensions/pi-subagents/src/tui/render.d.ts.map +1 -1
  146. package/dist/builtin-extensions/pi-subagents/src/tui/render.js +407 -450
  147. package/dist/builtin-extensions/pi-subagents/src/tui/render.js.map +1 -1
  148. package/dist/builtin-extensions/pi-subagents/src/watchdog/register-main.d.ts.map +1 -1
  149. package/dist/builtin-extensions/pi-subagents/src/watchdog/register-main.js +1 -1
  150. package/dist/builtin-extensions/pi-subagents/src/watchdog/register-main.js.map +1 -1
  151. package/dist/builtin-extensions/pi-subagents/src/watchdog/tool-actions.d.ts +2 -13
  152. package/dist/builtin-extensions/pi-subagents/src/watchdog/tool-actions.d.ts.map +1 -1
  153. package/dist/builtin-extensions/pi-subagents/src/watchdog/tool-actions.js +5 -91
  154. package/dist/builtin-extensions/pi-subagents/src/watchdog/tool-actions.js.map +1 -1
  155. package/dist/core/customize.d.ts +2 -0
  156. package/dist/core/customize.d.ts.map +1 -1
  157. package/dist/core/customize.js +3 -0
  158. package/dist/core/customize.js.map +1 -1
  159. package/dist/core/permissions.d.ts +1 -0
  160. package/dist/core/permissions.d.ts.map +1 -1
  161. package/dist/core/permissions.js +8 -4
  162. package/dist/core/permissions.js.map +1 -1
  163. package/dist/core/plan-mode.d.ts.map +1 -1
  164. package/dist/core/plan-mode.js +0 -5
  165. package/dist/core/plan-mode.js.map +1 -1
  166. package/dist/core/runtime-bridges.d.ts.map +1 -1
  167. package/dist/core/runtime-bridges.js +0 -2
  168. package/dist/core/runtime-bridges.js.map +1 -1
  169. package/dist/core/settings-manager.d.ts +4 -0
  170. package/dist/core/settings-manager.d.ts.map +1 -1
  171. package/dist/core/settings-manager.js +11 -0
  172. package/dist/core/settings-manager.js.map +1 -1
  173. package/dist/core/subagent-cancellation.d.ts +21 -0
  174. package/dist/core/subagent-cancellation.d.ts.map +1 -0
  175. package/dist/core/subagent-cancellation.js +53 -0
  176. package/dist/core/subagent-cancellation.js.map +1 -0
  177. package/dist/core/subagent-spinner-setting.d.ts +6 -0
  178. package/dist/core/subagent-spinner-setting.d.ts.map +1 -0
  179. package/dist/core/subagent-spinner-setting.js +12 -0
  180. package/dist/core/subagent-spinner-setting.js.map +1 -0
  181. package/dist/core/subagent-spinner.d.ts +4 -0
  182. package/dist/core/subagent-spinner.d.ts.map +1 -0
  183. package/dist/core/subagent-spinner.js +6 -0
  184. package/dist/core/subagent-spinner.js.map +1 -0
  185. package/dist/modes/interactive/components/assistant-message.d.ts.map +1 -1
  186. package/dist/modes/interactive/components/assistant-message.js +12 -18
  187. package/dist/modes/interactive/components/assistant-message.js.map +1 -1
  188. package/dist/modes/interactive/components/settings-selector.d.ts +4 -0
  189. package/dist/modes/interactive/components/settings-selector.d.ts.map +1 -1
  190. package/dist/modes/interactive/components/settings-selector.js +73 -1
  191. package/dist/modes/interactive/components/settings-selector.js.map +1 -1
  192. package/dist/modes/interactive/components/tool-execution.d.ts.map +1 -1
  193. package/dist/modes/interactive/components/tool-execution.js +12 -0
  194. package/dist/modes/interactive/components/tool-execution.js.map +1 -1
  195. package/dist/modes/interactive/extension-widget-order.d.ts +8 -0
  196. package/dist/modes/interactive/extension-widget-order.d.ts.map +1 -0
  197. package/dist/modes/interactive/extension-widget-order.js +37 -0
  198. package/dist/modes/interactive/extension-widget-order.js.map +1 -0
  199. package/dist/modes/interactive/interactive-mode.d.ts +1 -0
  200. package/dist/modes/interactive/interactive-mode.d.ts.map +1 -1
  201. package/dist/modes/interactive/interactive-mode.js +44 -22
  202. package/dist/modes/interactive/interactive-mode.js.map +1 -1
  203. package/dist/node-runtime/{agent-session-services-35WNVGMR.js → agent-session-services-C743TYQE.js} +6 -5
  204. package/dist/node-runtime/{builtin-extensions-322XDDEM.js → builtin-extensions-JCOPAAB5.js} +3 -2
  205. package/dist/node-runtime/{chunk-XATUM2HK.js → chunk-25I2BHAA.js} +1 -1
  206. package/dist/node-runtime/{chunk-TXHKBRHZ.js → chunk-2BUAYZ7K.js} +136 -53
  207. package/dist/node-runtime/chunk-5ZH3ZFIZ.js +308 -0
  208. package/dist/node-runtime/{chunk-J26TSGDL.js → chunk-6N22HULO.js} +8 -5
  209. package/dist/node-runtime/chunk-A3KMVBZV.js +60 -0
  210. package/dist/node-runtime/{chunk-4FX25LWP.js → chunk-AWVD5IEY.js} +20 -421
  211. package/dist/node-runtime/{chunk-ZRCBN365.js → chunk-GB2MGFLI.js} +12 -12
  212. package/dist/node-runtime/chunk-LISUTZS3.js +19 -0
  213. package/dist/node-runtime/{chunk-PNJSG3IZ.js → chunk-LTYWTR3V.js} +1 -369
  214. package/dist/node-runtime/{chunk-TFBIJTM3.js → chunk-PDNXVXMD.js} +13 -13
  215. package/dist/node-runtime/{chunk-MCUNIRD5.js → chunk-SY2TFMLO.js} +532 -261
  216. package/dist/node-runtime/{chunk-HQCKFM2O.js → chunk-VGYZ3APQ.js} +3 -0
  217. package/dist/node-runtime/{chunk-4DJ6HEGH.js → chunk-VZR3NCM7.js} +3 -3
  218. package/dist/node-runtime/chunk-W3SILANP.js +24 -0
  219. package/dist/node-runtime/{chunk-CBGB57XT.js → chunk-WLLDXJRT.js} +10 -0
  220. package/dist/node-runtime/{chunk-ATGA2WLC.js → chunk-XI77KVKA.js} +399 -36
  221. package/dist/node-runtime/{chunk-4CSFRBCN.js → chunk-Y5KOEMBH.js} +1 -1
  222. package/dist/node-runtime/{chunk-AROOY4BB.js → chunk-YMEAYRBE.js} +1 -1
  223. package/dist/node-runtime/{command-DWUM5X3U.js → command-P4NYCJ2M.js} +1 -1
  224. package/dist/node-runtime/{customize-XEXL2DGQ.js → customize-LF5VST47.js} +1 -1
  225. package/dist/node-runtime/{gateway-UZXMFGWY.js → gateway-BM6NLOH4.js} +2 -2
  226. package/dist/node-runtime/index.js +16 -13
  227. package/dist/node-runtime/{interactive-mode-QT5IKGQ5.js → interactive-mode-EVVBA64D.js} +11 -8
  228. package/dist/node-runtime/{lunr-cron-QPBTKBGI.js → lunr-cron-4VHP4E4B.js} +2 -2
  229. package/dist/node-runtime/main.js +14 -12
  230. package/dist/node-runtime/{package-manager-cli-7RKSZGEN.js → package-manager-cli-N37546V5.js} +5 -4
  231. package/dist/node-runtime/{pi-intercom-EEMBGQID.js → pi-intercom-NV2LW6X7.js} +108 -87
  232. package/dist/node-runtime/{pi-subagents-7YJ3I4VE.js → pi-subagents-6MUIFNDM.js} +1262 -599
  233. package/dist/node-runtime/rpc-entry.js +14 -12
  234. package/dist/node-runtime/{runtime-bridges-3RKBDLNA.js → runtime-bridges-2VQTLPOZ.js} +3 -5
  235. package/dist/node-runtime/{settings-manager-GHPTUN7R.js → settings-manager-CUGAZWAB.js} +2 -1
  236. package/dist/node-runtime/{subagent-executor-5Q5A4HJ2.js → subagent-executor-MH4A7CCF.js} +181 -294
  237. package/dist/node-runtime/{update-cli-L3JIBH2U.js → update-cli-XTZMZGOL.js} +2 -1
  238. package/docs/features.md +22 -4
  239. package/docs/keybindings.md +3 -1
  240. package/docs/settings.md +3 -2
  241. package/examples/extensions/custom-provider-anthropic/package-lock.json +2 -2
  242. package/examples/extensions/custom-provider-anthropic/package.json +1 -1
  243. package/examples/extensions/custom-provider-gitlab-duo/package.json +1 -1
  244. package/examples/extensions/gondolin/package-lock.json +2 -2
  245. package/examples/extensions/gondolin/package.json +1 -1
  246. package/examples/extensions/sandbox/package-lock.json +2 -2
  247. package/examples/extensions/sandbox/package.json +1 -1
  248. package/examples/extensions/with-deps/package-lock.json +2 -2
  249. package/examples/extensions/with-deps/package.json +1 -1
  250. package/package.json +4 -4
  251. package/dist/builtin-extensions/lunr-settings-tools.d.ts +0 -4
  252. package/dist/builtin-extensions/lunr-settings-tools.d.ts.map +0 -1
  253. package/dist/builtin-extensions/lunr-settings-tools.js +0 -120
  254. package/dist/builtin-extensions/lunr-settings-tools.js.map +0 -1
  255. package/dist/core/settings-tools-bridge.d.ts +0 -35
  256. package/dist/core/settings-tools-bridge.d.ts.map +0 -1
  257. package/dist/core/settings-tools-bridge.js +0 -56
  258. package/dist/core/settings-tools-bridge.js.map +0 -1
  259. package/dist/node-runtime/chunk-3NMWLTPV.js +0 -64
@@ -1 +1 @@
1
- {"version":3,"file":"notify.js","sourceRoot":"","sources":["../../../../../../src/builtin-extensions/pi-subagents/src/runs/background/notify.ts"],"names":[],"mappings":"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","sourcesContent":["// @ts-nocheck\n/**\n * Subagent completion notifications.\n *\n * Successful (completed) async results are held briefly and emitted as a\n * single grouped message when sibling jobs finish within a short window (see\n * `completion-batcher.ts`). Failed and paused results bypass grouping and fire\n * immediately, flushing any held successes first, so failure and attention\n * signals are never delayed.\n */\n\nimport type { ExtensionAPI } from \"@ashx-j/lunr\";\nimport { buildCompletionKey, getGlobalSeenMap, markSeenWithTtl } from \"./completion-dedupe.ts\";\nimport {\n\ttype CompletionBatchConfig,\n\ttype CompletionBatcher,\n\tcreateCompletionBatcher,\n\tresolveCompletionBatchConfig,\n} from \"./completion-batcher.ts\";\nimport { SUBAGENT_ASYNC_COMPLETE_EVENT, SUBAGENT_FOREGROUND_COMPLETE_EVENT, type SubagentState } from \"../../shared/types.ts\";\n\ninterface ChainStepResult {\n\tagent: string;\n\toutput: string;\n\tsuccess: boolean;\n}\n\nexport interface SubagentNotifyDetails {\n\tagent: string;\n\tstatus: \"completed\" | \"failed\" | \"paused\";\n\tsource?: \"async\" | \"foreground\";\n\ttaskInfo?: string;\n\tresultPreview: string;\n\tdurationMs?: number;\n\tsessionLabel?: string;\n\tsessionValue?: string;\n}\n\ninterface SubagentResult {\n\tid: string | null;\n\tsource?: \"async\" | \"foreground\";\n\tagent: string | null;\n\tsuccess: boolean;\n\tsummary: string;\n\texitCode?: number;\n\tstate?: string;\n\ttimestamp: number;\n\tdurationMs?: number;\n\tcwd?: string;\n\tsessionFile?: string;\n\tshareUrl?: string;\n\tgistUrl?: string;\n\tshareError?: string;\n\tresults?: ChainStepResult[];\n\ttaskIndex?: number;\n\ttotalTasks?: number;\n\tsessionId?: string | null;\n}\n\ninterface NotifyTimerApi {\n\tsetTimeout(handler: () => void, delayMs: number): unknown;\n\tclearTimeout(handle: unknown): void;\n}\n\nexport interface RegisterSubagentNotifyOptions {\n\tbatchConfig?: CompletionBatchConfig;\n\ttimers?: NotifyTimerApi;\n\tnow?: () => number;\n}\n\nfunction formatSessionLine(details: SubagentNotifyDetails): string | undefined {\n\tif (!details.sessionValue) return undefined;\n\treturn details.sessionLabel ? `${details.sessionLabel}: ${details.sessionValue}` : details.sessionValue;\n}\n\nexport function formatSingleCompletion(details: SubagentNotifyDetails): string {\n\tconst sessionLine = formatSessionLine(details);\n\tconst taskKind = details.source === \"foreground\" ? \"Detached foreground task\" : \"Background task\";\n\treturn [\n\t\t`${taskKind} ${details.status}: **${details.agent}**${details.taskInfo ?? \"\"}`,\n\t\t\"\",\n\t\tdetails.resultPreview.trim() ? details.resultPreview : \"(no output)\",\n\t\tsessionLine ? \"\" : undefined,\n\t\tsessionLine,\n\t]\n\t\t.filter((line) => line !== undefined)\n\t\t.join(\"\\n\");\n}\n\nexport function parseSubagentNotifyContent(content: string): SubagentNotifyDetails | undefined {\n\tconst lines = content.split(\"\\n\");\n\tconst match = (lines[0] ?? \"\").match(/^(Background task|Detached foreground task) (completed|failed|paused): \\*\\*(.+?)\\*\\*(?:\\s+(\\([^)]*\\)))?$/);\n\tif (!match) return undefined;\n\tconst body = lines.slice(2);\n\tlet sessionIndex = -1;\n\tfor (let i = body.length - 1; i >= 1; i--) {\n\t\tif (body[i - 1]?.trim() === \"\" && /^(Session|Session file|Session share error):\\s+/.test(body[i]!)) {\n\t\t\tsessionIndex = i;\n\t\t\tbreak;\n\t\t}\n\t}\n\tconst sessionLine = sessionIndex >= 0 ? body[sessionIndex] : undefined;\n\tconst resultPreview = (sessionIndex >= 0 ? body.slice(0, sessionIndex) : body).join(\"\\n\").trim() || \"(no output)\";\n\tlet sessionLabel: string | undefined;\n\tlet sessionValue: string | undefined;\n\tif (sessionLine) {\n\t\tconst separator = sessionLine.indexOf(\":\");\n\t\tsessionLabel = sessionLine.slice(0, separator).toLowerCase();\n\t\tsessionValue = sessionLine.slice(separator + 1).trim();\n\t}\n\treturn {\n\t\tagent: match[3]!,\n\t\tstatus: match[2] as SubagentNotifyDetails[\"status\"],\n\t\t...(match[1] === \"Detached foreground task\" ? { source: \"foreground\" as const } : {}),\n\t\t...(match[4] ? { taskInfo: match[4] } : {}),\n\t\tresultPreview,\n\t\t...(sessionLabel && sessionValue ? { sessionLabel, sessionValue } : {}),\n\t};\n}\n\nexport function formatGroupedCompletion(details: SubagentNotifyDetails[]): string {\n\tconst header = `Background tasks completed (${details.length}): ${details.map((d) => `**${d.agent}**${d.taskInfo ?? \"\"}`).join(\", \")}`;\n\tconst blocks: string[] = [header, \"\"];\n\tfor (let index = 0; index < details.length; index++) {\n\t\tconst detail = details[index];\n\t\tif (!detail) continue;\n\t\tconst sessionLine = formatSessionLine(detail);\n\t\tblocks.push(`${index + 1}. ${detail.agent}${detail.taskInfo ?? \"\"}`);\n\t\tblocks.push(detail.resultPreview.trim() ? detail.resultPreview : \"(no output)\");\n\t\tif (sessionLine) blocks.push(sessionLine);\n\t\tblocks.push(\"\");\n\t}\n\treturn blocks.join(\"\\n\").trimEnd();\n}\n\nfunction sendCompletion(pi: Pick<ExtensionAPI, \"sendMessage\">, details: SubagentNotifyDetails[]): void {\n\tif (details.length === 0) return;\n\tconst content = details.length === 1\n\t\t? formatSingleCompletion(details[0]!)\n\t\t: formatGroupedCompletion(details);\n\tpi.sendMessage(\n\t\t{\n\t\t\tcustomType: \"subagent-notify\",\n\t\t\tcontent,\n\t\t\tdisplay: true,\n\t\t},\n\t\t{ triggerTurn: true },\n\t);\n}\n\nfunction completionBatchKey(result: SubagentResult): string {\n\tconst sessionId = typeof result.sessionId === \"string\" ? result.sessionId.trim() : \"\";\n\tif (sessionId) return `session:${sessionId}`;\n\tconst cwd = typeof result.cwd === \"string\" ? result.cwd.trim() : \"\";\n\treturn cwd ? `cwd:${cwd}` : \"unknown\";\n}\n\nexport function buildCompletionDetails(result: SubagentResult): SubagentNotifyDetails {\n\tconst agent = result.agent ?? \"unknown\";\n\tconst summary = typeof result.summary === \"string\" ? result.summary : \"\";\n\tconst paused = !result.success && (\n\t\tresult.exitCode === 0\n\t\t|| result.state === \"paused\"\n\t\t|| summary.startsWith(\"Paused after interrupt.\")\n\t);\n\tconst status = paused ? \"paused\" : result.success ? \"completed\" : \"failed\";\n\n\tconst taskInfo =\n\t\tresult.taskIndex !== undefined && result.totalTasks !== undefined\n\t\t\t? ` (${result.taskIndex + 1}/${result.totalTasks})`\n\t\t\t: undefined;\n\n\tconst session =\n\t\tresult.shareUrl\n\t\t\t? { label: \"Session\", value: result.shareUrl }\n\t\t\t: result.shareError\n\t\t\t\t? { label: \"Session share error\", value: result.shareError }\n\t\t\t\t: result.sessionFile\n\t\t\t\t\t? { label: \"Session file\", value: result.sessionFile }\n\t\t\t\t\t: undefined;\n\n\treturn {\n\t\tagent,\n\t\tstatus,\n\t\t...(result.source ? { source: result.source } : {}),\n\t\t...(taskInfo ? { taskInfo } : {}),\n\t\tresultPreview: summary,\n\t\t...(typeof result.durationMs === \"number\" ? { durationMs: result.durationMs } : {}),\n\t\t...(session ? { sessionLabel: session.label, sessionValue: session.value } : {}),\n\t};\n}\n\nexport default function registerSubagentNotify(\n\tpi: ExtensionAPI,\n\tstate: Pick<SubagentState, \"currentSessionId\">,\n\toptions: RegisterSubagentNotifyOptions = {},\n): void {\n\tconst unsubscribeStoreKey = \"__pi_subagents_notify_unsubscribe__\";\n\tconst batcherStoreKey = \"__pi_subagents_notify_batcher__\";\n\tconst globalStore = globalThis as Record<string, unknown>;\n\tconst previousUnsubscribe = globalStore[unsubscribeStoreKey];\n\tif (typeof previousUnsubscribe === \"function\") {\n\t\ttry {\n\t\t\tpreviousUnsubscribe();\n\t\t} catch {\n\t\t\t// Best effort cleanup for stale handlers from an older reload.\n\t\t}\n\t}\n\tconst previousBatcher = globalStore[batcherStoreKey];\n\tif (previousBatcher && typeof (previousBatcher as { dispose?: () => void }).dispose === \"function\") {\n\t\ttry {\n\t\t\t(previousBatcher as { dispose: () => void }).dispose();\n\t\t} catch {\n\t\t\t// Best effort cleanup for a stale batcher from an older reload.\n\t\t}\n\t}\n\n\tconst seen = getGlobalSeenMap(\"__pi_subagents_notify_seen__\");\n\tconst ttlMs = 10 * 60 * 1000;\n\tconst nowFn = options.now ?? Date.now;\n\tconst batchConfig = resolveCompletionBatchConfig(options.batchConfig);\n\tconst batchers = new Map<string, CompletionBatcher<SubagentNotifyDetails>>();\n\tglobalStore[batcherStoreKey] = {\n\t\tdispose() {\n\t\t\tfor (const batcher of batchers.values()) batcher.dispose();\n\t\t\tbatchers.clear();\n\t\t},\n\t};\n\n\tconst handleComplete = (data: unknown) => {\n\t\tconst result = data as SubagentResult;\n\t\tif (typeof result.sessionId !== \"string\" || result.sessionId !== state.currentSessionId) return;\n\t\tconst now = nowFn();\n\t\tconst key = buildCompletionKey(result, \"notify\");\n\t\tif (markSeenWithTtl(seen, key, now, ttlMs)) return;\n\n\t\tconst details = buildCompletionDetails(result);\n\t\tif (result.source === \"foreground\") {\n\t\t\tsendCompletion(pi, [details]);\n\t\t\treturn;\n\t\t}\n\t\tconst batchKey = completionBatchKey(result);\n\t\tlet batcher = batchers.get(batchKey);\n\t\tif (!batcher) {\n\t\t\tbatcher = createCompletionBatcher<SubagentNotifyDetails>({\n\t\t\t\tconfig: batchConfig,\n\t\t\t\temit: (items) => sendCompletion(pi, items),\n\t\t\t\t...(options.timers ? { timers: options.timers } : {}),\n\t\t\t\tnow: nowFn,\n\t\t\t});\n\t\t\tbatchers.set(batchKey, batcher);\n\t\t}\n\t\tif (details.status !== \"completed\") {\n\t\t\t// Failures and paused runs bypass grouping. Flush any held\n\t\t\t// successes for the same owner first so they are not stranded\n\t\t\t// behind this signal, then emit the non-completion result immediately.\n\t\t\tbatcher.flush();\n\t\t\tsendCompletion(pi, [details]);\n\t\t\treturn;\n\t\t}\n\t\tbatcher.push(details);\n\t};\n\n\tconst unsubscribers = [\n\t\tpi.events.on(SUBAGENT_ASYNC_COMPLETE_EVENT, handleComplete),\n\t\tpi.events.on(SUBAGENT_FOREGROUND_COMPLETE_EVENT, handleComplete),\n\t].filter((unsubscribe): unsubscribe is () => void => typeof unsubscribe === \"function\");\n\tglobalStore[unsubscribeStoreKey] = () => {\n\t\tfor (const unsubscribe of unsubscribers) unsubscribe();\n\t};\n}\n"]}
1
+ {"version":3,"file":"notify.js","sourceRoot":"","sources":["../../../../../../src/builtin-extensions/pi-subagents/src/runs/background/notify.ts"],"names":[],"mappings":"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","sourcesContent":["// @ts-nocheck\n/**\n * Subagent completion notifications.\n *\n * Successful (completed) async results are held briefly and emitted as a\n * single grouped message when sibling jobs finish within a short window (see\n * `completion-batcher.ts`). Failed and paused results bypass grouping and fire\n * immediately, flushing any held successes first, so failure and attention\n * signals are never delayed.\n */\n\nimport type { ExtensionAPI } from \"@ashx-j/lunr\";\nimport { buildCompletionKey, getGlobalSeenMap, markSeenWithTtl } from \"./completion-dedupe.ts\";\nimport {\n\ttype CompletionBatchConfig,\n\ttype CompletionBatcher,\n\tcreateCompletionBatcher,\n\tresolveCompletionBatchConfig,\n} from \"./completion-batcher.ts\";\nimport { formatNestedResultLines, resolveSubagentResultStatus } from \"../../intercom/result-intercom.ts\";\nimport { SUBAGENT_ASYNC_COMPLETE_EVENT, SUBAGENT_FOREGROUND_COMPLETE_EVENT, type AcceptanceLedger, type SubagentResultIntercomChild, type SubagentState } from \"../../shared/types.ts\";\n\ninterface ChainStepResult extends Partial<SubagentResultIntercomChild> {\n\tagent: string;\n\toutput: string;\n\tsummary?: string;\n\terror?: string;\n\tacceptance?: AcceptanceLedger;\n\tsuccess: boolean;\n}\n\nexport interface SubagentNotifyDetails {\n\tagent: string;\n\tstatus: \"completed\" | \"failed\" | \"paused\" | \"stopped\";\n\tsource?: \"async\" | \"foreground\";\n\ttaskInfo?: string;\n\tresultPreview: string;\n\tdurationMs?: number;\n\tsessionLabel?: string;\n\tsessionValue?: string;\n}\n\ninterface SubagentResult {\n\tid: string | null;\n\tsource?: \"async\" | \"foreground\";\n\tagent: string | null;\n\tsuccess: boolean;\n\tsummary: string;\n\texitCode?: number;\n\tstate?: string;\n\ttimestamp: number;\n\tdurationMs?: number;\n\tcwd?: string;\n\tasyncDir?: string;\n\tsessionFile?: string;\n\tshareUrl?: string;\n\tgistUrl?: string;\n\tshareError?: string;\n\tresults?: ChainStepResult[];\n\ttaskIndex?: number;\n\ttotalTasks?: number;\n\tsessionId?: string | null;\n}\n\ninterface NotifyTimerApi {\n\tsetTimeout(handler: () => void, delayMs: number): unknown;\n\tclearTimeout(handle: unknown): void;\n}\n\nexport interface RegisterSubagentNotifyOptions {\n\tbatchConfig?: CompletionBatchConfig;\n\ttimers?: NotifyTimerApi;\n\tnow?: () => number;\n}\n\nfunction formatSessionLine(details: SubagentNotifyDetails): string | undefined {\n\tif (!details.sessionValue) return undefined;\n\treturn details.sessionLabel ? `${details.sessionLabel}: ${details.sessionValue}` : details.sessionValue;\n}\n\nexport function formatSingleCompletion(details: SubagentNotifyDetails): string {\n\tconst sessionLine = formatSessionLine(details);\n\tconst taskKind = details.source === \"foreground\" ? \"Detached foreground task\" : \"Background task\";\n\treturn [\n\t\t`${taskKind} ${details.status}: **${details.agent}**${details.taskInfo ?? \"\"}`,\n\t\t\"\",\n\t\tdetails.resultPreview.trim() ? details.resultPreview : \"(no output)\",\n\t\tsessionLine ? \"\" : undefined,\n\t\tsessionLine,\n\t]\n\t\t.filter((line) => line !== undefined)\n\t\t.join(\"\\n\");\n}\n\nexport function parseSubagentNotifyContent(content: string): SubagentNotifyDetails | undefined {\n\tconst lines = content.split(\"\\n\");\n\tconst match = (lines[0] ?? \"\").match(/^(Background task|Detached foreground task) (completed|failed|paused|stopped): \\*\\*(.+?)\\*\\*(?:\\s+(\\([^)]*\\)))?$/);\n\tif (!match) return undefined;\n\tconst body = lines.slice(2);\n\tlet sessionIndex = -1;\n\tfor (let i = body.length - 1; i >= 1; i--) {\n\t\tif (body[i - 1]?.trim() === \"\" && /^(Session|Session file|Session share error):\\s+/.test(body[i]!)) {\n\t\t\tsessionIndex = i;\n\t\t\tbreak;\n\t\t}\n\t}\n\tconst sessionLine = sessionIndex >= 0 ? body[sessionIndex] : undefined;\n\tconst resultPreview = (sessionIndex >= 0 ? body.slice(0, sessionIndex) : body).join(\"\\n\").trim() || \"(no output)\";\n\tlet sessionLabel: string | undefined;\n\tlet sessionValue: string | undefined;\n\tif (sessionLine) {\n\t\tconst separator = sessionLine.indexOf(\":\");\n\t\tsessionLabel = sessionLine.slice(0, separator).toLowerCase();\n\t\tsessionValue = sessionLine.slice(separator + 1).trim();\n\t}\n\treturn {\n\t\tagent: match[3]!,\n\t\tstatus: match[2] as SubagentNotifyDetails[\"status\"],\n\t\t...(match[1] === \"Detached foreground task\" ? { source: \"foreground\" as const } : {}),\n\t\t...(match[4] ? { taskInfo: match[4] } : {}),\n\t\tresultPreview,\n\t\t...(sessionLabel && sessionValue ? { sessionLabel, sessionValue } : {}),\n\t};\n}\n\nexport function formatGroupedCompletion(details: SubagentNotifyDetails[]): string {\n\tconst header = `Background tasks completed (${details.length}): ${details.map((d) => `**${d.agent}**${d.taskInfo ?? \"\"}`).join(\", \")}`;\n\tconst blocks: string[] = [header, \"\"];\n\tfor (let index = 0; index < details.length; index++) {\n\t\tconst detail = details[index];\n\t\tif (!detail) continue;\n\t\tconst sessionLine = formatSessionLine(detail);\n\t\tblocks.push(`${index + 1}. ${detail.agent}${detail.taskInfo ?? \"\"}`);\n\t\tblocks.push(detail.resultPreview.trim() ? detail.resultPreview : \"(no output)\");\n\t\tif (sessionLine) blocks.push(sessionLine);\n\t\tblocks.push(\"\");\n\t}\n\treturn blocks.join(\"\\n\").trimEnd();\n}\n\nfunction sendCompletion(pi: Pick<ExtensionAPI, \"sendMessage\">, details: SubagentNotifyDetails[]): void {\n\tif (details.length === 0) return;\n\tconst content = details.length === 1\n\t\t? formatSingleCompletion(details[0]!)\n\t\t: formatGroupedCompletion(details);\n\tpi.sendMessage(\n\t\t{\n\t\t\tcustomType: \"subagent-notify\",\n\t\t\tcontent,\n\t\t\tdisplay: true,\n\t\t},\n\t\t{ triggerTurn: details.some((detail) => detail.status !== \"stopped\") },\n\t);\n}\n\nfunction completionBatchKey(result: SubagentResult): string {\n\tconst sessionId = typeof result.sessionId === \"string\" ? result.sessionId.trim() : \"\";\n\tif (sessionId) return `session:${sessionId}`;\n\tconst cwd = typeof result.cwd === \"string\" ? result.cwd.trim() : \"\";\n\treturn cwd ? `cwd:${cwd}` : \"unknown\";\n}\n\nexport function buildCompletionDetails(result: SubagentResult): SubagentNotifyDetails {\n\tconst agent = result.agent ?? \"unknown\";\n\tconst summary = typeof result.summary === \"string\" ? result.summary : \"\";\n\tconst paused = !result.success && (\n\t\tresult.exitCode === 0\n\t\t|| result.state === \"paused\"\n\t\t|| summary.startsWith(\"Paused after interrupt.\")\n\t);\n\tconst status = result.state === \"stopped\" ? \"stopped\" : paused ? \"paused\" : result.success ? \"completed\" : \"failed\";\n\n\tconst taskInfo =\n\t\tresult.taskIndex !== undefined && result.totalTasks !== undefined\n\t\t\t? ` (${result.taskIndex + 1}/${result.totalTasks})`\n\t\t\t: undefined;\n\n\tconst session =\n\t\tresult.shareUrl\n\t\t\t? { label: \"Session\", value: result.shareUrl }\n\t\t\t: result.shareError\n\t\t\t\t? { label: \"Session share error\", value: result.shareError }\n\t\t\t\t: result.sessionFile\n\t\t\t\t\t? { label: \"Session file\", value: result.sessionFile }\n\t\t\t\t\t: undefined;\n\n\treturn {\n\t\tagent,\n\t\tstatus,\n\t\t...(result.source ? { source: result.source } : {}),\n\t\t...(taskInfo ? { taskInfo } : {}),\n\t\tresultPreview: [\n\t\t\tresult.id ? `Run: ${result.id}` : undefined,\n\t\t\tresult.asyncDir ? `Async dir: ${result.asyncDir}` : undefined,\n\t\t\tresult.results?.length\n\t\t\t\t? result.results.map((child, index) => {\n\t\t\t\t\tconst output = child.summary ?? (child.error ? `${child.error}\\n\\nOutput:\\n${child.output}` : child.output);\n\t\t\t\t\tconst report = child.acceptance?.childReport;\n\t\t\t\t\tconst childIndex = child.index ?? index;\n\t\t\t\t\treturn [\n\t\t\t\t\t\t`${childIndex + 1}. ${child.agent} [${child.status ?? resolveSubagentResultStatus({ success: child.success, state: result.state })}]`,\n\t\t\t\t\t\tchild.artifactPath ? `Output artifact: ${child.artifactPath}` : undefined,\n\t\t\t\t\t\tchild.sessionPath ? `Session: ${child.sessionPath}` : undefined,\n\t\t\t\t\t\tchild.sessionPath && result.id && result.source !== \"foreground\"\n\t\t\t\t\t\t\t? `Revive: subagent({ action: \"resume\", id: ${JSON.stringify(result.id)}, index: ${childIndex}, message: \"...\" })`\n\t\t\t\t\t\t\t: undefined,\n\t\t\t\t\t\t...formatNestedResultLines(child.children),\n\t\t\t\t\t\toutput,\n\t\t\t\t\t\treport ? `\\`\\`\\`acceptance-report\\n${JSON.stringify(report, null, 2)}\\n\\`\\`\\`` : undefined,\n\t\t\t\t\t].filter((line) => line !== undefined).join(\"\\n\");\n\t\t\t\t}).join(\"\\n\\n\")\n\t\t\t\t: summary,\n\t\t].filter((line) => line !== undefined).join(\"\\n\\n\"),\n\t\t...(typeof result.durationMs === \"number\" ? { durationMs: result.durationMs } : {}),\n\t\t...(session ? { sessionLabel: session.label, sessionValue: session.value } : {}),\n\t};\n}\n\nexport default function registerSubagentNotify(\n\tpi: ExtensionAPI,\n\tstate: Pick<SubagentState, \"currentSessionId\">,\n\toptions: RegisterSubagentNotifyOptions = {},\n): void {\n\tconst unsubscribeStoreKey = \"__pi_subagents_notify_unsubscribe__\";\n\tconst batcherStoreKey = \"__pi_subagents_notify_batcher__\";\n\tconst globalStore = globalThis as Record<string, unknown>;\n\tconst previousUnsubscribe = globalStore[unsubscribeStoreKey];\n\tif (typeof previousUnsubscribe === \"function\") {\n\t\ttry {\n\t\t\tpreviousUnsubscribe();\n\t\t} catch {\n\t\t\t// Best effort cleanup for stale handlers from an older reload.\n\t\t}\n\t}\n\tconst previousBatcher = globalStore[batcherStoreKey];\n\tif (previousBatcher && typeof (previousBatcher as { dispose?: () => void }).dispose === \"function\") {\n\t\ttry {\n\t\t\t(previousBatcher as { dispose: () => void }).dispose();\n\t\t} catch {\n\t\t\t// Best effort cleanup for a stale batcher from an older reload.\n\t\t}\n\t}\n\n\tconst seen = getGlobalSeenMap(\"__pi_subagents_notify_seen__\");\n\tconst ttlMs = 10 * 60 * 1000;\n\tconst nowFn = options.now ?? Date.now;\n\tconst batchConfig = resolveCompletionBatchConfig(options.batchConfig);\n\tconst batchers = new Map<string, CompletionBatcher<SubagentNotifyDetails>>();\n\tglobalStore[batcherStoreKey] = {\n\t\tdispose() {\n\t\t\tfor (const batcher of batchers.values()) batcher.dispose();\n\t\t\tbatchers.clear();\n\t\t},\n\t};\n\n\tconst handleComplete = (data: unknown) => {\n\t\tconst result = data as SubagentResult;\n\t\tif (typeof result.sessionId !== \"string\" || result.sessionId !== state.currentSessionId) return;\n\t\tconst now = nowFn();\n\t\tconst key = buildCompletionKey(result, \"notify\");\n\t\tif (markSeenWithTtl(seen, key, now, ttlMs)) return;\n\n\t\tconst details = buildCompletionDetails(result);\n\t\tif (result.source === \"foreground\") {\n\t\t\tsendCompletion(pi, [details]);\n\t\t\treturn;\n\t\t}\n\t\tconst batchKey = completionBatchKey(result);\n\t\tlet batcher = batchers.get(batchKey);\n\t\tif (!batcher) {\n\t\t\tbatcher = createCompletionBatcher<SubagentNotifyDetails>({\n\t\t\t\tconfig: batchConfig,\n\t\t\t\temit: (items) => sendCompletion(pi, items),\n\t\t\t\t...(options.timers ? { timers: options.timers } : {}),\n\t\t\t\tnow: nowFn,\n\t\t\t});\n\t\t\tbatchers.set(batchKey, batcher);\n\t\t}\n\t\tif (details.status !== \"completed\") {\n\t\t\t// Failures and paused runs bypass grouping. Flush any held\n\t\t\t// successes for the same owner first so they are not stranded\n\t\t\t// behind this signal, then emit the non-completion result immediately.\n\t\t\tbatcher.flush();\n\t\t\tsendCompletion(pi, [details]);\n\t\t\treturn;\n\t\t}\n\t\tbatcher.push(details);\n\t};\n\n\tconst unsubscribers = [\n\t\tpi.events.on(SUBAGENT_ASYNC_COMPLETE_EVENT, handleComplete),\n\t\tpi.events.on(SUBAGENT_FOREGROUND_COMPLETE_EVENT, handleComplete),\n\t].filter((unsubscribe): unsubscribe is () => void => typeof unsubscribe === \"function\");\n\tglobalStore[unsubscribeStoreKey] = () => {\n\t\tfor (const unsubscribe of unsubscribers) unsubscribe();\n\t};\n}\n"]}
@@ -13,6 +13,7 @@ type ResultWatcherDeps = {
13
13
  };
14
14
  export declare function createResultWatcher(pi: {
15
15
  events: IntercomEventBus;
16
+ appendEntry?: (type: string, data: unknown) => void;
16
17
  }, state: SubagentState, resultsDir: string, completionTtlMs: number, deps?: ResultWatcherDeps): {
17
18
  startResultWatcher: () => void;
18
19
  primeExistingResults: () => void;
@@ -1 +1 @@
1
- {"version":3,"file":"result-watcher.d.ts","sourceRoot":"","sources":["../../../../../../src/builtin-extensions/pi-subagents/src/runs/background/result-watcher.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,MAAM,SAAS,CAAC;AAI9B,OAAO,EAEN,KAAK,gBAAgB,EAGrB,KAAK,aAAa,EAClB,MAAM,uBAAuB,CAAC;AAc/B,KAAK,eAAe,GAAG,IAAI,CAAC,OAAO,EAAE,EAAE,YAAY,GAAG,cAAc,GAAG,YAAY,GAAG,aAAa,GAAG,WAAW,GAAG,cAAc,GAAG,OAAO,CAAC,CAAC;AAE9I,KAAK,mBAAmB,GAAG;IAC1B,UAAU,EAAE,OAAO,UAAU,CAAC;IAC9B,YAAY,EAAE,OAAO,YAAY,CAAC;IAClC,WAAW,EAAE,OAAO,WAAW,CAAC;IAChC,aAAa,EAAE,OAAO,aAAa,CAAC;CACpC,CAAC;AAEF,KAAK,iBAAiB,GAAG;IACxB,EAAE,CAAC,EAAE,eAAe,CAAC;IACrB,MAAM,CAAC,EAAE,mBAAmB,CAAC;CAC7B,CAAC;AA6DF,wBAAgB,mBAAmB,CAClC,EAAE,EAAE;IAAE,MAAM,EAAE,gBAAgB,CAAA;CAAE,EAChC,KAAK,EAAE,aAAa,EACpB,UAAU,EAAE,MAAM,EAClB,eAAe,EAAE,MAAM,EACvB,IAAI,GAAE,iBAAsB,GAC1B;IACF,kBAAkB,EAAE,MAAM,IAAI,CAAC;IAC/B,oBAAoB,EAAE,MAAM,IAAI,CAAC;IACjC,iBAAiB,EAAE,MAAM,IAAI,CAAC;CAC9B,CAkNA","sourcesContent":["// @ts-nocheck\nimport * as fs from \"node:fs\";\nimport * as path from \"node:path\";\nimport { buildCompletionKey, markSeenWithTtl } from \"./completion-dedupe.ts\";\nimport { createFileCoalescer } from \"../../shared/file-coalescer.ts\";\nimport {\n\tSUBAGENT_ASYNC_COMPLETE_EVENT,\n\ttype IntercomEventBus,\n\ttype NestedRunSummary,\n\ttype SubagentResultIntercomChild,\n\ttype SubagentState,\n} from \"../../shared/types.ts\";\nimport {\n\tattachNestedChildrenToResultChildren,\n\tbuildSubagentResultIntercomPayload,\n\tcompactNestedResultChildren,\n\tdeliverSubagentResultIntercomEvent,\n\tresolveSubagentResultStatus,\n} from \"../../intercom/result-intercom.ts\";\nimport { projectNestedRegistryForRoot, sanitizeSummary } from \"../shared/nested-events.ts\";\nimport { resolveWatchPath } from \"../../shared/utils.ts\";\n\nconst WATCHER_RESTART_DELAY_MS = 3000;\nconst POLL_INTERVAL_MS = 3000;\n\ntype ResultWatcherFs = Pick<typeof fs, \"existsSync\" | \"readFileSync\" | \"unlinkSync\" | \"readdirSync\" | \"mkdirSync\" | \"realpathSync\" | \"watch\">;\n\ntype ResultWatcherTimers = {\n\tsetTimeout: typeof setTimeout;\n\tclearTimeout: typeof clearTimeout;\n\tsetInterval: typeof setInterval;\n\tclearInterval: typeof clearInterval;\n};\n\ntype ResultWatcherDeps = {\n\tfs?: ResultWatcherFs;\n\ttimers?: ResultWatcherTimers;\n};\n\ntype ResultFileChild = {\n\tagent?: string;\n\toutput?: string;\n\terror?: string;\n\tsuccess?: boolean;\n\tstate?: string;\n\tstopped?: boolean;\n\tsessionFile?: string;\n\tartifactPaths?: { outputPath?: string };\n\tintercomTarget?: string;\n\tchildren?: unknown;\n};\n\ntype ResultFileData = {\n\tid?: string;\n\trunId?: string;\n\tagent?: string;\n\tsuccess?: boolean;\n\tstate?: string;\n\tmode?: string;\n\tsummary?: string;\n\tresults?: ResultFileChild[];\n\tnestedChildren?: unknown;\n\tsessionId?: string;\n\tcwd?: string;\n\tsessionFile?: string;\n\tasyncDir?: string;\n\tintercomTarget?: string;\n};\n\nfunction sanitizeNestedResultChildren(value: unknown, resultPath: string, label: string): NestedRunSummary[] | undefined {\n\tif (value === undefined) return undefined;\n\tif (!Array.isArray(value)) {\n\t\tconsole.error(`Ignoring invalid nested children in subagent result file '${resultPath}' at ${label}: expected an array.`);\n\t\treturn undefined;\n\t}\n\tconst children = value.map((child) => sanitizeSummary(child)).filter((child): child is NestedRunSummary => Boolean(child));\n\tif (children.length !== value.length) {\n\t\tconsole.error(`Ignoring ${value.length - children.length} invalid nested child record(s) in subagent result file '${resultPath}' at ${label}.`);\n\t}\n\treturn children.length ? children : undefined;\n}\n\nfunction getErrorCode(error: unknown): string | undefined {\n\treturn typeof error === \"object\" && error !== null && \"code\" in error\n\t\t? (error as NodeJS.ErrnoException).code\n\t\t: undefined;\n}\n\nfunction isNotFoundError(error: unknown): boolean {\n\treturn getErrorCode(error) === \"ENOENT\";\n}\n\nfunction shouldFallBackToPolling(error: unknown): boolean {\n\tconst code = getErrorCode(error);\n\treturn code === \"EMFILE\" || code === \"ENOSPC\";\n}\n\n\nexport function createResultWatcher(\n\tpi: { events: IntercomEventBus },\n\tstate: SubagentState,\n\tresultsDir: string,\n\tcompletionTtlMs: number,\n\tdeps: ResultWatcherDeps = {},\n): {\n\tstartResultWatcher: () => void;\n\tprimeExistingResults: () => void;\n\tstopResultWatcher: () => void;\n} {\n\tconst fsApi = deps.fs ?? fs;\n\tconst timers = deps.timers ?? { setTimeout, clearTimeout, setInterval, clearInterval };\n\n\tconst handleResult = async (file: string) => {\n\t\tconst resultPath = path.join(resultsDir, file);\n\t\tif (!fsApi.existsSync(resultPath)) return;\n\t\ttry {\n\t\t\tconst data = JSON.parse(fsApi.readFileSync(resultPath, \"utf-8\")) as ResultFileData;\n\t\t\tif (typeof data.sessionId !== \"string\" || data.sessionId !== state.currentSessionId) return;\n\n\t\t\tconst runId = data.runId ?? data.id ?? file.replace(/\\.json$/i, \"\");\n\t\t\tconst hasExplicitNestedChildren = data.nestedChildren !== undefined;\n\t\t\tlet nestedChildren = compactNestedResultChildren(sanitizeNestedResultChildren(data.nestedChildren, resultPath, \"nestedChildren\"));\n\t\t\tif (!nestedChildren?.length && !hasExplicitNestedChildren) {\n\t\t\t\ttry {\n\t\t\t\t\tnestedChildren = compactNestedResultChildren(projectNestedRegistryForRoot(runId)?.children);\n\t\t\t\t} catch (error) {\n\t\t\t\t\tconsole.error(`Failed to enrich subagent result file '${resultPath}' with nested registry children; will retry later:`, error);\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t}\n\t\t\tconst now = Date.now();\n\t\t\tconst completionKey = buildCompletionKey(data, `result:${file}`);\n\t\t\tif (markSeenWithTtl(state.completionSeen, completionKey, now, completionTtlMs)) {\n\t\t\t\tfsApi.unlinkSync(resultPath);\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\tconst hasResultChildren = Array.isArray(data.results) && data.results.length > 0;\n\t\t\tconst resultChildren = hasResultChildren\n\t\t\t\t? data.results!\n\t\t\t\t: [{\n\t\t\t\t\tagent: data.agent,\n\t\t\t\t\toutput: data.summary,\n\t\t\t\t\tsuccess: data.success,\n\t\t\t\t}];\n\t\t\tconst normalizedChildren = attachNestedChildrenToResultChildren(runId, resultChildren.map((result = {}, index): SubagentResultIntercomChild => {\n\t\t\t\tconst baseOutput = result.output ?? data.summary;\n\t\t\t\tconst hasRealOutput = typeof baseOutput === \"string\" && baseOutput.trim().length > 0;\n\t\t\t\tconst output = hasRealOutput ? baseOutput : \"(no output)\";\n\t\t\t\tconst summary = result.success === false && result.error\n\t\t\t\t\t? `${result.error}${hasRealOutput ? `\\n\\nOutput:\\n${baseOutput}` : \"\"}`\n\t\t\t\t\t: output;\n\t\t\t\tconst sessionPath = result.sessionFile ?? (resultChildren.length === 1 ? data.sessionFile : undefined);\n\t\t\t\tconst childNestedChildren = sanitizeNestedResultChildren(result.children, resultPath, `results[${index}].children`);\n\t\t\t\tconst childState = result.state === \"paused\" || result.state === \"stopped\"\n\t\t\t\t\t? result.state\n\t\t\t\t\t: result.stopped === true\n\t\t\t\t\t\t? \"stopped\"\n\t\t\t\t\t\t: data.state === \"paused\" || (!hasResultChildren && (data.state === \"stopped\" || typeof result.success !== \"boolean\"))\n\t\t\t\t\t\t\t? data.state\n\t\t\t\t\t\t\t: undefined;\n\t\t\t\treturn {\n\t\t\t\t\tagent: result.agent ?? data.agent ?? `step-${index + 1}`,\n\t\t\t\t\tstatus: resolveSubagentResultStatus({\n\t\t\t\t\t\tsuccess: result.success,\n\t\t\t\t\t\tstate: childState,\n\t\t\t\t\t}),\n\t\t\t\t\tsummary,\n\t\t\t\t\tindex,\n\t\t\t\t\tartifactPath: result.artifactPaths?.outputPath,\n\t\t\t\t\t...(typeof sessionPath === \"string\" && fsApi.existsSync(sessionPath) ? { sessionPath } : {}),\n\t\t\t\t\t...(result.intercomTarget ? { intercomTarget: result.intercomTarget } : {}),\n\t\t\t\t\t...(childNestedChildren ? { children: childNestedChildren } : {}),\n\t\t\t\t};\n\t\t\t}), nestedChildren);\n\n\t\t\tconst intercomTarget = data.intercomTarget?.trim();\n\t\t\tif (intercomTarget) {\n\t\t\t\tconst mode = data.mode === \"single\" || data.mode === \"parallel\" || data.mode === \"chain\"\n\t\t\t\t\t? data.mode\n\t\t\t\t\t: resultChildren.length > 1 ? \"chain\" : \"single\";\n\t\t\t\tconst payload = buildSubagentResultIntercomPayload({\n\t\t\t\t\tto: intercomTarget,\n\t\t\t\t\trunId,\n\t\t\t\t\tmode,\n\t\t\t\t\tsource: \"async\",\n\t\t\t\t\tchildren: normalizedChildren,\n\t\t\t\t\tasyncId: data.id,\n\t\t\t\t\tasyncDir: data.asyncDir,\n\t\t\t\t});\n\t\t\t\tconst delivered = await deliverSubagentResultIntercomEvent(pi.events, payload);\n\t\t\t\tif (!delivered) {\n\t\t\t\t\tconsole.error(`Subagent async grouped result intercom delivery was not acknowledged for '${resultPath}'.`);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tpi.events.emit(SUBAGENT_ASYNC_COMPLETE_EVENT, {\n\t\t\t\t...data,\n\t\t\t\trunId,\n\t\t\t\t...(nestedChildren?.length ? { nestedChildren } : {}),\n\t\t\t\t...(Array.isArray(data.results) ? {\n\t\t\t\t\tresults: hasResultChildren\n\t\t\t\t\t\t? normalizedChildren.map((child, index) => ({\n\t\t\t\t\t\t\t...data.results![index],\n\t\t\t\t\t\t\tagent: child.agent,\n\t\t\t\t\t\t\tstatus: child.status,\n\t\t\t\t\t\t\tsummary: child.summary,\n\t\t\t\t\t\t\tindex: child.index,\n\t\t\t\t\t\t\tartifactPath: child.artifactPath,\n\t\t\t\t\t\t\tsessionPath: child.sessionPath,\n\t\t\t\t\t\t\tchildren: child.children,\n\t\t\t\t\t\t}))\n\t\t\t\t\t\t: [],\n\t\t\t\t} : {}),\n\t\t\t});\n\t\t\tfsApi.unlinkSync(resultPath);\n\t\t} catch (error) {\n\t\t\tif (isNotFoundError(error)) return;\n\t\t\tconsole.error(`Failed to process subagent result file '${resultPath}':`, error);\n\t\t}\n\t};\n\n\tstate.resultFileCoalescer = createFileCoalescer((file) => {\n\t\tvoid handleResult(file);\n\t}, 50);\n\n\tconst primeExistingResults = () => {\n\t\ttry {\n\t\t\tfsApi.readdirSync(resultsDir)\n\t\t\t\t.filter((f) => f.endsWith(\".json\"))\n\t\t\t\t.forEach((file) => state.resultFileCoalescer.schedule(file, 0));\n\t\t} catch (error) {\n\t\t\tif (isNotFoundError(error)) return;\n\t\t\tconsole.error(`Failed to scan subagent result directory '${resultsDir}':`, error);\n\t\t}\n\t};\n\n\tconst startPollingFallback = (reason: unknown) => {\n\t\tstate.watcher?.close();\n\t\tstate.watcher = null;\n\t\tif (state.watcherRestartTimer) return;\n\n\t\tconsole.error(\n\t\t\t`Subagent result watcher for '${resultsDir}' fell back to polling because native fs.watch is unavailable (${getErrorCode(reason) ?? \"unknown error\"}).`,\n\t\t);\n\t\tprimeExistingResults();\n\t\tstate.watcherRestartTimer = timers.setInterval(primeExistingResults, POLL_INTERVAL_MS);\n\t\tstate.watcherRestartTimer.unref?.();\n\t};\n\n\tconst scheduleRestart = () => {\n\t\tif (state.watcherRestartTimer) return;\n\t\tstate.watcherRestartTimer = timers.setTimeout(() => {\n\t\t\tstate.watcherRestartTimer = null;\n\t\t\ttry {\n\t\t\t\tfsApi.mkdirSync(resultsDir, { recursive: true });\n\t\t\t\tstartResultWatcher();\n\t\t\t} catch (error) {\n\t\t\t\tif (shouldFallBackToPolling(error)) {\n\t\t\t\t\tstartPollingFallback(error);\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\tconsole.error(`Failed to restart subagent result watcher for '${resultsDir}':`, error);\n\t\t\t\tscheduleRestart();\n\t\t\t}\n\t\t}, WATCHER_RESTART_DELAY_MS);\n\t\tstate.watcherRestartTimer.unref?.();\n\t};\n\n\tconst startResultWatcher = () => {\n\t\tif (state.watcher) return;\n\t\tif (state.watcherRestartTimer) {\n\t\t\ttimers.clearTimeout(state.watcherRestartTimer);\n\t\t\ttimers.clearInterval(state.watcherRestartTimer);\n\t\t\tstate.watcherRestartTimer = null;\n\t\t}\n\t\ttry {\n\t\t\tconst watchDir = resolveWatchPath(resultsDir, fsApi.realpathSync.native);\n\t\t\tstate.watcher = fsApi.watch(watchDir, (ev, file) => {\n\t\t\t\tif (ev !== \"rename\" || !file) return;\n\t\t\t\tconst fileName = file.toString();\n\t\t\t\tif (!fileName.endsWith(\".json\")) return;\n\t\t\t\tstate.resultFileCoalescer.schedule(fileName);\n\t\t\t});\n\t\t\tstate.watcher.on(\"error\", (error) => {\n\t\t\t\tif (shouldFallBackToPolling(error)) {\n\t\t\t\t\tstartPollingFallback(error);\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\tconsole.error(`Subagent result watcher failed for '${resultsDir}':`, error);\n\t\t\t\tstate.watcher?.close();\n\t\t\t\tstate.watcher = null;\n\t\t\t\tscheduleRestart();\n\t\t\t});\n\t\t\tstate.watcher.unref?.();\n\t\t} catch (error) {\n\t\t\tif (shouldFallBackToPolling(error)) {\n\t\t\t\tstartPollingFallback(error);\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tconsole.error(`Failed to start subagent result watcher for '${resultsDir}':`, error);\n\t\t\tstate.watcher = null;\n\t\t\tscheduleRestart();\n\t\t}\n\t};\n\n\tconst stopResultWatcher = () => {\n\t\tstate.watcher?.close();\n\t\tstate.watcher = null;\n\t\tif (state.watcherRestartTimer) {\n\t\t\ttimers.clearTimeout(state.watcherRestartTimer);\n\t\t\ttimers.clearInterval(state.watcherRestartTimer);\n\t\t}\n\t\tstate.watcherRestartTimer = null;\n\t\tstate.resultFileCoalescer.clear();\n\t};\n\n\treturn { startResultWatcher, primeExistingResults, stopResultWatcher };\n}\n"]}
1
+ {"version":3,"file":"result-watcher.d.ts","sourceRoot":"","sources":["../../../../../../src/builtin-extensions/pi-subagents/src/runs/background/result-watcher.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,MAAM,SAAS,CAAC;AAI9B,OAAO,EAEN,KAAK,gBAAgB,EAGrB,KAAK,aAAa,EAClB,MAAM,uBAAuB,CAAC;AAc/B,KAAK,eAAe,GAAG,IAAI,CAAC,OAAO,EAAE,EAAE,YAAY,GAAG,cAAc,GAAG,YAAY,GAAG,aAAa,GAAG,WAAW,GAAG,cAAc,GAAG,OAAO,CAAC,CAAC;AAE9I,KAAK,mBAAmB,GAAG;IAC1B,UAAU,EAAE,OAAO,UAAU,CAAC;IAC9B,YAAY,EAAE,OAAO,YAAY,CAAC;IAClC,WAAW,EAAE,OAAO,WAAW,CAAC;IAChC,aAAa,EAAE,OAAO,aAAa,CAAC;CACpC,CAAC;AAEF,KAAK,iBAAiB,GAAG;IACxB,EAAE,CAAC,EAAE,eAAe,CAAC;IACrB,MAAM,CAAC,EAAE,mBAAmB,CAAC;CAC7B,CAAC;AA6DF,wBAAgB,mBAAmB,CAClC,EAAE,EAAE;IAAE,MAAM,EAAE,gBAAgB,CAAC;IAAC,WAAW,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,OAAO,KAAK,IAAI,CAAA;CAAE,EACrF,KAAK,EAAE,aAAa,EACpB,UAAU,EAAE,MAAM,EAClB,eAAe,EAAE,MAAM,EACvB,IAAI,GAAE,iBAAsB,GAC1B;IACF,kBAAkB,EAAE,MAAM,IAAI,CAAC;IAC/B,oBAAoB,EAAE,MAAM,IAAI,CAAC;IACjC,iBAAiB,EAAE,MAAM,IAAI,CAAC;CAC9B,CA6NA","sourcesContent":["// @ts-nocheck\nimport * as fs from \"node:fs\";\nimport * as path from \"node:path\";\nimport { buildCompletionKey, markSeenWithTtl } from \"./completion-dedupe.ts\";\nimport { createFileCoalescer } from \"../../shared/file-coalescer.ts\";\nimport {\n\tSUBAGENT_ASYNC_COMPLETE_EVENT,\n\ttype IntercomEventBus,\n\ttype NestedRunSummary,\n\ttype SubagentResultIntercomChild,\n\ttype SubagentState,\n} from \"../../shared/types.ts\";\nimport {\n\tattachNestedChildrenToResultChildren,\n\tbuildSubagentResultIntercomPayload,\n\tcompactNestedResultChildren,\n\tdeliverSubagentResultIntercomEvent,\n\tresolveSubagentResultStatus,\n} from \"../../intercom/result-intercom.ts\";\nimport { projectNestedRegistryForRoot, sanitizeSummary } from \"../shared/nested-events.ts\";\nimport { resolveWatchPath } from \"../../shared/utils.ts\";\n\nconst WATCHER_RESTART_DELAY_MS = 3000;\nconst POLL_INTERVAL_MS = 3000;\n\ntype ResultWatcherFs = Pick<typeof fs, \"existsSync\" | \"readFileSync\" | \"unlinkSync\" | \"readdirSync\" | \"mkdirSync\" | \"realpathSync\" | \"watch\">;\n\ntype ResultWatcherTimers = {\n\tsetTimeout: typeof setTimeout;\n\tclearTimeout: typeof clearTimeout;\n\tsetInterval: typeof setInterval;\n\tclearInterval: typeof clearInterval;\n};\n\ntype ResultWatcherDeps = {\n\tfs?: ResultWatcherFs;\n\ttimers?: ResultWatcherTimers;\n};\n\ntype ResultFileChild = {\n\tagent?: string;\n\toutput?: string;\n\terror?: string;\n\tsuccess?: boolean;\n\tstate?: string;\n\tstopped?: boolean;\n\tsessionFile?: string;\n\tartifactPaths?: { outputPath?: string };\n\tintercomTarget?: string;\n\tchildren?: unknown;\n};\n\ntype ResultFileData = {\n\tid?: string;\n\trunId?: string;\n\tagent?: string;\n\tsuccess?: boolean;\n\tstate?: string;\n\tmode?: string;\n\tsummary?: string;\n\tresults?: ResultFileChild[];\n\tnestedChildren?: unknown;\n\tsessionId?: string;\n\tcwd?: string;\n\tsessionFile?: string;\n\tasyncDir?: string;\n\tintercomTarget?: string;\n};\n\nfunction sanitizeNestedResultChildren(value: unknown, resultPath: string, label: string, report: (message: string) => void): NestedRunSummary[] | undefined {\n\tif (value === undefined) return undefined;\n\tif (!Array.isArray(value)) {\n\t\treport(`Ignoring invalid nested children in subagent result file '${resultPath}' at ${label}: expected an array.`);\n\t\treturn undefined;\n\t}\n\tconst children = value.map((child) => sanitizeSummary(child)).filter((child): child is NestedRunSummary => Boolean(child));\n\tif (children.length !== value.length) {\n\t\treport(`Ignoring ${value.length - children.length} invalid nested child record(s) in subagent result file '${resultPath}' at ${label}.`);\n\t}\n\treturn children.length ? children : undefined;\n}\n\nfunction getErrorCode(error: unknown): string | undefined {\n\treturn typeof error === \"object\" && error !== null && \"code\" in error\n\t\t? (error as NodeJS.ErrnoException).code\n\t\t: undefined;\n}\n\nfunction isNotFoundError(error: unknown): boolean {\n\treturn getErrorCode(error) === \"ENOENT\";\n}\n\nfunction shouldFallBackToPolling(error: unknown): boolean {\n\tconst code = getErrorCode(error);\n\treturn code === \"EMFILE\" || code === \"ENOSPC\";\n}\n\n\nexport function createResultWatcher(\n\tpi: { events: IntercomEventBus; appendEntry?: (type: string, data: unknown) => void },\n\tstate: SubagentState,\n\tresultsDir: string,\n\tcompletionTtlMs: number,\n\tdeps: ResultWatcherDeps = {},\n): {\n\tstartResultWatcher: () => void;\n\tprimeExistingResults: () => void;\n\tstopResultWatcher: () => void;\n} {\n\tconst fsApi = deps.fs ?? fs;\n\tconst timers = deps.timers ?? { setTimeout, clearTimeout, setInterval, clearInterval };\n\n\tlet generation = 0;\n\tconst inFlight = new Set<string>();\n\tconst attempts = new Map<string, number>();\n\tconst report = (message: string, error?: unknown) => {\n\t\tpi.appendEntry?.(\"subagent_result_delivery\", { message, error: error instanceof Error ? error.message : error });\n\t};\n\n\tconst handleResult = async (file: string) => {\n\t\tif (inFlight.has(file) || (attempts.get(file) ?? 0) >= 3) return;\n\t\tconst currentGeneration = generation;\n\t\tconst sessionId = state.currentSessionId;\n\t\tconst isCurrent = () => generation === currentGeneration && state.currentSessionId === sessionId;\n\t\tconst resultPath = path.join(resultsDir, file);\n\t\tif (!fsApi.existsSync(resultPath)) return;\n\t\tinFlight.add(file);\n\t\ttry {\n\t\t\tconst data = JSON.parse(fsApi.readFileSync(resultPath, \"utf-8\")) as ResultFileData;\n\t\t\tif (typeof data.sessionId !== \"string\" || data.sessionId !== state.currentSessionId) return;\n\n\t\t\tconst runId = data.runId ?? data.id ?? file.replace(/\\.json$/i, \"\");\n\t\t\tconst hasExplicitNestedChildren = data.nestedChildren !== undefined;\n\t\t\tlet nestedChildren = compactNestedResultChildren(sanitizeNestedResultChildren(data.nestedChildren, resultPath, \"nestedChildren\", report));\n\t\t\tif (!nestedChildren?.length && !hasExplicitNestedChildren) {\n\t\t\t\ttry {\n\t\t\t\t\tnestedChildren = compactNestedResultChildren(projectNestedRegistryForRoot(runId)?.children);\n\t\t\t\t} catch (error) {\n\t\t\t\t\treport(`Failed to enrich subagent result file '${resultPath}' with nested registry children; will retry later:`, error);\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t}\n\t\t\tconst now = Date.now();\n\t\t\tconst completionKey = buildCompletionKey(data, `result:${file}`);\n\n\t\t\tconst hasResultChildren = Array.isArray(data.results) && data.results.length > 0;\n\t\t\tconst resultChildren = hasResultChildren\n\t\t\t\t? data.results!\n\t\t\t\t: [{\n\t\t\t\t\tagent: data.agent,\n\t\t\t\t\toutput: data.summary,\n\t\t\t\t\tsuccess: data.success,\n\t\t\t\t}];\n\t\t\tconst normalizedChildren = attachNestedChildrenToResultChildren(runId, resultChildren.map((result = {}, index): SubagentResultIntercomChild => {\n\t\t\t\tconst baseOutput = result.output ?? data.summary;\n\t\t\t\tconst hasRealOutput = typeof baseOutput === \"string\" && baseOutput.trim().length > 0;\n\t\t\t\tconst output = hasRealOutput ? baseOutput : \"(no output)\";\n\t\t\t\tconst summary = result.success === false && result.error\n\t\t\t\t\t? `${result.error}${hasRealOutput ? `\\n\\nOutput:\\n${baseOutput}` : \"\"}`\n\t\t\t\t\t: output;\n\t\t\t\tconst sessionPath = result.sessionFile ?? (resultChildren.length === 1 ? data.sessionFile : undefined);\n\t\t\t\tconst childNestedChildren = sanitizeNestedResultChildren(result.children, resultPath, `results[${index}].children`, report);\n\t\t\t\tconst childState = result.state === \"paused\" || result.state === \"stopped\"\n\t\t\t\t\t? result.state\n\t\t\t\t\t: result.stopped === true\n\t\t\t\t\t\t? \"stopped\"\n\t\t\t\t\t\t: data.state === \"paused\" || (!hasResultChildren && (data.state === \"stopped\" || typeof result.success !== \"boolean\"))\n\t\t\t\t\t\t\t? data.state\n\t\t\t\t\t\t\t: undefined;\n\t\t\t\treturn {\n\t\t\t\t\tagent: result.agent ?? data.agent ?? `step-${index + 1}`,\n\t\t\t\t\tstatus: resolveSubagentResultStatus({\n\t\t\t\t\t\tsuccess: result.success,\n\t\t\t\t\t\tstate: childState,\n\t\t\t\t\t}),\n\t\t\t\t\tsummary,\n\t\t\t\t\tindex,\n\t\t\t\t\tartifactPath: result.artifactPaths?.outputPath,\n\t\t\t\t\t...(typeof sessionPath === \"string\" && fsApi.existsSync(sessionPath) ? { sessionPath } : {}),\n\t\t\t\t\t...(result.intercomTarget ? { intercomTarget: result.intercomTarget } : {}),\n\t\t\t\t\t...(childNestedChildren ? { children: childNestedChildren } : {}),\n\t\t\t\t};\n\t\t\t}), nestedChildren);\n\n\t\t\tif (!markSeenWithTtl(state.completionSeen, completionKey, now, completionTtlMs)) {\n\t\t\t\tpi.events.emit(SUBAGENT_ASYNC_COMPLETE_EVENT, {\n\t\t\t\t\t...data,\n\t\t\t\t\trunId,\n\t\t\t\t\t...(nestedChildren?.length ? { nestedChildren } : {}),\n\t\t\t\t\t...(Array.isArray(data.results) ? { results: hasResultChildren ? normalizedChildren.map((child, index) => ({\n\t\t\t\t\t\t...data.results![index], agent: child.agent, status: child.status, summary: child.summary,\n\t\t\t\t\t\tindex: child.index, artifactPath: child.artifactPath, sessionPath: child.sessionPath, children: child.children,\n\t\t\t\t\t})) : [] } : {}),\n\t\t\t\t});\n\t\t\t}\n\t\t\tif (!isCurrent()) return;\n\t\t\tconst intercomTarget = data.state === \"stopped\" ? undefined : data.intercomTarget?.trim();\n\t\t\tif (intercomTarget) {\n\t\t\t\tconst mode = data.mode === \"single\" || data.mode === \"parallel\" || data.mode === \"chain\"\n\t\t\t\t\t? data.mode\n\t\t\t\t\t: resultChildren.length > 1 ? \"chain\" : \"single\";\n\t\t\t\tconst payload = buildSubagentResultIntercomPayload({\n\t\t\t\t\tto: intercomTarget,\n\t\t\t\t\trunId,\n\t\t\t\t\tmode,\n\t\t\t\t\tsource: \"async\",\n\t\t\t\t\tchildren: normalizedChildren,\n\t\t\t\t\tasyncId: data.id,\n\t\t\t\t\tasyncDir: data.asyncDir,\n\t\t\t\t});\n\t\t\t\tpayload.requestId = `async-result:${sessionId}:${completionKey}`;\n\t\t\t\tpayload.ownerNotificationSessionId = sessionId;\n\t\t\t\tattempts.set(file, (attempts.get(file) ?? 0) + 1);\n\t\t\t\tconst delivered = await deliverSubagentResultIntercomEvent(pi.events, payload);\n\t\t\t\tif (!isCurrent()) return;\n\t\t\t\tif (!delivered) {\n\t\t\t\t\treport(`Async result delivery pending for '${runId}'; output retained.`, resultPath);\n\t\t\t\t\tif (attempts.get(file)! < 3) state.resultFileCoalescer.schedule(file, 1000);\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif (isCurrent()) fsApi.unlinkSync(resultPath);\n\t\t} catch (error) {\n\t\t\tif (isNotFoundError(error)) return;\n\t\t\treport(`Failed to process subagent result file '${resultPath}'.`, error);\n\t\t} finally {\n\t\t\tinFlight.delete(file);\n\t\t}\n\t};\n\n\tstate.resultFileCoalescer = createFileCoalescer((file) => {\n\t\tvoid handleResult(file);\n\t}, 50);\n\n\tconst primeExistingResults = () => {\n\t\ttry {\n\t\t\tfsApi.readdirSync(resultsDir)\n\t\t\t\t.filter((f) => f.endsWith(\".json\"))\n\t\t\t\t.forEach((file) => state.resultFileCoalescer.schedule(file, 0));\n\t\t} catch (error) {\n\t\t\tif (isNotFoundError(error)) return;\n\t\t\treport(`Failed to scan subagent result directory '${resultsDir}':`, error);\n\t\t}\n\t};\n\n\tconst startPollingFallback = (reason: unknown) => {\n\t\tstate.watcher?.close();\n\t\tstate.watcher = null;\n\t\tif (state.watcherRestartTimer) return;\n\n\t\treport(\n\t\t\t`Subagent result watcher for '${resultsDir}' fell back to polling because native fs.watch is unavailable (${getErrorCode(reason) ?? \"unknown error\"}).`,\n\t\t);\n\t\tprimeExistingResults();\n\t\tstate.watcherRestartTimer = timers.setInterval(primeExistingResults, POLL_INTERVAL_MS);\n\t\tstate.watcherRestartTimer.unref?.();\n\t};\n\n\tconst scheduleRestart = () => {\n\t\tif (state.watcherRestartTimer) return;\n\t\tstate.watcherRestartTimer = timers.setTimeout(() => {\n\t\t\tstate.watcherRestartTimer = null;\n\t\t\ttry {\n\t\t\t\tfsApi.mkdirSync(resultsDir, { recursive: true });\n\t\t\t\tstartResultWatcher();\n\t\t\t} catch (error) {\n\t\t\t\tif (shouldFallBackToPolling(error)) {\n\t\t\t\t\tstartPollingFallback(error);\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\treport(`Failed to restart subagent result watcher for '${resultsDir}':`, error);\n\t\t\t\tscheduleRestart();\n\t\t\t}\n\t\t}, WATCHER_RESTART_DELAY_MS);\n\t\tstate.watcherRestartTimer.unref?.();\n\t};\n\n\tconst startResultWatcher = () => {\n\t\tif (state.watcher) return;\n\t\tif (state.watcherRestartTimer) {\n\t\t\ttimers.clearTimeout(state.watcherRestartTimer);\n\t\t\ttimers.clearInterval(state.watcherRestartTimer);\n\t\t\tstate.watcherRestartTimer = null;\n\t\t}\n\t\ttry {\n\t\t\tconst watchDir = resolveWatchPath(resultsDir, fsApi.realpathSync.native);\n\t\t\tstate.watcher = fsApi.watch(watchDir, (ev, file) => {\n\t\t\t\tif (ev !== \"rename\" || !file) return;\n\t\t\t\tconst fileName = file.toString();\n\t\t\t\tif (!fileName.endsWith(\".json\")) return;\n\t\t\t\tstate.resultFileCoalescer.schedule(fileName);\n\t\t\t});\n\t\t\tstate.watcher.on(\"error\", (error) => {\n\t\t\t\tif (shouldFallBackToPolling(error)) {\n\t\t\t\t\tstartPollingFallback(error);\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\treport(`Subagent result watcher failed for '${resultsDir}':`, error);\n\t\t\t\tstate.watcher?.close();\n\t\t\t\tstate.watcher = null;\n\t\t\t\tscheduleRestart();\n\t\t\t});\n\t\t\tstate.watcher.unref?.();\n\t\t} catch (error) {\n\t\t\tif (shouldFallBackToPolling(error)) {\n\t\t\t\tstartPollingFallback(error);\n\t\t\t\treturn;\n\t\t\t}\n\t\t\treport(`Failed to start subagent result watcher for '${resultsDir}':`, error);\n\t\t\tstate.watcher = null;\n\t\t\tscheduleRestart();\n\t\t}\n\t};\n\n\tconst stopResultWatcher = () => {\n\t\tgeneration++;\n\t\tattempts.clear();\n\t\tstate.watcher?.close();\n\t\tstate.watcher = null;\n\t\tif (state.watcherRestartTimer) {\n\t\t\ttimers.clearTimeout(state.watcherRestartTimer);\n\t\t\ttimers.clearInterval(state.watcherRestartTimer);\n\t\t}\n\t\tstate.watcherRestartTimer = null;\n\t\tstate.resultFileCoalescer.clear();\n\t};\n\n\treturn { startResultWatcher, primeExistingResults, stopResultWatcher };\n}\n"]}
@@ -9,16 +9,16 @@ import { projectNestedRegistryForRoot, sanitizeSummary } from "../shared/nested-
9
9
  import { resolveWatchPath } from "../../shared/utils.js";
10
10
  const WATCHER_RESTART_DELAY_MS = 3000;
11
11
  const POLL_INTERVAL_MS = 3000;
12
- function sanitizeNestedResultChildren(value, resultPath, label) {
12
+ function sanitizeNestedResultChildren(value, resultPath, label, report) {
13
13
  if (value === undefined)
14
14
  return undefined;
15
15
  if (!Array.isArray(value)) {
16
- console.error(`Ignoring invalid nested children in subagent result file '${resultPath}' at ${label}: expected an array.`);
16
+ report(`Ignoring invalid nested children in subagent result file '${resultPath}' at ${label}: expected an array.`);
17
17
  return undefined;
18
18
  }
19
19
  const children = value.map((child) => sanitizeSummary(child)).filter((child) => Boolean(child));
20
20
  if (children.length !== value.length) {
21
- console.error(`Ignoring ${value.length - children.length} invalid nested child record(s) in subagent result file '${resultPath}' at ${label}.`);
21
+ report(`Ignoring ${value.length - children.length} invalid nested child record(s) in subagent result file '${resultPath}' at ${label}.`);
22
22
  }
23
23
  return children.length ? children : undefined;
24
24
  }
@@ -37,32 +37,40 @@ function shouldFallBackToPolling(error) {
37
37
  export function createResultWatcher(pi, state, resultsDir, completionTtlMs, deps = {}) {
38
38
  const fsApi = deps.fs ?? fs;
39
39
  const timers = deps.timers ?? { setTimeout, clearTimeout, setInterval, clearInterval };
40
+ let generation = 0;
41
+ const inFlight = new Set();
42
+ const attempts = new Map();
43
+ const report = (message, error) => {
44
+ pi.appendEntry?.("subagent_result_delivery", { message, error: error instanceof Error ? error.message : error });
45
+ };
40
46
  const handleResult = async (file) => {
47
+ if (inFlight.has(file) || (attempts.get(file) ?? 0) >= 3)
48
+ return;
49
+ const currentGeneration = generation;
50
+ const sessionId = state.currentSessionId;
51
+ const isCurrent = () => generation === currentGeneration && state.currentSessionId === sessionId;
41
52
  const resultPath = path.join(resultsDir, file);
42
53
  if (!fsApi.existsSync(resultPath))
43
54
  return;
55
+ inFlight.add(file);
44
56
  try {
45
57
  const data = JSON.parse(fsApi.readFileSync(resultPath, "utf-8"));
46
58
  if (typeof data.sessionId !== "string" || data.sessionId !== state.currentSessionId)
47
59
  return;
48
60
  const runId = data.runId ?? data.id ?? file.replace(/\.json$/i, "");
49
61
  const hasExplicitNestedChildren = data.nestedChildren !== undefined;
50
- let nestedChildren = compactNestedResultChildren(sanitizeNestedResultChildren(data.nestedChildren, resultPath, "nestedChildren"));
62
+ let nestedChildren = compactNestedResultChildren(sanitizeNestedResultChildren(data.nestedChildren, resultPath, "nestedChildren", report));
51
63
  if (!nestedChildren?.length && !hasExplicitNestedChildren) {
52
64
  try {
53
65
  nestedChildren = compactNestedResultChildren(projectNestedRegistryForRoot(runId)?.children);
54
66
  }
55
67
  catch (error) {
56
- console.error(`Failed to enrich subagent result file '${resultPath}' with nested registry children; will retry later:`, error);
68
+ report(`Failed to enrich subagent result file '${resultPath}' with nested registry children; will retry later:`, error);
57
69
  return;
58
70
  }
59
71
  }
60
72
  const now = Date.now();
61
73
  const completionKey = buildCompletionKey(data, `result:${file}`);
62
- if (markSeenWithTtl(state.completionSeen, completionKey, now, completionTtlMs)) {
63
- fsApi.unlinkSync(resultPath);
64
- return;
65
- }
66
74
  const hasResultChildren = Array.isArray(data.results) && data.results.length > 0;
67
75
  const resultChildren = hasResultChildren
68
76
  ? data.results
@@ -79,7 +87,7 @@ export function createResultWatcher(pi, state, resultsDir, completionTtlMs, deps
79
87
  ? `${result.error}${hasRealOutput ? `\n\nOutput:\n${baseOutput}` : ""}`
80
88
  : output;
81
89
  const sessionPath = result.sessionFile ?? (resultChildren.length === 1 ? data.sessionFile : undefined);
82
- const childNestedChildren = sanitizeNestedResultChildren(result.children, resultPath, `results[${index}].children`);
90
+ const childNestedChildren = sanitizeNestedResultChildren(result.children, resultPath, `results[${index}].children`, report);
83
91
  const childState = result.state === "paused" || result.state === "stopped"
84
92
  ? result.state
85
93
  : result.stopped === true
@@ -101,7 +109,21 @@ export function createResultWatcher(pi, state, resultsDir, completionTtlMs, deps
101
109
  ...(childNestedChildren ? { children: childNestedChildren } : {}),
102
110
  };
103
111
  }), nestedChildren);
104
- const intercomTarget = data.intercomTarget?.trim();
112
+ if (!markSeenWithTtl(state.completionSeen, completionKey, now, completionTtlMs)) {
113
+ pi.events.emit(SUBAGENT_ASYNC_COMPLETE_EVENT, {
114
+ ...data,
115
+ runId,
116
+ ...(nestedChildren?.length ? { nestedChildren } : {}),
117
+ ...(Array.isArray(data.results) ? { results: hasResultChildren ? normalizedChildren.map((child, index) => ({
118
+ ...data.results[index],
119
+ agent: child.agent, status: child.status, summary: child.summary,
120
+ index: child.index, artifactPath: child.artifactPath, sessionPath: child.sessionPath, children: child.children,
121
+ })) : [] } : {}),
122
+ });
123
+ }
124
+ if (!isCurrent())
125
+ return;
126
+ const intercomTarget = data.state === "stopped" ? undefined : data.intercomTarget?.trim();
105
127
  if (intercomTarget) {
106
128
  const mode = data.mode === "single" || data.mode === "parallel" || data.mode === "chain"
107
129
  ? data.mode
@@ -115,36 +137,29 @@ export function createResultWatcher(pi, state, resultsDir, completionTtlMs, deps
115
137
  asyncId: data.id,
116
138
  asyncDir: data.asyncDir,
117
139
  });
140
+ payload.requestId = `async-result:${sessionId}:${completionKey}`;
141
+ payload.ownerNotificationSessionId = sessionId;
142
+ attempts.set(file, (attempts.get(file) ?? 0) + 1);
118
143
  const delivered = await deliverSubagentResultIntercomEvent(pi.events, payload);
144
+ if (!isCurrent())
145
+ return;
119
146
  if (!delivered) {
120
- console.error(`Subagent async grouped result intercom delivery was not acknowledged for '${resultPath}'.`);
147
+ report(`Async result delivery pending for '${runId}'; output retained.`, resultPath);
148
+ if (attempts.get(file) < 3)
149
+ state.resultFileCoalescer.schedule(file, 1000);
150
+ return;
121
151
  }
122
152
  }
123
- pi.events.emit(SUBAGENT_ASYNC_COMPLETE_EVENT, {
124
- ...data,
125
- runId,
126
- ...(nestedChildren?.length ? { nestedChildren } : {}),
127
- ...(Array.isArray(data.results) ? {
128
- results: hasResultChildren
129
- ? normalizedChildren.map((child, index) => ({
130
- ...data.results[index],
131
- agent: child.agent,
132
- status: child.status,
133
- summary: child.summary,
134
- index: child.index,
135
- artifactPath: child.artifactPath,
136
- sessionPath: child.sessionPath,
137
- children: child.children,
138
- }))
139
- : [],
140
- } : {}),
141
- });
142
- fsApi.unlinkSync(resultPath);
153
+ if (isCurrent())
154
+ fsApi.unlinkSync(resultPath);
143
155
  }
144
156
  catch (error) {
145
157
  if (isNotFoundError(error))
146
158
  return;
147
- console.error(`Failed to process subagent result file '${resultPath}':`, error);
159
+ report(`Failed to process subagent result file '${resultPath}'.`, error);
160
+ }
161
+ finally {
162
+ inFlight.delete(file);
148
163
  }
149
164
  };
150
165
  state.resultFileCoalescer = createFileCoalescer((file) => {
@@ -159,7 +174,7 @@ export function createResultWatcher(pi, state, resultsDir, completionTtlMs, deps
159
174
  catch (error) {
160
175
  if (isNotFoundError(error))
161
176
  return;
162
- console.error(`Failed to scan subagent result directory '${resultsDir}':`, error);
177
+ report(`Failed to scan subagent result directory '${resultsDir}':`, error);
163
178
  }
164
179
  };
165
180
  const startPollingFallback = (reason) => {
@@ -167,7 +182,7 @@ export function createResultWatcher(pi, state, resultsDir, completionTtlMs, deps
167
182
  state.watcher = null;
168
183
  if (state.watcherRestartTimer)
169
184
  return;
170
- console.error(`Subagent result watcher for '${resultsDir}' fell back to polling because native fs.watch is unavailable (${getErrorCode(reason) ?? "unknown error"}).`);
185
+ report(`Subagent result watcher for '${resultsDir}' fell back to polling because native fs.watch is unavailable (${getErrorCode(reason) ?? "unknown error"}).`);
171
186
  primeExistingResults();
172
187
  state.watcherRestartTimer = timers.setInterval(primeExistingResults, POLL_INTERVAL_MS);
173
188
  state.watcherRestartTimer.unref?.();
@@ -186,7 +201,7 @@ export function createResultWatcher(pi, state, resultsDir, completionTtlMs, deps
186
201
  startPollingFallback(error);
187
202
  return;
188
203
  }
189
- console.error(`Failed to restart subagent result watcher for '${resultsDir}':`, error);
204
+ report(`Failed to restart subagent result watcher for '${resultsDir}':`, error);
190
205
  scheduleRestart();
191
206
  }
192
207
  }, WATCHER_RESTART_DELAY_MS);
@@ -215,7 +230,7 @@ export function createResultWatcher(pi, state, resultsDir, completionTtlMs, deps
215
230
  startPollingFallback(error);
216
231
  return;
217
232
  }
218
- console.error(`Subagent result watcher failed for '${resultsDir}':`, error);
233
+ report(`Subagent result watcher failed for '${resultsDir}':`, error);
219
234
  state.watcher?.close();
220
235
  state.watcher = null;
221
236
  scheduleRestart();
@@ -227,12 +242,14 @@ export function createResultWatcher(pi, state, resultsDir, completionTtlMs, deps
227
242
  startPollingFallback(error);
228
243
  return;
229
244
  }
230
- console.error(`Failed to start subagent result watcher for '${resultsDir}':`, error);
245
+ report(`Failed to start subagent result watcher for '${resultsDir}':`, error);
231
246
  state.watcher = null;
232
247
  scheduleRestart();
233
248
  }
234
249
  };
235
250
  const stopResultWatcher = () => {
251
+ generation++;
252
+ attempts.clear();
236
253
  state.watcher?.close();
237
254
  state.watcher = null;
238
255
  if (state.watcherRestartTimer) {
@@ -1 +1 @@
1
- {"version":3,"file":"result-watcher.js","sourceRoot":"","sources":["../../../../../../src/builtin-extensions/pi-subagents/src/runs/background/result-watcher.ts"],"names":[],"mappings":"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","sourcesContent":["// @ts-nocheck\nimport * as fs from \"node:fs\";\nimport * as path from \"node:path\";\nimport { buildCompletionKey, markSeenWithTtl } from \"./completion-dedupe.ts\";\nimport { createFileCoalescer } from \"../../shared/file-coalescer.ts\";\nimport {\n\tSUBAGENT_ASYNC_COMPLETE_EVENT,\n\ttype IntercomEventBus,\n\ttype NestedRunSummary,\n\ttype SubagentResultIntercomChild,\n\ttype SubagentState,\n} from \"../../shared/types.ts\";\nimport {\n\tattachNestedChildrenToResultChildren,\n\tbuildSubagentResultIntercomPayload,\n\tcompactNestedResultChildren,\n\tdeliverSubagentResultIntercomEvent,\n\tresolveSubagentResultStatus,\n} from \"../../intercom/result-intercom.ts\";\nimport { projectNestedRegistryForRoot, sanitizeSummary } from \"../shared/nested-events.ts\";\nimport { resolveWatchPath } from \"../../shared/utils.ts\";\n\nconst WATCHER_RESTART_DELAY_MS = 3000;\nconst POLL_INTERVAL_MS = 3000;\n\ntype ResultWatcherFs = Pick<typeof fs, \"existsSync\" | \"readFileSync\" | \"unlinkSync\" | \"readdirSync\" | \"mkdirSync\" | \"realpathSync\" | \"watch\">;\n\ntype ResultWatcherTimers = {\n\tsetTimeout: typeof setTimeout;\n\tclearTimeout: typeof clearTimeout;\n\tsetInterval: typeof setInterval;\n\tclearInterval: typeof clearInterval;\n};\n\ntype ResultWatcherDeps = {\n\tfs?: ResultWatcherFs;\n\ttimers?: ResultWatcherTimers;\n};\n\ntype ResultFileChild = {\n\tagent?: string;\n\toutput?: string;\n\terror?: string;\n\tsuccess?: boolean;\n\tstate?: string;\n\tstopped?: boolean;\n\tsessionFile?: string;\n\tartifactPaths?: { outputPath?: string };\n\tintercomTarget?: string;\n\tchildren?: unknown;\n};\n\ntype ResultFileData = {\n\tid?: string;\n\trunId?: string;\n\tagent?: string;\n\tsuccess?: boolean;\n\tstate?: string;\n\tmode?: string;\n\tsummary?: string;\n\tresults?: ResultFileChild[];\n\tnestedChildren?: unknown;\n\tsessionId?: string;\n\tcwd?: string;\n\tsessionFile?: string;\n\tasyncDir?: string;\n\tintercomTarget?: string;\n};\n\nfunction sanitizeNestedResultChildren(value: unknown, resultPath: string, label: string): NestedRunSummary[] | undefined {\n\tif (value === undefined) return undefined;\n\tif (!Array.isArray(value)) {\n\t\tconsole.error(`Ignoring invalid nested children in subagent result file '${resultPath}' at ${label}: expected an array.`);\n\t\treturn undefined;\n\t}\n\tconst children = value.map((child) => sanitizeSummary(child)).filter((child): child is NestedRunSummary => Boolean(child));\n\tif (children.length !== value.length) {\n\t\tconsole.error(`Ignoring ${value.length - children.length} invalid nested child record(s) in subagent result file '${resultPath}' at ${label}.`);\n\t}\n\treturn children.length ? children : undefined;\n}\n\nfunction getErrorCode(error: unknown): string | undefined {\n\treturn typeof error === \"object\" && error !== null && \"code\" in error\n\t\t? (error as NodeJS.ErrnoException).code\n\t\t: undefined;\n}\n\nfunction isNotFoundError(error: unknown): boolean {\n\treturn getErrorCode(error) === \"ENOENT\";\n}\n\nfunction shouldFallBackToPolling(error: unknown): boolean {\n\tconst code = getErrorCode(error);\n\treturn code === \"EMFILE\" || code === \"ENOSPC\";\n}\n\n\nexport function createResultWatcher(\n\tpi: { events: IntercomEventBus },\n\tstate: SubagentState,\n\tresultsDir: string,\n\tcompletionTtlMs: number,\n\tdeps: ResultWatcherDeps = {},\n): {\n\tstartResultWatcher: () => void;\n\tprimeExistingResults: () => void;\n\tstopResultWatcher: () => void;\n} {\n\tconst fsApi = deps.fs ?? fs;\n\tconst timers = deps.timers ?? { setTimeout, clearTimeout, setInterval, clearInterval };\n\n\tconst handleResult = async (file: string) => {\n\t\tconst resultPath = path.join(resultsDir, file);\n\t\tif (!fsApi.existsSync(resultPath)) return;\n\t\ttry {\n\t\t\tconst data = JSON.parse(fsApi.readFileSync(resultPath, \"utf-8\")) as ResultFileData;\n\t\t\tif (typeof data.sessionId !== \"string\" || data.sessionId !== state.currentSessionId) return;\n\n\t\t\tconst runId = data.runId ?? data.id ?? file.replace(/\\.json$/i, \"\");\n\t\t\tconst hasExplicitNestedChildren = data.nestedChildren !== undefined;\n\t\t\tlet nestedChildren = compactNestedResultChildren(sanitizeNestedResultChildren(data.nestedChildren, resultPath, \"nestedChildren\"));\n\t\t\tif (!nestedChildren?.length && !hasExplicitNestedChildren) {\n\t\t\t\ttry {\n\t\t\t\t\tnestedChildren = compactNestedResultChildren(projectNestedRegistryForRoot(runId)?.children);\n\t\t\t\t} catch (error) {\n\t\t\t\t\tconsole.error(`Failed to enrich subagent result file '${resultPath}' with nested registry children; will retry later:`, error);\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t}\n\t\t\tconst now = Date.now();\n\t\t\tconst completionKey = buildCompletionKey(data, `result:${file}`);\n\t\t\tif (markSeenWithTtl(state.completionSeen, completionKey, now, completionTtlMs)) {\n\t\t\t\tfsApi.unlinkSync(resultPath);\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\tconst hasResultChildren = Array.isArray(data.results) && data.results.length > 0;\n\t\t\tconst resultChildren = hasResultChildren\n\t\t\t\t? data.results!\n\t\t\t\t: [{\n\t\t\t\t\tagent: data.agent,\n\t\t\t\t\toutput: data.summary,\n\t\t\t\t\tsuccess: data.success,\n\t\t\t\t}];\n\t\t\tconst normalizedChildren = attachNestedChildrenToResultChildren(runId, resultChildren.map((result = {}, index): SubagentResultIntercomChild => {\n\t\t\t\tconst baseOutput = result.output ?? data.summary;\n\t\t\t\tconst hasRealOutput = typeof baseOutput === \"string\" && baseOutput.trim().length > 0;\n\t\t\t\tconst output = hasRealOutput ? baseOutput : \"(no output)\";\n\t\t\t\tconst summary = result.success === false && result.error\n\t\t\t\t\t? `${result.error}${hasRealOutput ? `\\n\\nOutput:\\n${baseOutput}` : \"\"}`\n\t\t\t\t\t: output;\n\t\t\t\tconst sessionPath = result.sessionFile ?? (resultChildren.length === 1 ? data.sessionFile : undefined);\n\t\t\t\tconst childNestedChildren = sanitizeNestedResultChildren(result.children, resultPath, `results[${index}].children`);\n\t\t\t\tconst childState = result.state === \"paused\" || result.state === \"stopped\"\n\t\t\t\t\t? result.state\n\t\t\t\t\t: result.stopped === true\n\t\t\t\t\t\t? \"stopped\"\n\t\t\t\t\t\t: data.state === \"paused\" || (!hasResultChildren && (data.state === \"stopped\" || typeof result.success !== \"boolean\"))\n\t\t\t\t\t\t\t? data.state\n\t\t\t\t\t\t\t: undefined;\n\t\t\t\treturn {\n\t\t\t\t\tagent: result.agent ?? data.agent ?? `step-${index + 1}`,\n\t\t\t\t\tstatus: resolveSubagentResultStatus({\n\t\t\t\t\t\tsuccess: result.success,\n\t\t\t\t\t\tstate: childState,\n\t\t\t\t\t}),\n\t\t\t\t\tsummary,\n\t\t\t\t\tindex,\n\t\t\t\t\tartifactPath: result.artifactPaths?.outputPath,\n\t\t\t\t\t...(typeof sessionPath === \"string\" && fsApi.existsSync(sessionPath) ? { sessionPath } : {}),\n\t\t\t\t\t...(result.intercomTarget ? { intercomTarget: result.intercomTarget } : {}),\n\t\t\t\t\t...(childNestedChildren ? { children: childNestedChildren } : {}),\n\t\t\t\t};\n\t\t\t}), nestedChildren);\n\n\t\t\tconst intercomTarget = data.intercomTarget?.trim();\n\t\t\tif (intercomTarget) {\n\t\t\t\tconst mode = data.mode === \"single\" || data.mode === \"parallel\" || data.mode === \"chain\"\n\t\t\t\t\t? data.mode\n\t\t\t\t\t: resultChildren.length > 1 ? \"chain\" : \"single\";\n\t\t\t\tconst payload = buildSubagentResultIntercomPayload({\n\t\t\t\t\tto: intercomTarget,\n\t\t\t\t\trunId,\n\t\t\t\t\tmode,\n\t\t\t\t\tsource: \"async\",\n\t\t\t\t\tchildren: normalizedChildren,\n\t\t\t\t\tasyncId: data.id,\n\t\t\t\t\tasyncDir: data.asyncDir,\n\t\t\t\t});\n\t\t\t\tconst delivered = await deliverSubagentResultIntercomEvent(pi.events, payload);\n\t\t\t\tif (!delivered) {\n\t\t\t\t\tconsole.error(`Subagent async grouped result intercom delivery was not acknowledged for '${resultPath}'.`);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tpi.events.emit(SUBAGENT_ASYNC_COMPLETE_EVENT, {\n\t\t\t\t...data,\n\t\t\t\trunId,\n\t\t\t\t...(nestedChildren?.length ? { nestedChildren } : {}),\n\t\t\t\t...(Array.isArray(data.results) ? {\n\t\t\t\t\tresults: hasResultChildren\n\t\t\t\t\t\t? normalizedChildren.map((child, index) => ({\n\t\t\t\t\t\t\t...data.results![index],\n\t\t\t\t\t\t\tagent: child.agent,\n\t\t\t\t\t\t\tstatus: child.status,\n\t\t\t\t\t\t\tsummary: child.summary,\n\t\t\t\t\t\t\tindex: child.index,\n\t\t\t\t\t\t\tartifactPath: child.artifactPath,\n\t\t\t\t\t\t\tsessionPath: child.sessionPath,\n\t\t\t\t\t\t\tchildren: child.children,\n\t\t\t\t\t\t}))\n\t\t\t\t\t\t: [],\n\t\t\t\t} : {}),\n\t\t\t});\n\t\t\tfsApi.unlinkSync(resultPath);\n\t\t} catch (error) {\n\t\t\tif (isNotFoundError(error)) return;\n\t\t\tconsole.error(`Failed to process subagent result file '${resultPath}':`, error);\n\t\t}\n\t};\n\n\tstate.resultFileCoalescer = createFileCoalescer((file) => {\n\t\tvoid handleResult(file);\n\t}, 50);\n\n\tconst primeExistingResults = () => {\n\t\ttry {\n\t\t\tfsApi.readdirSync(resultsDir)\n\t\t\t\t.filter((f) => f.endsWith(\".json\"))\n\t\t\t\t.forEach((file) => state.resultFileCoalescer.schedule(file, 0));\n\t\t} catch (error) {\n\t\t\tif (isNotFoundError(error)) return;\n\t\t\tconsole.error(`Failed to scan subagent result directory '${resultsDir}':`, error);\n\t\t}\n\t};\n\n\tconst startPollingFallback = (reason: unknown) => {\n\t\tstate.watcher?.close();\n\t\tstate.watcher = null;\n\t\tif (state.watcherRestartTimer) return;\n\n\t\tconsole.error(\n\t\t\t`Subagent result watcher for '${resultsDir}' fell back to polling because native fs.watch is unavailable (${getErrorCode(reason) ?? \"unknown error\"}).`,\n\t\t);\n\t\tprimeExistingResults();\n\t\tstate.watcherRestartTimer = timers.setInterval(primeExistingResults, POLL_INTERVAL_MS);\n\t\tstate.watcherRestartTimer.unref?.();\n\t};\n\n\tconst scheduleRestart = () => {\n\t\tif (state.watcherRestartTimer) return;\n\t\tstate.watcherRestartTimer = timers.setTimeout(() => {\n\t\t\tstate.watcherRestartTimer = null;\n\t\t\ttry {\n\t\t\t\tfsApi.mkdirSync(resultsDir, { recursive: true });\n\t\t\t\tstartResultWatcher();\n\t\t\t} catch (error) {\n\t\t\t\tif (shouldFallBackToPolling(error)) {\n\t\t\t\t\tstartPollingFallback(error);\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\tconsole.error(`Failed to restart subagent result watcher for '${resultsDir}':`, error);\n\t\t\t\tscheduleRestart();\n\t\t\t}\n\t\t}, WATCHER_RESTART_DELAY_MS);\n\t\tstate.watcherRestartTimer.unref?.();\n\t};\n\n\tconst startResultWatcher = () => {\n\t\tif (state.watcher) return;\n\t\tif (state.watcherRestartTimer) {\n\t\t\ttimers.clearTimeout(state.watcherRestartTimer);\n\t\t\ttimers.clearInterval(state.watcherRestartTimer);\n\t\t\tstate.watcherRestartTimer = null;\n\t\t}\n\t\ttry {\n\t\t\tconst watchDir = resolveWatchPath(resultsDir, fsApi.realpathSync.native);\n\t\t\tstate.watcher = fsApi.watch(watchDir, (ev, file) => {\n\t\t\t\tif (ev !== \"rename\" || !file) return;\n\t\t\t\tconst fileName = file.toString();\n\t\t\t\tif (!fileName.endsWith(\".json\")) return;\n\t\t\t\tstate.resultFileCoalescer.schedule(fileName);\n\t\t\t});\n\t\t\tstate.watcher.on(\"error\", (error) => {\n\t\t\t\tif (shouldFallBackToPolling(error)) {\n\t\t\t\t\tstartPollingFallback(error);\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\tconsole.error(`Subagent result watcher failed for '${resultsDir}':`, error);\n\t\t\t\tstate.watcher?.close();\n\t\t\t\tstate.watcher = null;\n\t\t\t\tscheduleRestart();\n\t\t\t});\n\t\t\tstate.watcher.unref?.();\n\t\t} catch (error) {\n\t\t\tif (shouldFallBackToPolling(error)) {\n\t\t\t\tstartPollingFallback(error);\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tconsole.error(`Failed to start subagent result watcher for '${resultsDir}':`, error);\n\t\t\tstate.watcher = null;\n\t\t\tscheduleRestart();\n\t\t}\n\t};\n\n\tconst stopResultWatcher = () => {\n\t\tstate.watcher?.close();\n\t\tstate.watcher = null;\n\t\tif (state.watcherRestartTimer) {\n\t\t\ttimers.clearTimeout(state.watcherRestartTimer);\n\t\t\ttimers.clearInterval(state.watcherRestartTimer);\n\t\t}\n\t\tstate.watcherRestartTimer = null;\n\t\tstate.resultFileCoalescer.clear();\n\t};\n\n\treturn { startResultWatcher, primeExistingResults, stopResultWatcher };\n}\n"]}
1
+ {"version":3,"file":"result-watcher.js","sourceRoot":"","sources":["../../../../../../src/builtin-extensions/pi-subagents/src/runs/background/result-watcher.ts"],"names":[],"mappings":"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","sourcesContent":["// @ts-nocheck\nimport * as fs from \"node:fs\";\nimport * as path from \"node:path\";\nimport { buildCompletionKey, markSeenWithTtl } from \"./completion-dedupe.ts\";\nimport { createFileCoalescer } from \"../../shared/file-coalescer.ts\";\nimport {\n\tSUBAGENT_ASYNC_COMPLETE_EVENT,\n\ttype IntercomEventBus,\n\ttype NestedRunSummary,\n\ttype SubagentResultIntercomChild,\n\ttype SubagentState,\n} from \"../../shared/types.ts\";\nimport {\n\tattachNestedChildrenToResultChildren,\n\tbuildSubagentResultIntercomPayload,\n\tcompactNestedResultChildren,\n\tdeliverSubagentResultIntercomEvent,\n\tresolveSubagentResultStatus,\n} from \"../../intercom/result-intercom.ts\";\nimport { projectNestedRegistryForRoot, sanitizeSummary } from \"../shared/nested-events.ts\";\nimport { resolveWatchPath } from \"../../shared/utils.ts\";\n\nconst WATCHER_RESTART_DELAY_MS = 3000;\nconst POLL_INTERVAL_MS = 3000;\n\ntype ResultWatcherFs = Pick<typeof fs, \"existsSync\" | \"readFileSync\" | \"unlinkSync\" | \"readdirSync\" | \"mkdirSync\" | \"realpathSync\" | \"watch\">;\n\ntype ResultWatcherTimers = {\n\tsetTimeout: typeof setTimeout;\n\tclearTimeout: typeof clearTimeout;\n\tsetInterval: typeof setInterval;\n\tclearInterval: typeof clearInterval;\n};\n\ntype ResultWatcherDeps = {\n\tfs?: ResultWatcherFs;\n\ttimers?: ResultWatcherTimers;\n};\n\ntype ResultFileChild = {\n\tagent?: string;\n\toutput?: string;\n\terror?: string;\n\tsuccess?: boolean;\n\tstate?: string;\n\tstopped?: boolean;\n\tsessionFile?: string;\n\tartifactPaths?: { outputPath?: string };\n\tintercomTarget?: string;\n\tchildren?: unknown;\n};\n\ntype ResultFileData = {\n\tid?: string;\n\trunId?: string;\n\tagent?: string;\n\tsuccess?: boolean;\n\tstate?: string;\n\tmode?: string;\n\tsummary?: string;\n\tresults?: ResultFileChild[];\n\tnestedChildren?: unknown;\n\tsessionId?: string;\n\tcwd?: string;\n\tsessionFile?: string;\n\tasyncDir?: string;\n\tintercomTarget?: string;\n};\n\nfunction sanitizeNestedResultChildren(value: unknown, resultPath: string, label: string, report: (message: string) => void): NestedRunSummary[] | undefined {\n\tif (value === undefined) return undefined;\n\tif (!Array.isArray(value)) {\n\t\treport(`Ignoring invalid nested children in subagent result file '${resultPath}' at ${label}: expected an array.`);\n\t\treturn undefined;\n\t}\n\tconst children = value.map((child) => sanitizeSummary(child)).filter((child): child is NestedRunSummary => Boolean(child));\n\tif (children.length !== value.length) {\n\t\treport(`Ignoring ${value.length - children.length} invalid nested child record(s) in subagent result file '${resultPath}' at ${label}.`);\n\t}\n\treturn children.length ? children : undefined;\n}\n\nfunction getErrorCode(error: unknown): string | undefined {\n\treturn typeof error === \"object\" && error !== null && \"code\" in error\n\t\t? (error as NodeJS.ErrnoException).code\n\t\t: undefined;\n}\n\nfunction isNotFoundError(error: unknown): boolean {\n\treturn getErrorCode(error) === \"ENOENT\";\n}\n\nfunction shouldFallBackToPolling(error: unknown): boolean {\n\tconst code = getErrorCode(error);\n\treturn code === \"EMFILE\" || code === \"ENOSPC\";\n}\n\n\nexport function createResultWatcher(\n\tpi: { events: IntercomEventBus; appendEntry?: (type: string, data: unknown) => void },\n\tstate: SubagentState,\n\tresultsDir: string,\n\tcompletionTtlMs: number,\n\tdeps: ResultWatcherDeps = {},\n): {\n\tstartResultWatcher: () => void;\n\tprimeExistingResults: () => void;\n\tstopResultWatcher: () => void;\n} {\n\tconst fsApi = deps.fs ?? fs;\n\tconst timers = deps.timers ?? { setTimeout, clearTimeout, setInterval, clearInterval };\n\n\tlet generation = 0;\n\tconst inFlight = new Set<string>();\n\tconst attempts = new Map<string, number>();\n\tconst report = (message: string, error?: unknown) => {\n\t\tpi.appendEntry?.(\"subagent_result_delivery\", { message, error: error instanceof Error ? error.message : error });\n\t};\n\n\tconst handleResult = async (file: string) => {\n\t\tif (inFlight.has(file) || (attempts.get(file) ?? 0) >= 3) return;\n\t\tconst currentGeneration = generation;\n\t\tconst sessionId = state.currentSessionId;\n\t\tconst isCurrent = () => generation === currentGeneration && state.currentSessionId === sessionId;\n\t\tconst resultPath = path.join(resultsDir, file);\n\t\tif (!fsApi.existsSync(resultPath)) return;\n\t\tinFlight.add(file);\n\t\ttry {\n\t\t\tconst data = JSON.parse(fsApi.readFileSync(resultPath, \"utf-8\")) as ResultFileData;\n\t\t\tif (typeof data.sessionId !== \"string\" || data.sessionId !== state.currentSessionId) return;\n\n\t\t\tconst runId = data.runId ?? data.id ?? file.replace(/\\.json$/i, \"\");\n\t\t\tconst hasExplicitNestedChildren = data.nestedChildren !== undefined;\n\t\t\tlet nestedChildren = compactNestedResultChildren(sanitizeNestedResultChildren(data.nestedChildren, resultPath, \"nestedChildren\", report));\n\t\t\tif (!nestedChildren?.length && !hasExplicitNestedChildren) {\n\t\t\t\ttry {\n\t\t\t\t\tnestedChildren = compactNestedResultChildren(projectNestedRegistryForRoot(runId)?.children);\n\t\t\t\t} catch (error) {\n\t\t\t\t\treport(`Failed to enrich subagent result file '${resultPath}' with nested registry children; will retry later:`, error);\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t}\n\t\t\tconst now = Date.now();\n\t\t\tconst completionKey = buildCompletionKey(data, `result:${file}`);\n\n\t\t\tconst hasResultChildren = Array.isArray(data.results) && data.results.length > 0;\n\t\t\tconst resultChildren = hasResultChildren\n\t\t\t\t? data.results!\n\t\t\t\t: [{\n\t\t\t\t\tagent: data.agent,\n\t\t\t\t\toutput: data.summary,\n\t\t\t\t\tsuccess: data.success,\n\t\t\t\t}];\n\t\t\tconst normalizedChildren = attachNestedChildrenToResultChildren(runId, resultChildren.map((result = {}, index): SubagentResultIntercomChild => {\n\t\t\t\tconst baseOutput = result.output ?? data.summary;\n\t\t\t\tconst hasRealOutput = typeof baseOutput === \"string\" && baseOutput.trim().length > 0;\n\t\t\t\tconst output = hasRealOutput ? baseOutput : \"(no output)\";\n\t\t\t\tconst summary = result.success === false && result.error\n\t\t\t\t\t? `${result.error}${hasRealOutput ? `\\n\\nOutput:\\n${baseOutput}` : \"\"}`\n\t\t\t\t\t: output;\n\t\t\t\tconst sessionPath = result.sessionFile ?? (resultChildren.length === 1 ? data.sessionFile : undefined);\n\t\t\t\tconst childNestedChildren = sanitizeNestedResultChildren(result.children, resultPath, `results[${index}].children`, report);\n\t\t\t\tconst childState = result.state === \"paused\" || result.state === \"stopped\"\n\t\t\t\t\t? result.state\n\t\t\t\t\t: result.stopped === true\n\t\t\t\t\t\t? \"stopped\"\n\t\t\t\t\t\t: data.state === \"paused\" || (!hasResultChildren && (data.state === \"stopped\" || typeof result.success !== \"boolean\"))\n\t\t\t\t\t\t\t? data.state\n\t\t\t\t\t\t\t: undefined;\n\t\t\t\treturn {\n\t\t\t\t\tagent: result.agent ?? data.agent ?? `step-${index + 1}`,\n\t\t\t\t\tstatus: resolveSubagentResultStatus({\n\t\t\t\t\t\tsuccess: result.success,\n\t\t\t\t\t\tstate: childState,\n\t\t\t\t\t}),\n\t\t\t\t\tsummary,\n\t\t\t\t\tindex,\n\t\t\t\t\tartifactPath: result.artifactPaths?.outputPath,\n\t\t\t\t\t...(typeof sessionPath === \"string\" && fsApi.existsSync(sessionPath) ? { sessionPath } : {}),\n\t\t\t\t\t...(result.intercomTarget ? { intercomTarget: result.intercomTarget } : {}),\n\t\t\t\t\t...(childNestedChildren ? { children: childNestedChildren } : {}),\n\t\t\t\t};\n\t\t\t}), nestedChildren);\n\n\t\t\tif (!markSeenWithTtl(state.completionSeen, completionKey, now, completionTtlMs)) {\n\t\t\t\tpi.events.emit(SUBAGENT_ASYNC_COMPLETE_EVENT, {\n\t\t\t\t\t...data,\n\t\t\t\t\trunId,\n\t\t\t\t\t...(nestedChildren?.length ? { nestedChildren } : {}),\n\t\t\t\t\t...(Array.isArray(data.results) ? { results: hasResultChildren ? normalizedChildren.map((child, index) => ({\n\t\t\t\t\t\t...data.results![index], agent: child.agent, status: child.status, summary: child.summary,\n\t\t\t\t\t\tindex: child.index, artifactPath: child.artifactPath, sessionPath: child.sessionPath, children: child.children,\n\t\t\t\t\t})) : [] } : {}),\n\t\t\t\t});\n\t\t\t}\n\t\t\tif (!isCurrent()) return;\n\t\t\tconst intercomTarget = data.state === \"stopped\" ? undefined : data.intercomTarget?.trim();\n\t\t\tif (intercomTarget) {\n\t\t\t\tconst mode = data.mode === \"single\" || data.mode === \"parallel\" || data.mode === \"chain\"\n\t\t\t\t\t? data.mode\n\t\t\t\t\t: resultChildren.length > 1 ? \"chain\" : \"single\";\n\t\t\t\tconst payload = buildSubagentResultIntercomPayload({\n\t\t\t\t\tto: intercomTarget,\n\t\t\t\t\trunId,\n\t\t\t\t\tmode,\n\t\t\t\t\tsource: \"async\",\n\t\t\t\t\tchildren: normalizedChildren,\n\t\t\t\t\tasyncId: data.id,\n\t\t\t\t\tasyncDir: data.asyncDir,\n\t\t\t\t});\n\t\t\t\tpayload.requestId = `async-result:${sessionId}:${completionKey}`;\n\t\t\t\tpayload.ownerNotificationSessionId = sessionId;\n\t\t\t\tattempts.set(file, (attempts.get(file) ?? 0) + 1);\n\t\t\t\tconst delivered = await deliverSubagentResultIntercomEvent(pi.events, payload);\n\t\t\t\tif (!isCurrent()) return;\n\t\t\t\tif (!delivered) {\n\t\t\t\t\treport(`Async result delivery pending for '${runId}'; output retained.`, resultPath);\n\t\t\t\t\tif (attempts.get(file)! < 3) state.resultFileCoalescer.schedule(file, 1000);\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif (isCurrent()) fsApi.unlinkSync(resultPath);\n\t\t} catch (error) {\n\t\t\tif (isNotFoundError(error)) return;\n\t\t\treport(`Failed to process subagent result file '${resultPath}'.`, error);\n\t\t} finally {\n\t\t\tinFlight.delete(file);\n\t\t}\n\t};\n\n\tstate.resultFileCoalescer = createFileCoalescer((file) => {\n\t\tvoid handleResult(file);\n\t}, 50);\n\n\tconst primeExistingResults = () => {\n\t\ttry {\n\t\t\tfsApi.readdirSync(resultsDir)\n\t\t\t\t.filter((f) => f.endsWith(\".json\"))\n\t\t\t\t.forEach((file) => state.resultFileCoalescer.schedule(file, 0));\n\t\t} catch (error) {\n\t\t\tif (isNotFoundError(error)) return;\n\t\t\treport(`Failed to scan subagent result directory '${resultsDir}':`, error);\n\t\t}\n\t};\n\n\tconst startPollingFallback = (reason: unknown) => {\n\t\tstate.watcher?.close();\n\t\tstate.watcher = null;\n\t\tif (state.watcherRestartTimer) return;\n\n\t\treport(\n\t\t\t`Subagent result watcher for '${resultsDir}' fell back to polling because native fs.watch is unavailable (${getErrorCode(reason) ?? \"unknown error\"}).`,\n\t\t);\n\t\tprimeExistingResults();\n\t\tstate.watcherRestartTimer = timers.setInterval(primeExistingResults, POLL_INTERVAL_MS);\n\t\tstate.watcherRestartTimer.unref?.();\n\t};\n\n\tconst scheduleRestart = () => {\n\t\tif (state.watcherRestartTimer) return;\n\t\tstate.watcherRestartTimer = timers.setTimeout(() => {\n\t\t\tstate.watcherRestartTimer = null;\n\t\t\ttry {\n\t\t\t\tfsApi.mkdirSync(resultsDir, { recursive: true });\n\t\t\t\tstartResultWatcher();\n\t\t\t} catch (error) {\n\t\t\t\tif (shouldFallBackToPolling(error)) {\n\t\t\t\t\tstartPollingFallback(error);\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\treport(`Failed to restart subagent result watcher for '${resultsDir}':`, error);\n\t\t\t\tscheduleRestart();\n\t\t\t}\n\t\t}, WATCHER_RESTART_DELAY_MS);\n\t\tstate.watcherRestartTimer.unref?.();\n\t};\n\n\tconst startResultWatcher = () => {\n\t\tif (state.watcher) return;\n\t\tif (state.watcherRestartTimer) {\n\t\t\ttimers.clearTimeout(state.watcherRestartTimer);\n\t\t\ttimers.clearInterval(state.watcherRestartTimer);\n\t\t\tstate.watcherRestartTimer = null;\n\t\t}\n\t\ttry {\n\t\t\tconst watchDir = resolveWatchPath(resultsDir, fsApi.realpathSync.native);\n\t\t\tstate.watcher = fsApi.watch(watchDir, (ev, file) => {\n\t\t\t\tif (ev !== \"rename\" || !file) return;\n\t\t\t\tconst fileName = file.toString();\n\t\t\t\tif (!fileName.endsWith(\".json\")) return;\n\t\t\t\tstate.resultFileCoalescer.schedule(fileName);\n\t\t\t});\n\t\t\tstate.watcher.on(\"error\", (error) => {\n\t\t\t\tif (shouldFallBackToPolling(error)) {\n\t\t\t\t\tstartPollingFallback(error);\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\treport(`Subagent result watcher failed for '${resultsDir}':`, error);\n\t\t\t\tstate.watcher?.close();\n\t\t\t\tstate.watcher = null;\n\t\t\t\tscheduleRestart();\n\t\t\t});\n\t\t\tstate.watcher.unref?.();\n\t\t} catch (error) {\n\t\t\tif (shouldFallBackToPolling(error)) {\n\t\t\t\tstartPollingFallback(error);\n\t\t\t\treturn;\n\t\t\t}\n\t\t\treport(`Failed to start subagent result watcher for '${resultsDir}':`, error);\n\t\t\tstate.watcher = null;\n\t\t\tscheduleRestart();\n\t\t}\n\t};\n\n\tconst stopResultWatcher = () => {\n\t\tgeneration++;\n\t\tattempts.clear();\n\t\tstate.watcher?.close();\n\t\tstate.watcher = null;\n\t\tif (state.watcherRestartTimer) {\n\t\t\ttimers.clearTimeout(state.watcherRestartTimer);\n\t\t\ttimers.clearInterval(state.watcherRestartTimer);\n\t\t}\n\t\tstate.watcherRestartTimer = null;\n\t\tstate.resultFileCoalescer.clear();\n\t};\n\n\treturn { startResultWatcher, primeExistingResults, stopResultWatcher };\n}\n"]}
@@ -1,2 +1,102 @@
1
+ import type { Message } from "@ashx-j/lunr-ai";
2
+ import { type ArtifactConfig, type ArtifactPaths, type ChainOutputMap, type ModelAttempt, type NestedRouteInfo, type ResolvedTurnBudget, type ToolBudgetState, type TurnBudgetState } from "../../shared/types.ts";
3
+ import { type RunnerSubagentStep as SubagentStep } from "../shared/parallel-utils.ts";
4
+ interface ChildUsage {
5
+ input?: number;
6
+ inputTokens?: number;
7
+ output?: number;
8
+ outputTokens?: number;
9
+ cacheRead?: number;
10
+ cacheWrite?: number;
11
+ cost?: {
12
+ total?: number;
13
+ };
14
+ }
15
+ type ChildMessage = Message & {
16
+ model?: string;
17
+ errorMessage?: string;
18
+ usage?: ChildUsage;
19
+ };
20
+ interface ChildEvent {
21
+ type?: string;
22
+ message?: ChildMessage;
23
+ toolName?: string;
24
+ args?: Record<string, unknown>;
25
+ willRetry?: unknown;
26
+ }
27
+ /** Context for running a single step */
28
+ interface SingleStepContext {
29
+ supervisorSessionId?: string;
30
+ previousOutput: string;
31
+ outputs?: ChainOutputMap;
32
+ placeholder: string;
33
+ cwd: string;
34
+ sessionEnabled: boolean;
35
+ sessionDir?: string;
36
+ artifactsDir?: string;
37
+ artifactConfig?: Partial<ArtifactConfig>;
38
+ id: string;
39
+ flatIndex: number;
40
+ flatStepCount: number;
41
+ outputFile: string;
42
+ steerInboxDir?: string;
43
+ steerCapabilityPath?: string;
44
+ steerAckDir?: string;
45
+ transcriptPath?: string;
46
+ piPackageRoot?: string;
47
+ piArgv1?: string;
48
+ registerInterrupt?: (interrupt: (() => void) | undefined) => void;
49
+ registerTimeout?: (interrupt: (() => void) | undefined) => void;
50
+ registerStop?: (stop: (() => void) | undefined) => void;
51
+ registerTurnBudgetAbort?: (abort: ((message: string, state?: TurnBudgetState) => void) | undefined) => void;
52
+ timeoutSignal?: AbortSignal;
53
+ stopSignal?: AbortSignal;
54
+ timeoutMessage?: string;
55
+ stopMessage?: string;
56
+ turnBudget?: ResolvedTurnBudget;
57
+ childIntercomTarget?: string;
58
+ orchestratorIntercomTarget?: string;
59
+ nestedRoute?: NestedRouteInfo;
60
+ onAttemptStart?: (attempt: {
61
+ model?: string;
62
+ thinking?: string;
63
+ }) => void;
64
+ onChildEvent?: (event: ChildEvent) => void;
65
+ onWriterProcess?: (writer: {
66
+ state: "none" | "spawning";
67
+ } | {
68
+ state: "running";
69
+ pid: number;
70
+ }) => void;
71
+ skipAcceptance?: () => boolean;
72
+ }
73
+ /** Run a single pi agent step, returning output and metadata */
74
+ export declare function runSingleStep(step: SubagentStep, ctx: SingleStepContext): Promise<{
75
+ agent: string;
76
+ output: string;
77
+ exitCode: number | null;
78
+ error?: string;
79
+ model?: string;
80
+ attemptedModels?: string[];
81
+ modelAttempts?: ModelAttempt[];
82
+ artifactPaths?: ArtifactPaths;
83
+ transcriptPath?: string;
84
+ transcriptError?: string;
85
+ interrupted?: boolean;
86
+ timedOut?: boolean;
87
+ stopped?: boolean;
88
+ turnBudget?: TurnBudgetState;
89
+ turnBudgetExceeded?: boolean;
90
+ wrapUpRequested?: boolean;
91
+ toolBudget?: ToolBudgetState;
92
+ toolBudgetBlocked?: boolean;
93
+ sessionFile?: string;
94
+ intercomTarget?: string;
95
+ completionGuardTriggered?: boolean;
96
+ structuredOutput?: unknown;
97
+ structuredOutputPath?: string;
98
+ structuredOutputSchemaPath?: string;
99
+ acceptance?: import("../../shared/types.ts").AcceptanceLedger;
100
+ }>;
1
101
  export {};
2
102
  //# sourceMappingURL=subagent-runner.d.ts.map