@zhushanwen/pi-subagent-workflow 8.5.0 → 8.7.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (336) hide show
  1. package/package.json +13 -16
  2. package/relay/relay.mjs +1 -1
  3. package/src/host/__tests__/pi-host.test.ts +214 -0
  4. package/src/host/pi-host.ts +109 -0
  5. package/src/index.ts +142 -32
  6. package/src/injectors/__tests__/engine-awareness.test.ts +292 -0
  7. package/src/injectors/__tests__/engine-section-stability.test.ts +341 -0
  8. package/src/injectors/__tests__/subagent-list-injector.test.ts +5 -5
  9. package/src/injectors/__tests__/workflow-list-injector.test.ts +5 -5
  10. package/src/injectors/engine-awareness.ts +123 -0
  11. package/src/injectors/model-list-injector.ts +1 -1
  12. package/src/injectors/subagent-list-injector.ts +8 -8
  13. package/src/injectors/workflow-list-injector.ts +8 -8
  14. package/src/interface/__tests__/detectors.test.ts +3 -3
  15. package/src/interface/__tests__/subagent-tool-path-guard.test.ts +157 -0
  16. package/src/interface/__tests__/subagent-tool-prompt.test.ts +12 -0
  17. package/src/interface/__tests__/tool-workflow-script-generate.test.ts +2 -2
  18. package/src/interface/__tests__/tool-workflow-throw-paths.test.ts +1 -1
  19. package/src/interface/bg-notify-render.ts +34 -13
  20. package/src/interface/commands.ts +3 -3
  21. package/src/interface/format.ts +2 -2
  22. package/src/interface/helpers.ts +3 -3
  23. package/src/interface/list-component.ts +4 -4
  24. package/src/interface/list-shared.ts +2 -2
  25. package/src/interface/list-view.ts +2 -2
  26. package/src/interface/subagent-actions.ts +288 -19
  27. package/src/interface/subagent-tool-schema.ts +163 -0
  28. package/src/interface/subagent-tool.ts +65 -129
  29. package/src/interface/subagents.ts +5 -5
  30. package/src/interface/tool-render.ts +34 -2
  31. package/src/interface/tool-workflow-script.ts +4 -4
  32. package/src/interface/tool-workflow.ts +6 -6
  33. package/src/interface/views/WorkflowsView.ts +5 -5
  34. package/src/interface/views/__tests__/WorkflowsView-signature.test.ts +3 -3
  35. package/src/interface/views/__tests__/detail-content-session-file.test.ts +2 -2
  36. package/src/interface/views/detail-content.ts +4 -4
  37. package/src/interface/views/format.ts +4 -4
  38. package/src/{orchestration/jsonl-run-store.ts → jsonl-run-store.ts} +132 -18
  39. package/src/execution/__tests__/__fixtures__/notifier-golden-snapshots.json +0 -53
  40. package/src/execution/__tests__/__fixtures__/truncline.snapshot.json +0 -1
  41. package/src/execution/__tests__/agent-registry.test.ts +0 -363
  42. package/src/execution/__tests__/agent-result-mapper.test.ts +0 -150
  43. package/src/execution/__tests__/alive-store.test.ts +0 -147
  44. package/src/execution/__tests__/ask-user-transit-e2e.test.ts +0 -490
  45. package/src/execution/__tests__/before-agent-start-injection.test.ts +0 -132
  46. package/src/execution/__tests__/bg-notify-render.test.ts +0 -256
  47. package/src/execution/__tests__/channel-registry-handshake.test.ts +0 -243
  48. package/src/execution/__tests__/chat-engine-routing.test.ts +0 -597
  49. package/src/execution/__tests__/chatmode-first-round-closure-service.test.ts +0 -365
  50. package/src/execution/__tests__/chatmode-first-round-closure-spawn.test.ts +0 -190
  51. package/src/execution/__tests__/chatmode-round-notify-real-chain.test.ts +0 -215
  52. package/src/execution/__tests__/concurrency-pool.test.ts +0 -250
  53. package/src/execution/__tests__/config.test.ts +0 -110
  54. package/src/execution/__tests__/conversation-wiring.test.ts +0 -198
  55. package/src/execution/__tests__/crash-recovery.test.ts +0 -320
  56. package/src/execution/__tests__/delivery-methods.test.ts +0 -385
  57. package/src/execution/__tests__/dialog-queue.test.ts +0 -299
  58. package/src/execution/__tests__/epipe-fallback.test.ts +0 -241
  59. package/src/execution/__tests__/execute-and-await-worktree.test.ts +0 -243
  60. package/src/execution/__tests__/execute-nesting.test.ts +0 -323
  61. package/src/execution/__tests__/execute-options-mapper.test.ts +0 -189
  62. package/src/execution/__tests__/execution-record.test.ts +0 -1284
  63. package/src/execution/__tests__/finalize-record.test.ts +0 -368
  64. package/src/execution/__tests__/finalized-marker.test.ts +0 -82
  65. package/src/execution/__tests__/format-schema-instruction.test.ts +0 -138
  66. package/src/execution/__tests__/format.test.ts +0 -458
  67. package/src/execution/__tests__/gc-timer.test.ts +0 -184
  68. package/src/execution/__tests__/get-record-for-action-restart.test.ts +0 -254
  69. package/src/execution/__tests__/gui-mode-dispatch.test.ts +0 -59
  70. package/src/execution/__tests__/helpers/mock-extension-api.ts +0 -30
  71. package/src/execution/__tests__/helpers/spawn-mock.ts +0 -238
  72. package/src/execution/__tests__/host-mode.test.ts +0 -87
  73. package/src/execution/__tests__/index-session-start-identity.test.ts +0 -371
  74. package/src/execution/__tests__/index-session-start.test.ts +0 -593
  75. package/src/execution/__tests__/lifecycle-manager-lock.test.ts +0 -211
  76. package/src/execution/__tests__/lifecycle-manager.test.ts +0 -337
  77. package/src/execution/__tests__/lifecycle-predicates.test.ts +0 -116
  78. package/src/execution/__tests__/list-component.test.ts +0 -401
  79. package/src/execution/__tests__/list-fields.test.ts +0 -109
  80. package/src/execution/__tests__/manifest-parentid.test.ts +0 -117
  81. package/src/execution/__tests__/model-resolver.test.ts +0 -413
  82. package/src/execution/__tests__/nested-visibility-env-propagation.test.ts +0 -287
  83. package/src/execution/__tests__/nested-visibility.test.ts +0 -325
  84. package/src/execution/__tests__/notifier-flush.test.ts +0 -574
  85. package/src/execution/__tests__/notifier-golden-snapshot.test.ts +0 -261
  86. package/src/execution/__tests__/one-shot-upgrade.test.ts +0 -205
  87. package/src/execution/__tests__/output-collector.test.ts +0 -61
  88. package/src/execution/__tests__/parent-child-matrix.test.ts +0 -336
  89. package/src/execution/__tests__/path-encoding.test.ts +0 -104
  90. package/src/execution/__tests__/pi-invocation.test.ts +0 -134
  91. package/src/execution/__tests__/record-store.test.ts +0 -1057
  92. package/src/execution/__tests__/records-cwd-isolation.test.ts +0 -91
  93. package/src/execution/__tests__/recursive-visibility-baseline.test.ts +0 -339
  94. package/src/execution/__tests__/recursive-visibility-env.test.ts +0 -273
  95. package/src/execution/__tests__/relay-agent.test.ts +0 -448
  96. package/src/execution/__tests__/relay-env.test.ts +0 -42
  97. package/src/execution/__tests__/resource-policy.test.ts +0 -109
  98. package/src/execution/__tests__/rpc-mode.test.ts +0 -89
  99. package/src/execution/__tests__/run-and-finalize-chatmode.test.ts +0 -267
  100. package/src/execution/__tests__/run-spawn-chatmode-settled.test.ts +0 -253
  101. package/src/execution/__tests__/run-spawn-edges.test.ts +0 -644
  102. package/src/execution/__tests__/run-spawn-integration.test.ts +0 -933
  103. package/src/execution/__tests__/run-spawn-resume.test.ts +0 -322
  104. package/src/execution/__tests__/run-spawn-rpc-mode.test.ts +0 -196
  105. package/src/execution/__tests__/sdk-contract.test.ts +0 -273
  106. package/src/execution/__tests__/session-context-resolver.test.ts +0 -167
  107. package/src/execution/__tests__/session-file-gc.test.ts +0 -293
  108. package/src/execution/__tests__/session-pending.test.ts +0 -197
  109. package/src/execution/__tests__/session-reconstructor.test.ts +0 -379
  110. package/src/execution/__tests__/session-runner-epipe.test.ts +0 -178
  111. package/src/execution/__tests__/session-runner-schema-env.test.ts +0 -311
  112. package/src/execution/__tests__/session-start-reaper.test.ts +0 -233
  113. package/src/execution/__tests__/spawn-args.test.ts +0 -434
  114. package/src/execution/__tests__/spawn-event-adapter-rpc.test.ts +0 -189
  115. package/src/execution/__tests__/spawn-event-adapter.test.ts +0 -167
  116. package/src/execution/__tests__/spawn-worktree-guidance.test.ts +0 -207
  117. package/src/execution/__tests__/spawned-children.test.ts +0 -92
  118. package/src/execution/__tests__/startup-config-declaration.test.ts +0 -35
  119. package/src/execution/__tests__/status-refactor.test.ts +0 -345
  120. package/src/execution/__tests__/stdin-writer.test.ts +0 -463
  121. package/src/execution/__tests__/stream-sink-retirement.test.ts +0 -261
  122. package/src/execution/__tests__/subagent-service-abort.test.ts +0 -60
  123. package/src/execution/__tests__/subagent-service-message-close.test.ts +0 -629
  124. package/src/execution/__tests__/subagent-service-parent-guard.test.ts +0 -180
  125. package/src/execution/__tests__/subagent-service.test.ts +0 -788
  126. package/src/execution/__tests__/subprocess-agent-runner-routing.test.ts +0 -310
  127. package/src/execution/__tests__/subprocess-agent-runner.test.ts +0 -506
  128. package/src/execution/__tests__/temp-prompt.test.ts +0 -53
  129. package/src/execution/__tests__/timeout-integration.test.ts +0 -397
  130. package/src/execution/__tests__/tombstone-store.test.ts +0 -73
  131. package/src/execution/__tests__/tool-action.test.ts +0 -385
  132. package/src/execution/__tests__/truncline-snapshot.test.ts +0 -81
  133. package/src/execution/__tests__/turn-limiter-semantics.test.ts +0 -194
  134. package/src/execution/__tests__/turn-limiter.test.ts +0 -65
  135. package/src/execution/__tests__/ui-channels.test.ts +0 -187
  136. package/src/execution/__tests__/ui-interaction-model.test.ts +0 -67
  137. package/src/execution/__tests__/ui-request-handler-factory.test.ts +0 -370
  138. package/src/execution/__tests__/ui-request-handler.test.ts +0 -204
  139. package/src/execution/__tests__/ui-request-observability.test.ts +0 -114
  140. package/src/execution/__tests__/ui-request-queue.test.ts +0 -133
  141. package/src/execution/__tests__/worktree-manager.test.ts +0 -633
  142. package/src/execution/__tests__/worktree-pid-registration.integration.test.ts +0 -229
  143. package/src/execution/__tests__/worktree-reconcile.integration.test.ts +0 -181
  144. package/src/execution/__tests__/worktree-registry.test.ts +0 -199
  145. package/src/execution/agent-registry.ts +0 -193
  146. package/src/execution/agent-result-mapper.ts +0 -90
  147. package/src/execution/alive-store.ts +0 -92
  148. package/src/execution/argv-mirror.ts +0 -109
  149. package/src/execution/best-effort.ts +0 -38
  150. package/src/execution/channel-registry-access.ts +0 -144
  151. package/src/execution/concurrency-pool.ts +0 -116
  152. package/src/execution/config.ts +0 -96
  153. package/src/execution/dialog-queue.ts +0 -330
  154. package/src/execution/engine/__tests__/common/data-dir.test.ts +0 -53
  155. package/src/execution/engine/__tests__/common/errors.test.ts +0 -132
  156. package/src/execution/engine/__tests__/common/event-journal.test.ts +0 -177
  157. package/src/execution/engine/__tests__/common/kill-chain.test.ts +0 -192
  158. package/src/execution/engine/__tests__/common/nesting-guard.test.ts +0 -81
  159. package/src/execution/engine/__tests__/common/persona-router.test.ts +0 -123
  160. package/src/execution/engine/__tests__/common/pool-manager.test.ts +0 -154
  161. package/src/execution/engine/__tests__/common/schema-emulation.test.ts +0 -128
  162. package/src/execution/engine/__tests__/conformance/__fixtures__/pi-golden-events.json +0 -28
  163. package/src/execution/engine/__tests__/conformance/agent-event-invariants.ts +0 -141
  164. package/src/execution/engine/__tests__/conformance/contract.abort.test.ts +0 -109
  165. package/src/execution/engine/__tests__/conformance/contract.agent-events.test.ts +0 -101
  166. package/src/execution/engine/__tests__/conformance/contract.probe.test.ts +0 -77
  167. package/src/execution/engine/__tests__/conformance/contract.read-degradation.test.ts +0 -104
  168. package/src/execution/engine/__tests__/conformance/contract.relay.test.ts +0 -342
  169. package/src/execution/engine/__tests__/conformance/engine-conformance.live.test.ts +0 -201
  170. package/src/execution/engine/__tests__/conformance/golden-replay.pi.test.ts +0 -76
  171. package/src/execution/engine/__tests__/conformance/golden-replay.zcode.test.ts +0 -79
  172. package/src/execution/engine/__tests__/engine-discovery.test.ts +0 -87
  173. package/src/execution/engine/__tests__/engines-declaration.test.ts +0 -36
  174. package/src/execution/engine/__tests__/model-prompt.test.ts +0 -85
  175. package/src/execution/engine/__tests__/paths.test.ts +0 -39
  176. package/src/execution/engine/__tests__/registry.test.ts +0 -120
  177. package/src/execution/engine/__tests__/routing.test.ts +0 -231
  178. package/src/execution/engine/common/data-dir.ts +0 -62
  179. package/src/execution/engine/common/errors.ts +0 -183
  180. package/src/execution/engine/common/event-journal.ts +0 -254
  181. package/src/execution/engine/common/journal-replay.ts +0 -62
  182. package/src/execution/engine/common/kill-chain.ts +0 -221
  183. package/src/execution/engine/common/nesting-guard.ts +0 -50
  184. package/src/execution/engine/common/persona-router.ts +0 -108
  185. package/src/execution/engine/common/pool-manager.ts +0 -226
  186. package/src/execution/engine/common/schema-emulation.ts +0 -189
  187. package/src/execution/engine/common/session-view-projection.ts +0 -51
  188. package/src/execution/engine/engine-discovery.ts +0 -65
  189. package/src/execution/engine/engines/pi/__tests__/pi-engine.test.ts +0 -469
  190. package/src/execution/engine/engines/pi/__tests__/reader.test.ts +0 -155
  191. package/src/execution/engine/engines/pi/__tests__/task-spec-mapper.test.ts +0 -164
  192. package/src/execution/engine/engines/pi/pi-engine.ts +0 -415
  193. package/src/execution/engine/engines/pi/reader.ts +0 -48
  194. package/src/execution/engine/engines/pi/registration.ts +0 -35
  195. package/src/execution/engine/engines/pi/task-spec-mapper.ts +0 -100
  196. package/src/execution/engine/engines/zcode/__tests__/__fixtures__/zcode-golden-spawn.json +0 -39
  197. package/src/execution/engine/engines/zcode/__tests__/launcher.test.ts +0 -150
  198. package/src/execution/engine/engines/zcode/__tests__/parser.test.ts +0 -246
  199. package/src/execution/engine/engines/zcode/__tests__/preparer.test.ts +0 -228
  200. package/src/execution/engine/engines/zcode/__tests__/reader.test.ts +0 -210
  201. package/src/execution/engine/engines/zcode/__tests__/registration.test.ts +0 -64
  202. package/src/execution/engine/engines/zcode/__tests__/zcode-engine.live.test.ts +0 -127
  203. package/src/execution/engine/engines/zcode/__tests__/zcode-engine.test.ts +0 -567
  204. package/src/execution/engine/engines/zcode/constants.ts +0 -43
  205. package/src/execution/engine/engines/zcode/golden-sample.ts +0 -39
  206. package/src/execution/engine/engines/zcode/launcher.ts +0 -161
  207. package/src/execution/engine/engines/zcode/parser.ts +0 -436
  208. package/src/execution/engine/engines/zcode/preparer.ts +0 -363
  209. package/src/execution/engine/engines/zcode/reader.ts +0 -381
  210. package/src/execution/engine/engines/zcode/registration.ts +0 -37
  211. package/src/execution/engine/engines/zcode/zcode-engine.ts +0 -648
  212. package/src/execution/engine/host-task-spec.ts +0 -47
  213. package/src/execution/engine/model-prompt.ts +0 -59
  214. package/src/execution/engine/paths.ts +0 -42
  215. package/src/execution/engine/port.ts +0 -153
  216. package/src/execution/engine/registry.ts +0 -123
  217. package/src/execution/engine/routing.ts +0 -218
  218. package/src/execution/engine/types.ts +0 -304
  219. package/src/execution/execute-options-mapper.ts +0 -111
  220. package/src/execution/execution-record.ts +0 -906
  221. package/src/execution/finalize-record.ts +0 -251
  222. package/src/execution/finalized-marker.ts +0 -51
  223. package/src/execution/get-state-handshake.ts +0 -104
  224. package/src/execution/host-mode.ts +0 -56
  225. package/src/execution/idle-gc.ts +0 -47
  226. package/src/execution/lifecycle-manager.ts +0 -491
  227. package/src/execution/lifecycle-predicates.ts +0 -65
  228. package/src/execution/manifest-store.ts +0 -256
  229. package/src/execution/model-config-service.ts +0 -204
  230. package/src/execution/model-resolver.ts +0 -276
  231. package/src/execution/notifier.ts +0 -260
  232. package/src/execution/output-collector.ts +0 -88
  233. package/src/execution/path-encoding.ts +0 -60
  234. package/src/execution/pi-invocation.ts +0 -120
  235. package/src/execution/record-entry.ts +0 -132
  236. package/src/execution/record-store.ts +0 -1234
  237. package/src/execution/relay-env.ts +0 -37
  238. package/src/execution/session-context-resolver.ts +0 -64
  239. package/src/execution/session-file-gc.ts +0 -120
  240. package/src/execution/session-pending.ts +0 -164
  241. package/src/execution/session-reconstructor.ts +0 -678
  242. package/src/execution/session-runner.ts +0 -1548
  243. package/src/execution/sessions-index.ts +0 -304
  244. package/src/execution/spawn-event-adapter.ts +0 -363
  245. package/src/execution/stdin-writer.ts +0 -198
  246. package/src/execution/stream-sink.ts +0 -126
  247. package/src/execution/subagent-service.ts +0 -2119
  248. package/src/execution/subprocess-agent-runner.ts +0 -303
  249. package/src/execution/temp-prompt.ts +0 -62
  250. package/src/execution/tombstone-store.ts +0 -72
  251. package/src/execution/turn-limiter.ts +0 -102
  252. package/src/execution/types.ts +0 -910
  253. package/src/execution/ui-channels.ts +0 -216
  254. package/src/execution/ui-interaction-model.ts +0 -48
  255. package/src/execution/ui-request-handler-factory.ts +0 -212
  256. package/src/execution/ui-request-observability.ts +0 -81
  257. package/src/execution/ui-request-queue.ts +0 -174
  258. package/src/execution/worktree-manager.ts +0 -688
  259. package/src/execution/worktree-registry.ts +0 -222
  260. package/src/orchestration/__tests__/__fixtures__/worker-template.snapshot.txt +0 -336
  261. package/src/orchestration/__tests__/agent-call-catch-fallback.test.ts +0 -208
  262. package/src/orchestration/__tests__/agent-call-stream.test.ts +0 -157
  263. package/src/orchestration/__tests__/args-validator.test.ts +0 -143
  264. package/src/orchestration/__tests__/concurrency-gate.test.ts +0 -125
  265. package/src/orchestration/__tests__/config-loader.test.ts +0 -503
  266. package/src/orchestration/__tests__/error-recovery-handlers.test.ts +0 -724
  267. package/src/orchestration/__tests__/error-recovery-postmessage-defense.test.ts +0 -405
  268. package/src/orchestration/__tests__/error-recovery-serialize-failed-result.test.ts +0 -56
  269. package/src/orchestration/__tests__/error-recovery-workflow-call.test.ts +0 -166
  270. package/src/orchestration/__tests__/execute-agent-call.test.ts +0 -314
  271. package/src/orchestration/__tests__/jsonl-run-store-loadall-sources.test.ts +0 -171
  272. package/src/orchestration/__tests__/jsonl-run-store-session-file.test.ts +0 -1030
  273. package/src/orchestration/__tests__/launcher-nested-workflow.test.ts +0 -277
  274. package/src/orchestration/__tests__/lifecycle-runid-injection.test.ts +0 -96
  275. package/src/orchestration/__tests__/lifecycle.test.ts +0 -625
  276. package/src/orchestration/__tests__/review-fix-loop-e2e.test.ts +0 -1971
  277. package/src/orchestration/__tests__/script-lint.test.ts +0 -831
  278. package/src/orchestration/__tests__/skill-discovery.test.ts +0 -157
  279. package/src/orchestration/__tests__/test-mocks.ts +0 -197
  280. package/src/orchestration/__tests__/worker-host.test.ts +0 -120
  281. package/src/orchestration/__tests__/worker-returnmeta-passthrough.test.ts +0 -164
  282. package/src/orchestration/__tests__/worker-script-builder-runtime.test.ts +0 -520
  283. package/src/orchestration/__tests__/worker-script-builder.test.ts +0 -309
  284. package/src/orchestration/__tests__/worker-script-template-snapshot.test.ts +0 -110
  285. package/src/orchestration/__tests__/workflow-nesting-e2e.test.ts +0 -317
  286. package/src/orchestration/__tests__/workflow-script-lint-memo.test.ts +0 -110
  287. package/src/orchestration/__tests__/workflows-e2e.test.ts +0 -537
  288. package/src/orchestration/agent-opts-resolver.ts +0 -93
  289. package/src/orchestration/args-validator.ts +0 -127
  290. package/src/orchestration/concurrency-gate.ts +0 -69
  291. package/src/orchestration/config-loader.ts +0 -315
  292. package/src/orchestration/error-recovery.ts +0 -862
  293. package/src/orchestration/execute-agent-call.ts +0 -217
  294. package/src/orchestration/launcher.ts +0 -410
  295. package/src/orchestration/lifecycle.ts +0 -396
  296. package/src/orchestration/models/__tests__/budget.test.ts +0 -367
  297. package/src/orchestration/models/__tests__/trace.test.ts +0 -408
  298. package/src/orchestration/models/agent-call.ts +0 -83
  299. package/src/orchestration/models/budget.ts +0 -148
  300. package/src/orchestration/models/ports.ts +0 -164
  301. package/src/orchestration/models/run-runtime.ts +0 -89
  302. package/src/orchestration/models/run-spec.ts +0 -83
  303. package/src/orchestration/models/run-state.ts +0 -44
  304. package/src/orchestration/models/trace.ts +0 -183
  305. package/src/orchestration/models/types.ts +0 -292
  306. package/src/orchestration/models/workflow-run.ts +0 -254
  307. package/src/orchestration/models/workflow-script-registry.ts +0 -35
  308. package/src/orchestration/models/workflow-script.ts +0 -117
  309. package/src/orchestration/script-lint.ts +0 -766
  310. package/src/orchestration/skill-discovery.ts +0 -92
  311. package/src/orchestration/worker-handle.ts +0 -115
  312. package/src/orchestration/worker-host.ts +0 -98
  313. package/src/orchestration/worker-script-builder.ts +0 -408
  314. package/src/orchestration/workflow-files.ts +0 -85
  315. package/src/orchestration/workflow-script-registry-impl.ts +0 -133
  316. package/src/shared/__tests__/agent-ref.test.ts +0 -34
  317. package/src/shared/__tests__/meta-parser.test.ts +0 -304
  318. package/src/shared/__tests__/resource-discovery-manifest-cache.test.ts +0 -280
  319. package/src/shared/__tests__/resource-discovery.test.ts +0 -736
  320. package/src/shared/__tests__/resource-meta.test.ts +0 -51
  321. package/src/shared/__tests__/schema-jsonify.test.ts +0 -81
  322. package/src/shared/agent-event.ts +0 -13
  323. package/src/shared/agent-ref.ts +0 -57
  324. package/src/shared/meta-parser.ts +0 -261
  325. package/src/shared/resource-discovery.ts +0 -811
  326. package/src/shared/resource-meta.ts +0 -65
  327. package/src/shared/schema-jsonify.ts +0 -56
  328. package/src/shared/xml-injection.ts +0 -35
  329. package/workflows/README.md +0 -81
  330. package/workflows/_shared/agent-refs.cjs +0 -40
  331. package/workflows/chain.js +0 -131
  332. package/workflows/map-reduce.js +0 -174
  333. package/workflows/parallel.js +0 -148
  334. package/workflows/review-fix-loop-utils.cjs +0 -1307
  335. package/workflows/review-fix-loop.js +0 -1396
  336. package/workflows/scatter-gather.js +0 -178
@@ -9,19 +9,19 @@
9
9
  // Theme、ExtensionContext)会触发 TS2307 误报(probe5d/5f 验证)。
10
10
  // 抽到顶层后参数类型由 alias 提供,绕过该 quirk。
11
11
 
12
+ import { isAbsolute } from "node:path";
13
+
12
14
  import type { Component } from "@earendil-works/pi-tui";
13
- import { StringEnum } from "@earendil-works/pi-ai";
14
15
  import type { AgentToolResult, ExtensionAPI, ExtensionContext, Theme } from "@earendil-works/pi-coding-agent";
15
16
  import { getLogger } from "@zhushanwen/pi-extension-logger";
16
- import { type Static, Type } from "typebox";
17
+ import type { Static } from "typebox";
17
18
 
18
- import { SLUG_MAX_LENGTH } from "../execution/execute-options-mapper.ts";
19
- import { THINKING_ORDER } from "../execution/model-resolver.ts";
20
- import { getSubagentService } from "../execution/subagent-service.ts";
21
- import type { SubagentToolResult } from "../execution/types.ts";
19
+ import { getSubagentService } from "@zhushanwen/subagent-core/execution/subagent-service.ts";
20
+ import type { SubagentToolResult } from "@zhushanwen/subagent-core/execution/types.ts";
22
21
  import { extractAgentName } from "./format.ts";
23
22
  import { toGuiCtx } from "./gui-mappers.ts";
24
- import { adapter, cancelHandler, closeHandler, listHandler, messageHandler, startHandler } from "./subagent-actions.ts";
23
+ import { adapter, cancelHandler, closeHandler, forkFromHandler, listHandler, messageHandler, startHandler } from "./subagent-actions.ts";
24
+ import { SubagentParams } from "./subagent-tool-schema.ts";
25
25
  import { type RenderContext,renderSubagentCall, renderSubagentResult } from "./tool-render.ts";
26
26
 
27
27
  // ============================================================
@@ -54,128 +54,14 @@ type SubagentRenderResultCb = (
54
54
  ctx: RenderContext,
55
55
  ) => Component;
56
56
 
57
- // ============================================================
58
- // Params schema
59
- // ============================================================
60
-
61
- // Params schema(模块内消费,未导出)。
62
- //
63
- // action:"start" 的 13 字段(task/slug/agent/model/...)拍平在顶层,不再用 startParam
64
- // 嵌套容器包。原因:弱模型(GLM/DeepSeek)信任 schema 结构信号 > 文本信号,经常省略
65
- // startParam 嵌套层把 task/slug 直接平铺到顶层导致调用失败。拍平后 schema 结构与模型
66
- // 的自然倾向一致,消除这层误用。task/slug 必填性由 startHandler runtime 校验(flat
67
- // JSON Schema 无法表达「action 条件必填」)。
68
- //
69
- // TODO(long-term, option-A): listParam/cancelParam 仍标 Optional 也是 flat JSON Schema
70
- // 表达「action 分发条件必填」的妥协——长期方案是拆成 3 个独立 tool
71
- // (subagent_start / subagent_list / subagent_cancel),让每个 tool 的 schema 真实
72
- // 反映必填性。勿在此基础上继续堆 action 条件逻辑——要加就拆 tool。
73
- const SubagentParams = Type.Object({
74
- action: StringEnum(["start", "list", "cancel", "message", "close"], {
75
- description: "Operation: 'start' runs a subagent, 'list' shows subagents, 'cancel' stops a background subagent, 'message' sends a follow-up to a running subagent (one-shot subagents are auto-upgraded to conversation mode on first message), 'close' ends a running subagent (conversation-mode or one-shot).",
76
- }),
77
- // ── action:"start" fields (flattened to top level). task/slug REQUIRED for start. ──
78
- // Missing/empty task or slug throws at runtime (startHandler).
79
- // (flat JSON Schema can't express conditional requirement — see file-level TODO.)
80
- task: Type.Optional(Type.String({
81
- description: "REQUIRED for action:'start'. The task for the subagent to execute. Throws if missing or whitespace-only.",
82
- })),
83
- slug: Type.Optional(Type.String({
84
- description:
85
- "REQUIRED for action:'start'. Short label (≤35 chars) for this subagent, e.g. 'fix-login', 'extract-urls'. " +
86
- "Shown in TUI to distinguish concurrent subagents.",
87
- maxLength: SLUG_MAX_LENGTH,
88
- })),
89
- agent: Type.Optional(Type.String({
90
- description: 'Agent ref: absolute path to the agent .md file (use <location> from <available_subagents>). If omitted, defaults to "general-purpose" — a generic agent that inherits the main agent\'s model and project context. Do not invent names — only use paths from the injected list.',
91
- })),
92
- model: Type.Optional(Type.String({
93
- description: 'Model override in "provider/modelId" format. Resolution order (top wins): (1) this param, (2) agent .md frontmatter model, (3) the main agent\'s current model (zero-config default). An explicit model (param or frontmatter) that is missing or unauthorized THROWS — there is no silent fallback to the main model. Omit this param to inherit the main model.',
94
- })),
95
- thinkingLevel: Type.Optional(StringEnum(THINKING_ORDER, {
96
- description: "Thinking depth override (derived from THINKING_ORDER SSOT, includes 'max'). Omit to default to the model's highest available level (not the main agent's level).",
97
- })),
98
- skillPath: Type.Optional(Type.String()),
99
- appendSystemPrompt: Type.Optional(Type.Array(Type.String())),
100
- schema: Type.Optional(Type.Record(Type.String(), Type.Unknown())),
101
- maxTurns: Type.Optional(Type.Number({
102
- description: "Turn limit. The subagent is terminated via SIGTERM after maxTurns turn_end events + graceTurns of slack. There is no graceful wrap-up message — the process is killed. 0 or omitted = unlimited.",
103
- })),
104
- graceTurns: Type.Optional(Type.Number({
105
- description: "Extra turns allowed after maxTurns is reached before SIGTERM (default 2). Only meaningful when maxTurns is set.",
106
- })),
107
- fork: Type.Optional(Type.Boolean({
108
- description: "Fork mode: inherit the parent's conversation context. When true, the subagent receives the parent's session file via --fork and builds a branched conversation (it sees prior turns/messages). The subagent still runs in a separate spawned child process (process isolation) — fork is about context inheritance, not process sharing; independent of worktree (file-system isolation, see worktree param). When to use: only when the task extends from the parent and genuinely needs key information from the parent's conversation history that a self-contained task prompt cannot carry — most tasks a plain prompt can describe do NOT need fork, so keep false by default and enable only when the user explicitly asks or the task truly depends on seeing prior turns. Caveat: fork drags in the parent's dispatch records and unrelated task context, polluting the subagent (it cannot tell 'context meant for me' from 'parent dispatching me'); when state lives in an external store the subagent can query (e.g., cw handoff), prefer that over fork.",
109
- })),
110
- worktree: Type.Optional(Type.Boolean({
111
- description: "Worktree isolation: run the subagent in a dedicated git worktree, providing file-system level isolation from the parent session (prevents concurrent file-write conflicts). Independent of fork — worktree may be combined with fork:false (file isolation does not require context inheritance). When to use: parallel development scenarios where multiple agents write files concurrently and need isolated working directories (each gets its own checkout; merge later); leave false for single-agent or read-only tasks.",
112
- })),
113
- cwd: Type.Optional(Type.String({
114
- description: 'Override the working directory for the subagent execution. Must be an absolute path. Defaults to the parent session\'s cwd.',
115
- })),
116
- conversation: Type.Optional(Type.Boolean({
117
- description:
118
- "Enable continuous chat with this subagent. When true, the subagent stays available after each reply — you can send follow-up messages (action:'message') and it keeps the full conversation context across rounds, with no need to re-spawn or re-explain. " +
119
- "\nUse conversation:true for: multi-round collaboration (iterative review-fix loops, back-and-forth refinement), any task where you expect to send follow-up messages after the initial result. " +
120
- "\nOmit (or false) for: one-shot tasks — single exploration, lookup, file read, code generation that needs no follow-up. The subagent runs once, notifies on completion, and is cleaned up automatically (default). " +
121
- "\nFor long-interval collaboration (each round spaced >5min apart), set conversation:true AND increase idleTimeoutMs to avoid premature timeout. " +
122
- "Cost: a conversation-mode subagent holds resources (memory, and a worktree if enabled) until you explicitly end it with action:'close'. Always close when done.",
123
- })),
124
- idleTimeoutMs: Type.Optional(Type.Number({
125
- description:
126
- "Idle timeout in milliseconds for conversation-mode subagents. Controls how long an idle subagent (between rounds) stays alive before automatic cleanup. " +
127
- "Default: 300000 (5min). Override for long-interval collaboration where each round is spaced >5min apart. " +
128
- "Only meaningful with conversation:true; ignored for one-shot subagents.",
129
- })),
130
- engine: Type.Optional(StringEnum(["pi", "zcode"], {
131
- description:
132
- "Execution engine for this subagent. Omit to inherit the global config. " +
133
- "Three-layer priority: this parameter > agent .md frontmatter engine > config.json defaultEngine. " +
134
- "Non-pi engines do not support conversation/fork/worktree (rejected before the subagent is created).",
135
- })),
136
- // action:"list" → listParam OPTIONAL (all fields optional, defaults apply). Ignored by other actions.
137
- listParam: Type.Optional(Type.Object({
138
- includeFinished: Type.Optional(Type.Boolean({
139
- description: "Include finished (done/failed/cancelled) records. Default false (running only).",
140
- })),
141
- limit: Type.Optional(Type.Number({
142
- description: "Max items to return. Default 20, clamped to [1, 100].",
143
- })),
144
- })),
145
- // action:"cancel" → cancelParam.subagentId REQUIRED. Throws if missing. Ignored by other actions.
146
- cancelParam: Type.Optional(Type.Object({
147
- subagentId: Type.String({
148
- description: "REQUIRED for action:'cancel'. The subagentId to cancel. Throws if missing. Only background subagents can be cancelled.",
149
- }),
150
- })),
151
- // action:"message" → messageParam.subagentId + text REQUIRED. Any RUNNING subagent works —
152
- // one-shot subagents are auto-upgraded to conversation mode on first message (SP-5); ended ones throw.
153
- messageParam: Type.Optional(Type.Object({
154
- subagentId: Type.String({
155
- description: "REQUIRED for action:'message'. The subagentId to message (any running subagent; a one-shot subagent is auto-upgraded to conversation mode on first message, so you may also message one-shot subagents that are still running).",
156
- }),
157
- text: Type.String({
158
- description: "REQUIRED for action:'message'. The message to send. Whitespace-only throws.",
159
- }),
160
- interrupt: Type.Optional(Type.Boolean({
161
- description: "If true, interrupt the subagent's current work immediately (in-progress output stops, it switches to your new message). If false (default), the message is queued and processed after the current round completes. When the subagent is idle (between rounds), interrupt has no effect — the message always starts a new round.",
162
- })),
163
- })),
164
- // action:"close" → closeParam.subagentId REQUIRED. Ends a running subagent (conversation-mode
165
- // or one-shot — closeSubagent behavior split covers both).
166
- closeParam: Type.Optional(Type.Object({
167
- subagentId: Type.String({
168
- description: "REQUIRED for action:'close'. The subagentId to close (any running subagent, conversation-mode or one-shot).",
169
- }),
170
- force: Type.Optional(Type.Boolean({
171
- description: "If true, terminate immediately even if mid-round (in-progress work is lost). If false (default), let the current round finish, then close. When idle, the subagent closes immediately regardless.",
172
- })),
173
- })),
174
- });
175
-
176
57
  // ============================================================
177
58
  // renderCall 预解析 helper
178
59
  // ============================================================
60
+ //
61
+ // Params schema(SubagentParams)定义在 ./subagent-tool-schema.ts 纯常量叶子:
62
+ // subagent-tool 依赖树沉重,structured-output 侧跨包契约测试需要零依赖 import
63
+ // schema 常量经真实 typebox 编译校验(SW 自身 vitest 把 typebox alias 到 mock,
64
+ // 丢 options——required/description 断言必须以真实构造为基准)。
179
65
 
180
66
  // extractAgentName 已上移到 ../tui/format.ts 共享(tool-render / subagent-tool 复用)。
181
67
 
@@ -185,13 +71,14 @@ function assertNever(value: never): string {
185
71
  }
186
72
 
187
73
  /** Subagent action 字面量联合(与 parameters schema 的 StringEnum 取值一致)。 */
188
- type SubagentAction = "start" | "list" | "cancel" | "message" | "close";
74
+ type SubagentAction = "start" | "list" | "cancel" | "message" | "close" | "fork-from";
189
75
 
190
76
  /** 类型守卫:把 schema 投影出的 string 形式 action 收窄回字面量联合。
191
77
  * typebox v1 的 StringEnum Static 退化为 string,需运行时校验 + 类型收窄
192
78
  * 才能恢复 switch 的 exhaustiveness 约束。 */
193
79
  function isSubagentAction(value: string): value is SubagentAction {
194
- return value === "start" || value === "list" || value === "cancel" || value === "message" || value === "close";
80
+ return value === "start" || value === "list" || value === "cancel" || value === "message"
81
+ || value === "close" || value === "fork-from";
195
82
  }
196
83
 
197
84
  /** unknown 是否为含 model/thinkingLevel 的对象(类型守卫,替代全可选结构 `as`)。 */
@@ -199,6 +86,47 @@ function isModelOverrideObj(a: unknown): a is { model?: unknown; thinkingLevel?:
199
86
  return typeof a === "object" && a !== null;
200
87
  }
201
88
 
89
+ /**
90
+ * start 路径类参数(skillPath / cwd)运行时守卫:绝对路径 + 禁 `..` 穿越。
91
+ *
92
+ * 校验链事实(pi 0.84.1 实装,登记 PS-20):pi agent-loop 对注册 typebox schema
93
+ * 有运行时强校验——agent-loop.js:403-404 在 beforeToolCall / execute 之前调
94
+ * validateToolArguments(pi-ai validation.js:247:Value.Convert :249 + Compile :210
95
+ * + Check :265,失败 throw `Validation failed for tool` :272-273)→ catch 走
96
+ * immediate error(agent-loop.js:445-451),execute 不被调用。schema 的
97
+ * pattern(skillPath/cwd `^/`)/ maxLength(slug 35)是运行时强制而非仅模型可见
98
+ * 契约;tool-definition-wrapper.js:11 只原样透传 params,校验发生在上游 agent-loop 层。
99
+ *
100
+ * 工具层守卫定位 = defense-in-depth + schema 表达力缺口,非「pi 无校验」:
101
+ * - action 条件必填(task/slug 仅 action=start 必填)flat JSON Schema 表达不了,
102
+ * 只能在 startHandler 运行时校验
103
+ * - `..` 穿越段拒绝超出 pattern 能力(`^/` 放行 "/a/../b"),穿越语义只能在
104
+ * 工具层判——与 slug maxLength 双闸同理(schema 强制之上再叠 handler 兜底)
105
+ *
106
+ * 规则:
107
+ * - 绝对路径(isAbsolute;`~` 缩写不是绝对路径,拒绝并指引展开后重试——
108
+ * 下游 session-runner 把该值原样拼进 `--skill <path>` / spawn cwd,不展开 `~`)
109
+ * - 任意 `..` 路径段拒绝(按 /[\\/] 分段判断而非子串——"a..b" 不是穿越):
110
+ * 相对穿越让子进程读到意图外的目录
111
+ *
112
+ * 校验失败 immediate throw(与 action 枚举守卫同风格):pi 只对 execute throw 置
113
+ * isError:true,错误文案原样进 toolResult。
114
+ */
115
+ function assertSafeStartPath(value: string, param: "skillPath" | "cwd"): void {
116
+ if (value.split(/[\\/]/).includes("..")) {
117
+ throw new Error(
118
+ `${param} must not contain '..' path segments (got "${value}"). ` +
119
+ `Pass a normalized absolute path — traversal segments are rejected.`,
120
+ );
121
+ }
122
+ if (!isAbsolute(value)) {
123
+ throw new Error(
124
+ `${param} must be an absolute path (got "${value}"). ` +
125
+ `Expand '~' yourself and pass the full path, e.g. "/Users/me/project".`,
126
+ );
127
+ }
128
+ }
129
+
202
130
  /** 从 unknown args 安全提取 model/thinkingLevel override(传给 resolveModel)。
203
131
  * 拍平后 args 已是顶层平铺结构(model/thinkingLevel 直接在 args 上)。 */
204
132
  function extractModelOverride(args: unknown): { model?: string; thinkingLevel?: string } | undefined {
@@ -238,18 +166,20 @@ action:"list" before action:"start" — a reusable running subagent may exist; c
238
166
  - action:"close" — end a running subagent and release its resources. REQUIRED closeParam: { subagentId }. Optional: force (default false; true terminates mid-round immediately). Always close when done.
239
167
  - action:"list" — list subagents. Pass listParam: { includeFinished?, limit? } (all optional). Read an item's sessionFile for full detail.
240
168
  - action:"cancel" — stop a background subagent (legacy verb; for conversation-mode use close). REQUIRED cancelParam: { subagentId }.
169
+ - action:"fork-from" — recovery for subagents disconnected by a session restart/exit: spawns a NEW subagent inheriting the old one's full history via --fork (source read-only, old record untouched). REQUIRED forkFromParam: { sourceSubagentId }. Optional: prompt (continuation instruction; handover frame injected if omitted). Returns { newSubagentId, sourceSessionFile }. Rejected with guidance: cancelled / worktree-bound / still-running sources.
241
170
 
242
171
  ## Examples
243
172
 
244
173
  \`\`\`
245
174
  {"action":"start","task":"<your task>","slug":"<kebab-case>"}
246
- {"action":"start","task":"...","slug":"fix-login","agent":"coder","model":"anthropic/claude-3.5-sonnet","fork":true}
175
+ {"action":"start","task":"...","slug":"fix-login","agent":"/abs/path/coder.md","model":"anthropic/claude-3.5-sonnet","fork":true}
247
176
  {"action":"start","task":"review iteratively","slug":"review","conversation":true}
248
177
  {"action":"message","messageParam":{"subagentId":"sa-550e8400","text":"now also handle the empty-list case"}}
249
178
  {"action":"message","messageParam":{"subagentId":"sa-550e8400","text":"stop, switch direction to X","interrupt":true}}
250
179
  {"action":"close","closeParam":{"subagentId":"sa-550e8400"}}
251
180
  {"action":"list","listParam":{"includeFinished":false,"limit":20}}
252
181
  {"action":"cancel","cancelParam":{"subagentId":"sa-550e8400"}}
182
+ {"action":"fork-from","forkFromParam":{"sourceSubagentId":"sa-550e8400","prompt":"continue from where it stopped; verify tests first"}}
253
183
  \`\`\`
254
184
 
255
185
  ## After launching — do NOT wait
@@ -381,6 +311,10 @@ const executeSubagent: SubagentExecuteCb = async (
381
311
  }
382
312
  switch (params.action) {
383
313
  case "start":
314
+ // 路径类参数守卫(三通道对称审查 + MF-13):skillPath/cwd 在进入 handler 前
315
+ // immediate throw,不产生半启动 record(与 action 枚举守卫同风格)。
316
+ if (params.skillPath !== undefined) assertSafeStartPath(params.skillPath, "skillPath");
317
+ if (params.cwd !== undefined) assertSafeStartPath(params.cwd, "cwd");
384
318
  // 拍平后直接传顶层 params(StartHandlerInput 是 SubagentExecuteParams 子集,
385
319
  // action/listParam/cancelParam 被忽略;task/slug 必填性由 startHandler 校验)。
386
320
  return adapter({ action: "start", domain: await startHandler(service, params, signal, _ctx?.model) }, toGuiCtx(_ctx));
@@ -392,6 +326,8 @@ const executeSubagent: SubagentExecuteCb = async (
392
326
  return adapter({ action: "message", domain: await messageHandler(service, params.messageParam) }, toGuiCtx(_ctx));
393
327
  case "close":
394
328
  return adapter({ action: "close", domain: await closeHandler(service, params.closeParam) }, toGuiCtx(_ctx));
329
+ case "fork-from":
330
+ return adapter({ action: "fork-from", domain: await forkFromHandler(service, params.forkFromParam) }, toGuiCtx(_ctx));
395
331
  default:
396
332
  // assertNever:让 exhaustiveness 成为承重约束——新增 action 时 tsc 报错,
397
333
  // 而非悄悄落入此分支。
@@ -9,9 +9,9 @@
9
9
 
10
10
  import type { ExtensionAPI, ExtensionCommandContext } from "@earendil-works/pi-coding-agent";
11
11
 
12
- import { getSubagentService } from "../execution/subagent-service.ts";
13
- import type { SubagentService } from "../execution/subagent-service.ts";
14
- import { displayAgentName } from "../shared/agent-ref.ts";
12
+ import { getSubagentService } from "@zhushanwen/subagent-core/execution/subagent-service.ts";
13
+ import type { SubagentService } from "@zhushanwen/subagent-core/execution/subagent-service.ts";
14
+ import { displayAgentName } from "@zhushanwen/subagent-core/shared/agent-ref.ts";
15
15
  import { messageHandler, startHandler } from "./subagent-actions.ts";
16
16
  import { parseSubagentRpcCommand } from "./command-actions.ts";
17
17
  import type { SubagentRpcAction } from "./command-actions.ts";
@@ -45,7 +45,7 @@ export interface SubagentDirectiveDetails {
45
45
  * 定向消息注入正在运行的主 agent LLM turn,违反「不经主 agent LLM 直达 subagent」。
46
46
  * 故按调用时刻的权威 streaming 状态(ctx.isIdle(),与 sendCustomMessage 内部
47
47
  * isStreaming 判据精确互补,含 agent_end 后 retry/continuation 窗口)分流:
48
- * - streaming(isMainAgentIdle=false):传 { deliverAs: "nextTurn" }——消息入
48
+ * - streaming(isMainAgentIdle=false):传 { deliverAs: "nextTurn" }——消息入(g4-allow: 交互注入——GUI 定向消息留痕分流,非结果语义通知)
49
49
  * pi 内存 _pendingNextTurnMessages 队列,下个 turn 注入主 agent 上下文;不打断、
50
50
  * 不 steer 当前 turn。注意:该队列不落 entry,留痕延迟到下个 turn
51
51
  * - 非 streaming(isMainAgentIdle=true):不传 options——立即 append entry 留痕
@@ -66,7 +66,7 @@ function emitSubagentDirective(
66
66
  display: false,
67
67
  details,
68
68
  },
69
- isMainAgentIdle ? undefined : { deliverAs: "nextTurn" },
69
+ isMainAgentIdle ? undefined : { deliverAs: "nextTurn" }, // g4-allow: 交互注入——/subagents GUI 定向消息留痕,非结果语义(C-ext-19 禁令边界,见 emitSubagentDirective JSDoc)
70
70
  );
71
71
  }
72
72
 
@@ -24,8 +24,8 @@ import type { AgentToolResult, Theme } from "@earendil-works/pi-coding-agent";
24
24
  import type {
25
25
  ListResponse,
26
26
  SubagentToolResult,
27
- } from "../execution/types.ts";
28
- import { displayAgentName } from "../shared/agent-ref.ts";
27
+ } from "@zhushanwen/subagent-core/execution/types.ts";
28
+ import { displayAgentName } from "@zhushanwen/subagent-core/shared/agent-ref.ts";
29
29
  import {
30
30
  extractAgentName,
31
31
  firstLine,
@@ -208,6 +208,15 @@ function buildCompactLines(d: SubagentToolResult, theme: ThemeLike): string[] {
208
208
  width,
209
209
  )];
210
210
  }
211
+ // ── fork-from 分支:接续确认行([v8.5 B])──
212
+ if (d.action === "fork-from" && d.forkFromResponse) {
213
+ const src = shortSessionLabel(d.forkFromResponse.sourceSessionFile);
214
+ return [truncLine(
215
+ `${theme.fg("accent", "⑂")} ${theme.fg("dim", "forked-from ")}${theme.fg("accent", src)}` +
216
+ ` ${theme.fg("dim", "→ new: ")}${theme.fg("accent", d.subagentId ?? "?")}`,
217
+ width,
218
+ )];
219
+ }
211
220
  // ── start 分支:background ──
212
221
  if ("bgResponse" in d) {
213
222
  return [truncLine(
@@ -234,6 +243,16 @@ function buildExpandedLines(d: SubagentToolResult, theme: ThemeLike): string[] {
234
243
  width,
235
244
  )];
236
245
  }
246
+ if (d.action === "fork-from" && d.forkFromResponse) {
247
+ // expanded 与 compact 同形(一次性 block 无细节可展开),另附源文件完整路径行。
248
+ return [
249
+ truncLine(
250
+ `${theme.fg("accent", "⑂")} ${theme.fg("dim", "forked-from ")}${theme.fg("accent", d.forkFromResponse.sourceSessionFile)}` +
251
+ ` ${theme.fg("dim", "→ new: ")}${theme.fg("accent", d.subagentId ?? "?")}`,
252
+ width,
253
+ ),
254
+ ];
255
+ }
237
256
 
238
257
  const lines: string[] = [];
239
258
  // bg 占位 expanded 与 compact 同(一次性 block 无细节可展开)
@@ -261,11 +280,24 @@ function isDetailsStructurallyComplete(d: SubagentToolResult): boolean {
261
280
  return "listResponse" in d;
262
281
  case "cancel":
263
282
  return "cancelResponse" in d;
283
+ case "fork-from":
284
+ // [v8.5 B] 新 action 直接纳入 guard:缺内层分组才 fallback。
285
+ // message/close 维持历史现状(不落此 switch 显式分支,走 extractResultError
286
+ // 回显 content 首行)不变,避免触碰现有渲染回归面——review MF-13 曾引入
287
+ // message/close 显式分支后回退:无对应渲染分支却判「结构完整」会改走
288
+ // generic 无响应渲染,属静默行为变更。
289
+ return "forkFromResponse" in d;
264
290
  default:
265
291
  return false;
266
292
  }
267
293
  }
268
294
 
295
+ /** fork-from 渲染用的源文件短标签(basename;失败时原样返回——渲染不应抛错)。 */
296
+ function shortSessionLabel(file: string): string {
297
+ const idx = file.lastIndexOf("/");
298
+ return idx >= 0 ? file.slice(idx + 1) : file;
299
+ }
300
+
269
301
  /**
270
302
  * 从 tool result 的 content 里提取错误文本。
271
303
  *
@@ -30,12 +30,12 @@ import {
30
30
  guiResult,
31
31
  isGuiCapable,
32
32
  } from "@xyz-agent/extension-protocol";
33
- import type { WorkflowScriptRegistry } from "../orchestration/models/workflow-script-registry.ts";
34
- import { lintScript } from "../orchestration/script-lint.ts";
35
- import { deleteWorkflow, saveWorkflow } from "../orchestration/workflow-files.ts";
33
+ import type { WorkflowScriptRegistry } from "@zhushanwen/subagent-core/orchestration/models/workflow-script-registry.ts";
34
+ import { lintScript } from "@zhushanwen/subagent-core/orchestration/script-lint.ts";
35
+ import { deleteWorkflow, saveWorkflow } from "@zhushanwen/subagent-core/orchestration/workflow-files.ts";
36
36
  import { toGuiCtx } from "./gui-mappers.ts";
37
37
  import { renderTextFallback } from "./views/format.ts";
38
- import { parseResourceMetaDetailed } from "../shared/meta-parser.ts";
38
+ import { parseResourceMetaDetailed } from "@zhushanwen/subagent-core/shared/meta-parser.ts";
39
39
 
40
40
  // ── Parameter schema ─────────────────────────────────────────
41
41
 
@@ -31,12 +31,12 @@ import {
31
31
  } from "@xyz-agent/extension-protocol";
32
32
  import { type Static, Type } from "typebox";
33
33
 
34
- import { SLUG_MAX_LENGTH } from "../execution/execute-options-mapper.ts";
35
- import { THINKING_ORDER } from "../execution/model-resolver.ts";
36
- import type { LauncherDeps } from "../orchestration/launcher.ts";
37
- import { abortRun, runWorkflow } from "../orchestration/lifecycle.ts";
38
- import type { RunStore } from "../orchestration/models/ports.ts";
39
- import type { WorkflowRun } from "../orchestration/models/workflow-run.ts";
34
+ import { SLUG_MAX_LENGTH } from "@zhushanwen/subagent-core/execution/execute-options-mapper.ts";
35
+ import { THINKING_ORDER } from "@zhushanwen/subagent-core/execution/model-resolver.ts";
36
+ import type { LauncherDeps } from "@zhushanwen/subagent-core/orchestration/launcher.ts";
37
+ import { abortRun, runWorkflow } from "@zhushanwen/subagent-core/orchestration/lifecycle.ts";
38
+ import type { RunStore } from "@zhushanwen/subagent-core/orchestration/models/ports.ts";
39
+ import type { WorkflowRun } from "@zhushanwen/subagent-core/orchestration/models/workflow-run.ts";
40
40
  import { mapRunIcon, mapRunStatus, toGuiCtx } from "./gui-mappers.ts";
41
41
  import {
42
42
  acquireReentryGuard,
@@ -33,11 +33,11 @@ import {
33
33
  countAllToolCalls,
34
34
  getAllToolCalls,
35
35
  projectLiveProgress,
36
- } from "../../execution/execution-record.ts";
37
- import type { ExecutionTraceNode } from "../../orchestration/models/types.ts";
38
- import type { WorkflowRun } from "../../orchestration/models/workflow-run.ts";
39
- import { saveWorkflow } from "../../orchestration/workflow-files.ts";
40
- import { displayAgentName } from "../../shared/agent-ref.ts";
36
+ } from "@zhushanwen/subagent-core/execution/execution-record.ts";
37
+ import type { ExecutionTraceNode } from "@zhushanwen/subagent-core/orchestration/models/types.ts";
38
+ import type { WorkflowRun } from "@zhushanwen/subagent-core/orchestration/models/workflow-run.ts";
39
+ import { saveWorkflow } from "@zhushanwen/subagent-core/orchestration/workflow-files.ts";
40
+ import { displayAgentName } from "@zhushanwen/subagent-core/shared/agent-ref.ts";
41
41
  import {
42
42
  BOX_BORDER_CHARS,
43
43
  BUDGET_TOKENS_DIVISOR,
@@ -13,9 +13,9 @@
13
13
  import { describe, it, expect, vi, beforeEach, afterEach } from "vitest";
14
14
 
15
15
  import { computeRenderSignature } from "../WorkflowsView.ts";
16
- import type { ExecutionRecord } from "../../../execution/types.ts";
17
- import type { ExecutionTraceNode, WorkerLogEntry } from "../../../orchestration/models/types.ts";
18
- import type { WorkflowRun } from "../../../orchestration/models/workflow-run.ts";
16
+ import type { ExecutionRecord } from "@zhushanwen/subagent-core/execution/types.ts";
17
+ import type { ExecutionTraceNode, WorkerLogEntry } from "@zhushanwen/subagent-core/orchestration/models/types.ts";
18
+ import type { WorkflowRun } from "@zhushanwen/subagent-core/orchestration/models/workflow-run.ts";
19
19
 
20
20
  // ── Fixtures(duck typing,对齐 detail-content-session-file.test.ts 先例)──
21
21
 
@@ -9,8 +9,8 @@ import { describe, expect, it } from "vitest";
9
9
 
10
10
  import { buildDetailContent } from "../detail-content.ts";
11
11
  import type { ThemeLike } from "../format.ts";
12
- import type { ExecutionTraceNode } from "../../../orchestration/models/types.ts";
13
- import type { WorkflowRun } from "../../../orchestration/models/workflow-run.ts";
12
+ import type { ExecutionTraceNode } from "@zhushanwen/subagent-core/orchestration/models/types.ts";
13
+ import type { WorkflowRun } from "@zhushanwen/subagent-core/orchestration/models/workflow-run.ts";
14
14
 
15
15
  /** plain theme: fg/bold 直接返回原文,无 ANSI 色码——测试断言纯文本。 */
16
16
  const plainTheme: ThemeLike = {
@@ -12,10 +12,10 @@
12
12
 
13
13
  import { Key, matchesKey } from "@earendil-works/pi-tui";
14
14
 
15
- import { getAllToolCalls, projectLiveProgress } from "../../execution/execution-record.ts";
16
- import type { AgentEventLogEntry } from "../../execution/types.ts";
17
- import type { ExecutionTraceNode } from "../../orchestration/models/types.ts";
18
- import type { WorkflowRun } from "../../orchestration/models/workflow-run.ts";
15
+ import { getAllToolCalls, projectLiveProgress } from "@zhushanwen/subagent-core/execution/execution-record.ts";
16
+ import type { AgentEventLogEntry } from "@zhushanwen/subagent-core/execution/types.ts";
17
+ import type { ExecutionTraceNode } from "@zhushanwen/subagent-core/orchestration/models/types.ts";
18
+ import type { WorkflowRun } from "@zhushanwen/subagent-core/orchestration/models/workflow-run.ts";
19
19
  import {
20
20
  BOX_BORDER_CHARS,
21
21
  BUDGET_TOKENS_DIVISOR,
@@ -7,10 +7,10 @@
7
7
 
8
8
  import { truncateToWidth, visibleWidth } from "@earendil-works/pi-tui";
9
9
 
10
- import type { AgentEventLogEntry } from "../../execution/types.ts";
11
- import type { ExecutionTraceNode, ToolCallEntry } from "../../orchestration/models/types.ts";
12
- import type { DoneReason, RunStatus } from "../../orchestration/models/types.ts";
13
- import { displayAgentName } from "../../shared/agent-ref.ts";
10
+ import type { AgentEventLogEntry } from "@zhushanwen/subagent-core/execution/types.ts";
11
+ import type { ExecutionTraceNode, ToolCallEntry } from "@zhushanwen/subagent-core/orchestration/models/types.ts";
12
+ import type { DoneReason, RunStatus } from "@zhushanwen/subagent-core/orchestration/models/types.ts";
13
+ import { displayAgentName } from "@zhushanwen/subagent-core/shared/agent-ref.ts";
14
14
 
15
15
  // ── Constants ─────────────────────────────────────────────────
16
16