@opengsd/gsd-pi 1.2.0-dev.844675c9 → 1.2.0-dev.955e4da0

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 (530) hide show
  1. package/dist/cli-web-branch.d.ts +2 -0
  2. package/dist/cli-web-branch.js +9 -2
  3. package/dist/help-text.js +5 -0
  4. package/dist/resources/.managed-resources-content-hash +1 -1
  5. package/dist/resources/extensions/ask-user-questions.js +78 -23
  6. package/dist/resources/extensions/bg-shell/utilities.js +2 -2
  7. package/dist/resources/extensions/claude-code-cli/models.js +9 -0
  8. package/dist/resources/extensions/claude-code-cli/stream-adapter.js +92 -230
  9. package/dist/resources/extensions/claude-code-cli/turn-assembler.js +224 -0
  10. package/dist/resources/extensions/github-sync/templates.js +3 -3
  11. package/dist/resources/extensions/gsd/artifact-projection.js +14 -0
  12. package/dist/resources/extensions/gsd/auto/loop.js +74 -56
  13. package/dist/resources/extensions/gsd/auto/orchestrator.js +142 -15
  14. package/dist/resources/extensions/gsd/auto/phases.js +34 -4
  15. package/dist/resources/extensions/gsd/auto/run-unit.js +2 -1
  16. package/dist/resources/extensions/gsd/auto/session.js +3 -0
  17. package/dist/resources/extensions/gsd/auto-dashboard.js +16 -4
  18. package/dist/resources/extensions/gsd/auto-dispatch.js +6 -5
  19. package/dist/resources/extensions/gsd/auto-model-selection.js +8 -0
  20. package/dist/resources/extensions/gsd/auto-post-unit.js +12 -9
  21. package/dist/resources/extensions/gsd/auto-prompts.js +81 -8
  22. package/dist/resources/extensions/gsd/auto-recovery.js +48 -49
  23. package/dist/resources/extensions/gsd/auto-runtime-state.js +14 -0
  24. package/dist/resources/extensions/gsd/auto-start.js +20 -36
  25. package/dist/resources/extensions/gsd/auto-timers.js +16 -2
  26. package/dist/resources/extensions/gsd/auto-tool-tracking.js +32 -0
  27. package/dist/resources/extensions/gsd/auto-unit-tool-scope.js +4 -29
  28. package/dist/resources/extensions/gsd/auto-verification.js +7 -7
  29. package/dist/resources/extensions/gsd/auto-worktree-repair.js +10 -2
  30. package/dist/resources/extensions/gsd/auto-worktree.js +34 -289
  31. package/dist/resources/extensions/gsd/auto.js +15 -14
  32. package/dist/resources/extensions/gsd/bootstrap/db-tools.js +28 -37
  33. package/dist/resources/extensions/gsd/bootstrap/dynamic-tools.js +20 -43
  34. package/dist/resources/extensions/gsd/bootstrap/query-tools.js +2 -2
  35. package/dist/resources/extensions/gsd/bootstrap/register-hooks.js +131 -140
  36. package/dist/resources/extensions/gsd/bootstrap/write-gate.js +89 -8
  37. package/dist/resources/extensions/gsd/captures.js +5 -13
  38. package/dist/resources/extensions/gsd/closeout-consistency-gate.js +21 -4
  39. package/dist/resources/extensions/gsd/closeout-recovery.js +3 -2
  40. package/dist/resources/extensions/gsd/codebase-generator.js +8 -4
  41. package/dist/resources/extensions/gsd/commands/catalog.js +6 -62
  42. package/dist/resources/extensions/gsd/commands/handlers/auto.js +3 -0
  43. package/dist/resources/extensions/gsd/commands-handlers.js +20 -0
  44. package/dist/resources/extensions/gsd/commands-inspect.js +4 -8
  45. package/dist/resources/extensions/gsd/commands-maintenance.js +61 -41
  46. package/dist/resources/extensions/gsd/commands-ship.js +2 -2
  47. package/dist/resources/extensions/gsd/commands-verdict.js +12 -2
  48. package/dist/resources/extensions/gsd/db/engine.js +755 -0
  49. package/dist/resources/extensions/gsd/db/queries.js +372 -0
  50. package/dist/resources/extensions/gsd/db/sql-constants.js +11 -0
  51. package/dist/resources/extensions/gsd/db/writers/cascades.js +194 -0
  52. package/dist/resources/extensions/gsd/db/writers/import-restore.js +182 -0
  53. package/dist/resources/extensions/gsd/db/writers/memory.js +149 -0
  54. package/dist/resources/extensions/gsd/db/writers/reconcile.js +458 -0
  55. package/dist/resources/extensions/gsd/db/writers/status.js +70 -0
  56. package/dist/resources/extensions/gsd/db-workspace.js +103 -0
  57. package/dist/resources/extensions/gsd/delegation-policy.js +2 -10
  58. package/dist/resources/extensions/gsd/discussion-handoff.js +218 -0
  59. package/dist/resources/extensions/gsd/docs/preferences-reference.md +9 -0
  60. package/dist/resources/extensions/gsd/doctor-environment.js +8 -10
  61. package/dist/resources/extensions/gsd/doctor-git-checks.js +4 -3
  62. package/dist/resources/extensions/gsd/doctor-runtime-checks.js +9 -2
  63. package/dist/resources/extensions/gsd/doctor.js +16 -9
  64. package/dist/resources/extensions/gsd/error-classifier.js +1 -1
  65. package/dist/resources/extensions/gsd/git-conflict-state.js +16 -1
  66. package/dist/resources/extensions/gsd/git-service.js +1 -0
  67. package/dist/resources/extensions/gsd/gitignore.js +3 -0
  68. package/dist/resources/extensions/gsd/gsd-db.js +183 -2048
  69. package/dist/resources/extensions/gsd/guided-flow.js +68 -471
  70. package/dist/resources/extensions/gsd/guided-unit-completion.js +225 -0
  71. package/dist/resources/extensions/gsd/markdown-renderer.js +2 -1
  72. package/dist/resources/extensions/gsd/mcp-filter.js +2 -1
  73. package/dist/resources/extensions/gsd/mcp-tool-name.js +26 -0
  74. package/dist/resources/extensions/gsd/md-importer.js +4 -3
  75. package/dist/resources/extensions/gsd/migrate/safety.js +19 -11
  76. package/dist/resources/extensions/gsd/migration-auto-check.js +27 -5
  77. package/dist/resources/extensions/gsd/milestone-closeout-proof.js +72 -0
  78. package/dist/resources/extensions/gsd/milestone-closeout.js +12 -4
  79. package/dist/resources/extensions/gsd/milestone-merge-transaction.js +10 -0
  80. package/dist/resources/extensions/gsd/milestone-planning-persistence.js +156 -0
  81. package/dist/resources/extensions/gsd/milestone-readiness.js +77 -0
  82. package/dist/resources/extensions/gsd/milestone-settlement.js +50 -0
  83. package/dist/resources/extensions/gsd/milestone-validation-evidence.js +73 -0
  84. package/dist/resources/extensions/gsd/milestone-validation-verdict.js +57 -0
  85. package/dist/resources/extensions/gsd/model-cost-table.js +1 -0
  86. package/dist/resources/extensions/gsd/model-router.js +3 -0
  87. package/dist/resources/extensions/gsd/parallel-eligibility.js +3 -6
  88. package/dist/resources/extensions/gsd/parallel-merge.js +14 -11
  89. package/dist/resources/extensions/gsd/parallel-monitor-overlay.js +7 -5
  90. package/dist/resources/extensions/gsd/parallel-orchestrator.js +3 -2
  91. package/dist/resources/extensions/gsd/paths.js +10 -24
  92. package/dist/resources/extensions/gsd/preferences-diagnostics.js +67 -0
  93. package/dist/resources/extensions/gsd/preferences.js +161 -29
  94. package/dist/resources/extensions/gsd/prompts/complete-slice.md +1 -0
  95. package/dist/resources/extensions/gsd/prompts/execute-task.md +2 -0
  96. package/dist/resources/extensions/gsd/prompts/guided-discuss-project.md +3 -1
  97. package/dist/resources/extensions/gsd/prompts/plan-milestone.md +2 -0
  98. package/dist/resources/extensions/gsd/prompts/plan-slice.md +1 -0
  99. package/dist/resources/extensions/gsd/prompts/refine-slice.md +1 -0
  100. package/dist/resources/extensions/gsd/prompts/system.md +1 -1
  101. package/dist/resources/extensions/gsd/provider-payload-policy.js +83 -0
  102. package/dist/resources/extensions/gsd/pull-request-process.js +13 -0
  103. package/dist/resources/extensions/gsd/quality-gate-closure.js +109 -0
  104. package/dist/resources/extensions/gsd/question-transport.js +86 -0
  105. package/dist/resources/extensions/gsd/recovery-classification.js +12 -1
  106. package/dist/resources/extensions/gsd/roadmap-slices.js +8 -2
  107. package/dist/resources/extensions/gsd/safety/evidence-collector.js +37 -4
  108. package/dist/resources/extensions/gsd/safety/evidence-cross-ref.js +7 -2
  109. package/dist/resources/extensions/gsd/safety/file-change-validator.js +10 -0
  110. package/dist/resources/extensions/gsd/slice-parallel-orchestrator.js +3 -2
  111. package/dist/resources/extensions/gsd/state-transition-matrix.js +38 -0
  112. package/dist/resources/extensions/gsd/state.js +13 -5
  113. package/dist/resources/extensions/gsd/status-guards.js +56 -8
  114. package/dist/resources/extensions/gsd/templates/plan.md +7 -0
  115. package/dist/resources/extensions/gsd/templates/project.md +1 -0
  116. package/dist/resources/extensions/gsd/templates/roadmap.md +1 -1
  117. package/dist/resources/extensions/gsd/templates/uat.md +5 -1
  118. package/dist/resources/extensions/gsd/tool-contract.js +52 -8
  119. package/dist/resources/extensions/gsd/tool-presentation-plan.js +15 -34
  120. package/dist/resources/extensions/gsd/tool-surface-snapshot.js +17 -0
  121. package/dist/resources/extensions/gsd/tools/complete-slice.js +24 -43
  122. package/dist/resources/extensions/gsd/tools/exec-tool.js +5 -5
  123. package/dist/resources/extensions/gsd/tools/plan-milestone.js +15 -143
  124. package/dist/resources/extensions/gsd/tools/reassess-roadmap.js +39 -0
  125. package/dist/resources/extensions/gsd/tools/reopen-milestone.js +11 -29
  126. package/dist/resources/extensions/gsd/tools/reopen-slice.js +14 -33
  127. package/dist/resources/extensions/gsd/tools/skip-slice.js +18 -36
  128. package/dist/resources/extensions/gsd/tools/validate-milestone.js +15 -78
  129. package/dist/resources/extensions/gsd/uat-policy.js +16 -10
  130. package/dist/resources/extensions/gsd/uat-run.js +9 -14
  131. package/dist/resources/extensions/gsd/undo.js +8 -7
  132. package/dist/resources/extensions/gsd/unit-context-composer.js +40 -20
  133. package/dist/resources/extensions/gsd/unit-runtime.js +3 -2
  134. package/dist/resources/extensions/gsd/unit-tool-contracts.js +2 -1
  135. package/dist/resources/extensions/gsd/user-input-boundary.js +23 -0
  136. package/dist/resources/extensions/gsd/validation-block-guard.js +2 -0
  137. package/dist/resources/extensions/gsd/web-app-uat.js +80 -0
  138. package/dist/resources/extensions/gsd/workflow-mcp.js +15 -102
  139. package/dist/resources/extensions/gsd/workflow-reconcile.js +4 -3
  140. package/dist/resources/extensions/gsd/workflow-tool-surface.js +46 -0
  141. package/dist/resources/extensions/gsd/workspace-git-guard.js +2 -0
  142. package/dist/resources/extensions/gsd/worktree-git-recovery.js +287 -0
  143. package/dist/resources/extensions/gsd/worktree-lifecycle.js +9 -1
  144. package/dist/resources/extensions/gsd/worktree-manager.js +45 -28
  145. package/dist/resources/extensions/gsd/worktree-placement.js +59 -0
  146. package/dist/resources/extensions/gsd/worktree-reentry.js +12 -8
  147. package/dist/resources/extensions/gsd/worktree-root.js +17 -6
  148. package/dist/resources/extensions/gsd/worktree-safety.js +8 -5
  149. package/dist/resources/extensions/gsd/worktree-session-state.js +12 -10
  150. package/dist/resources/extensions/gsd/worktree-state-projection.js +33 -4
  151. package/dist/resources/extensions/gsd/worktree-telemetry.js +12 -0
  152. package/dist/resources/extensions/shared/interview-ui.js +2 -2
  153. package/dist/resources/shared/claude-runtime-floor.js +182 -0
  154. package/dist/resources/skills/gsd-browser/SKILL.md +1 -1
  155. package/dist/tsconfig.extensions.tsbuildinfo +1 -1
  156. package/dist/update-cmd.js +20 -0
  157. package/dist/web/standalone/.next/BUILD_ID +1 -1
  158. package/dist/web/standalone/.next/app-path-routes-manifest.json +12 -12
  159. package/dist/web/standalone/.next/build-manifest.json +3 -3
  160. package/dist/web/standalone/.next/prerender-manifest.json +3 -3
  161. package/dist/web/standalone/.next/react-loadable-manifest.json +8 -8
  162. package/dist/web/standalone/.next/server/app/_global-error.html +1 -1
  163. package/dist/web/standalone/.next/server/app/_global-error.rsc +1 -1
  164. package/dist/web/standalone/.next/server/app/_global-error.segments/_full.segment.rsc +1 -1
  165. package/dist/web/standalone/.next/server/app/_global-error.segments/_global-error/__PAGE__.segment.rsc +1 -1
  166. package/dist/web/standalone/.next/server/app/_global-error.segments/_global-error.segment.rsc +1 -1
  167. package/dist/web/standalone/.next/server/app/_global-error.segments/_head.segment.rsc +1 -1
  168. package/dist/web/standalone/.next/server/app/_global-error.segments/_index.segment.rsc +1 -1
  169. package/dist/web/standalone/.next/server/app/_global-error.segments/_tree.segment.rsc +1 -1
  170. package/dist/web/standalone/.next/server/app/_not-found.html +1 -1
  171. package/dist/web/standalone/.next/server/app/_not-found.rsc +1 -1
  172. package/dist/web/standalone/.next/server/app/_not-found.segments/_full.segment.rsc +1 -1
  173. package/dist/web/standalone/.next/server/app/_not-found.segments/_head.segment.rsc +1 -1
  174. package/dist/web/standalone/.next/server/app/_not-found.segments/_index.segment.rsc +1 -1
  175. package/dist/web/standalone/.next/server/app/_not-found.segments/_not-found/__PAGE__.segment.rsc +1 -1
  176. package/dist/web/standalone/.next/server/app/_not-found.segments/_not-found.segment.rsc +1 -1
  177. package/dist/web/standalone/.next/server/app/_not-found.segments/_tree.segment.rsc +1 -1
  178. package/dist/web/standalone/.next/server/app/api/boot/route.js.nft.json +1 -1
  179. package/dist/web/standalone/.next/server/app/api/bridge-terminal/input/route.js.nft.json +1 -1
  180. package/dist/web/standalone/.next/server/app/api/bridge-terminal/resize/route.js.nft.json +1 -1
  181. package/dist/web/standalone/.next/server/app/api/bridge-terminal/stream/route.js.nft.json +1 -1
  182. package/dist/web/standalone/.next/server/app/api/captures/route.js.nft.json +1 -1
  183. package/dist/web/standalone/.next/server/app/api/cleanup/route.js.nft.json +1 -1
  184. package/dist/web/standalone/.next/server/app/api/doctor/route.js.nft.json +1 -1
  185. package/dist/web/standalone/.next/server/app/api/export-data/route.js.nft.json +1 -1
  186. package/dist/web/standalone/.next/server/app/api/files/route.js.nft.json +1 -1
  187. package/dist/web/standalone/.next/server/app/api/forensics/route.js.nft.json +1 -1
  188. package/dist/web/standalone/.next/server/app/api/git/route.js.nft.json +1 -1
  189. package/dist/web/standalone/.next/server/app/api/history/route.js.nft.json +1 -1
  190. package/dist/web/standalone/.next/server/app/api/hooks/route.js.nft.json +1 -1
  191. package/dist/web/standalone/.next/server/app/api/inspect/route.js.nft.json +1 -1
  192. package/dist/web/standalone/.next/server/app/api/knowledge/route.js.nft.json +1 -1
  193. package/dist/web/standalone/.next/server/app/api/live-state/route.js.nft.json +1 -1
  194. package/dist/web/standalone/.next/server/app/api/mcp-connections/route.js.nft.json +1 -1
  195. package/dist/web/standalone/.next/server/app/api/notifications/route.js.nft.json +1 -1
  196. package/dist/web/standalone/.next/server/app/api/onboarding/route.js.nft.json +1 -1
  197. package/dist/web/standalone/.next/server/app/api/projects/route.js.nft.json +1 -1
  198. package/dist/web/standalone/.next/server/app/api/recovery/route.js.nft.json +1 -1
  199. package/dist/web/standalone/.next/server/app/api/session/browser/route.js.nft.json +1 -1
  200. package/dist/web/standalone/.next/server/app/api/session/command/route.js.nft.json +1 -1
  201. package/dist/web/standalone/.next/server/app/api/session/events/route.js.nft.json +1 -1
  202. package/dist/web/standalone/.next/server/app/api/session/manage/route.js.nft.json +1 -1
  203. package/dist/web/standalone/.next/server/app/api/settings-data/route.js.nft.json +1 -1
  204. package/dist/web/standalone/.next/server/app/api/shutdown/route.js.nft.json +1 -1
  205. package/dist/web/standalone/.next/server/app/api/skill-health/route.js.nft.json +1 -1
  206. package/dist/web/standalone/.next/server/app/api/steer/route.js.nft.json +1 -1
  207. package/dist/web/standalone/.next/server/app/api/switch-root/route.js.nft.json +1 -1
  208. package/dist/web/standalone/.next/server/app/api/terminal/sessions/route.js.nft.json +1 -1
  209. package/dist/web/standalone/.next/server/app/api/terminal/stream/route.js.nft.json +1 -1
  210. package/dist/web/standalone/.next/server/app/api/undo/route.js.nft.json +1 -1
  211. package/dist/web/standalone/.next/server/app/api/visualizer/route.js.nft.json +1 -1
  212. package/dist/web/standalone/.next/server/app/index.html +1 -1
  213. package/dist/web/standalone/.next/server/app/index.rsc +1 -1
  214. package/dist/web/standalone/.next/server/app/index.segments/__PAGE__.segment.rsc +1 -1
  215. package/dist/web/standalone/.next/server/app/index.segments/_full.segment.rsc +1 -1
  216. package/dist/web/standalone/.next/server/app/index.segments/_head.segment.rsc +1 -1
  217. package/dist/web/standalone/.next/server/app/index.segments/_index.segment.rsc +1 -1
  218. package/dist/web/standalone/.next/server/app/index.segments/_tree.segment.rsc +1 -1
  219. package/dist/web/standalone/.next/server/app-paths-manifest.json +12 -12
  220. package/dist/web/standalone/.next/server/chunks/{5047.js → 5942.js} +2 -2
  221. package/dist/web/standalone/.next/server/chunks/8357.js +1 -1
  222. package/dist/web/standalone/.next/server/middleware-build-manifest.js +1 -1
  223. package/dist/web/standalone/.next/server/middleware-react-loadable-manifest.js +1 -1
  224. package/dist/web/standalone/.next/server/pages/404.html +1 -1
  225. package/dist/web/standalone/.next/server/pages/500.html +1 -1
  226. package/dist/web/standalone/.next/server/server-reference-manifest.json +1 -1
  227. package/dist/web/standalone/.next/static/chunks/2659.b7b129ee6a769448.js +1 -0
  228. package/dist/web/standalone/.next/static/chunks/2772.bfa657f49f955239.js +1 -0
  229. package/dist/web/standalone/.next/static/chunks/{3616.4113d484a994e411.js → 3616.3c60753b8ffcbd2e.js} +1 -1
  230. package/dist/web/standalone/.next/static/chunks/4283.e4873b058df143a1.js +2 -0
  231. package/dist/web/standalone/.next/static/chunks/5826.a46ecdd1cfe8dabc.js +1 -0
  232. package/dist/web/standalone/.next/static/chunks/796.cf859a427a2cb2ac.js +10 -0
  233. package/dist/web/standalone/.next/static/chunks/8785.2e5a118797fb2dd2.js +1 -0
  234. package/dist/web/standalone/.next/static/chunks/{webpack-dda80a1ef5587410.js → webpack-fbea77b5f9953368.js} +1 -1
  235. package/dist/web/standalone/node_modules/node-pty/build/Makefile +1 -1
  236. package/dist/web-mode.d.ts +2 -0
  237. package/dist/web-mode.js +20 -8
  238. package/dist/worktree-status-banner.js +7 -3
  239. package/package.json +2 -1
  240. package/packages/cloud-mcp-gateway/package.json +2 -2
  241. package/packages/contracts/package.json +1 -1
  242. package/packages/daemon/package.json +4 -4
  243. package/packages/gsd-agent-core/dist/session/agent-session-extensions.d.ts +2 -0
  244. package/packages/gsd-agent-core/dist/session/agent-session-extensions.d.ts.map +1 -1
  245. package/packages/gsd-agent-core/dist/session/agent-session-extensions.js +14 -0
  246. package/packages/gsd-agent-core/dist/session/agent-session-extensions.js.map +1 -1
  247. package/packages/gsd-agent-core/package.json +5 -5
  248. package/packages/gsd-agent-modes/dist/modes/interactive/components/tool-execution.d.ts.map +1 -1
  249. package/packages/gsd-agent-modes/dist/modes/interactive/components/tool-execution.js +3 -0
  250. package/packages/gsd-agent-modes/dist/modes/interactive/components/tool-execution.js.map +1 -1
  251. package/packages/gsd-agent-modes/dist/modes/interactive/controllers/chat-controller.d.ts.map +1 -1
  252. package/packages/gsd-agent-modes/dist/modes/interactive/controllers/chat-controller.js +106 -40
  253. package/packages/gsd-agent-modes/dist/modes/interactive/controllers/chat-controller.js.map +1 -1
  254. package/packages/gsd-agent-modes/dist/modes/interactive/interactive-extension-widgets.d.ts.map +1 -1
  255. package/packages/gsd-agent-modes/dist/modes/interactive/interactive-extension-widgets.js +6 -0
  256. package/packages/gsd-agent-modes/dist/modes/interactive/interactive-extension-widgets.js.map +1 -1
  257. package/packages/gsd-agent-modes/package.json +7 -7
  258. package/packages/mcp-server/dist/server.d.ts +10 -0
  259. package/packages/mcp-server/dist/server.d.ts.map +1 -1
  260. package/packages/mcp-server/dist/server.js +8 -0
  261. package/packages/mcp-server/dist/server.js.map +1 -1
  262. package/packages/mcp-server/dist/workflow-tools.d.ts +41 -0
  263. package/packages/mcp-server/dist/workflow-tools.d.ts.map +1 -1
  264. package/packages/mcp-server/dist/workflow-tools.js +32 -22
  265. package/packages/mcp-server/dist/workflow-tools.js.map +1 -1
  266. package/packages/mcp-server/package.json +3 -3
  267. package/packages/native/package.json +1 -1
  268. package/packages/pi-agent-core/package.json +1 -1
  269. package/packages/pi-ai/dist/image-models.generated.d.ts +2 -2
  270. package/packages/pi-ai/dist/image-models.generated.js +6 -6
  271. package/packages/pi-ai/dist/image-models.generated.js.map +1 -1
  272. package/packages/pi-ai/dist/models.generated.d.ts +295 -98
  273. package/packages/pi-ai/dist/models.generated.d.ts.map +1 -1
  274. package/packages/pi-ai/dist/models.generated.js +309 -154
  275. package/packages/pi-ai/dist/models.generated.js.map +1 -1
  276. package/packages/pi-ai/package.json +1 -1
  277. package/packages/pi-coding-agent/dist/core/capability-patches.d.ts.map +1 -1
  278. package/packages/pi-coding-agent/dist/core/capability-patches.js +3 -1
  279. package/packages/pi-coding-agent/dist/core/capability-patches.js.map +1 -1
  280. package/packages/pi-coding-agent/package.json +7 -7
  281. package/packages/pi-tui/dist/components/input.js +1 -1
  282. package/packages/pi-tui/dist/components/input.js.map +1 -1
  283. package/packages/pi-tui/dist/keys.d.ts.map +1 -1
  284. package/packages/pi-tui/dist/keys.js +39 -30
  285. package/packages/pi-tui/dist/keys.js.map +1 -1
  286. package/packages/pi-tui/dist/stdin-buffer.d.ts.map +1 -1
  287. package/packages/pi-tui/dist/stdin-buffer.js +22 -0
  288. package/packages/pi-tui/dist/stdin-buffer.js.map +1 -1
  289. package/packages/pi-tui/package.json +2 -2
  290. package/packages/rpc-client/package.json +2 -2
  291. package/pkg/package.json +1 -1
  292. package/src/resources/extensions/ask-user-questions.ts +87 -24
  293. package/src/resources/extensions/bg-shell/utilities.ts +2 -2
  294. package/src/resources/extensions/claude-code-cli/models.ts +9 -0
  295. package/src/resources/extensions/claude-code-cli/stream-adapter.ts +114 -281
  296. package/src/resources/extensions/claude-code-cli/tests/stream-adapter.test.ts +268 -0
  297. package/src/resources/extensions/claude-code-cli/turn-assembler.ts +287 -0
  298. package/src/resources/extensions/github-sync/templates.ts +3 -3
  299. package/src/resources/extensions/github-sync/tests/templates.test.ts +2 -2
  300. package/src/resources/extensions/gsd/artifact-projection.ts +31 -0
  301. package/src/resources/extensions/gsd/auto/contracts.ts +32 -2
  302. package/src/resources/extensions/gsd/auto/loop-deps.ts +3 -1
  303. package/src/resources/extensions/gsd/auto/loop.ts +83 -61
  304. package/src/resources/extensions/gsd/auto/orchestrator.ts +164 -17
  305. package/src/resources/extensions/gsd/auto/phases.ts +45 -4
  306. package/src/resources/extensions/gsd/auto/run-unit.ts +2 -1
  307. package/src/resources/extensions/gsd/auto/session.ts +4 -0
  308. package/src/resources/extensions/gsd/auto-dashboard.ts +18 -4
  309. package/src/resources/extensions/gsd/auto-dispatch.ts +20 -7
  310. package/src/resources/extensions/gsd/auto-model-selection.ts +8 -0
  311. package/src/resources/extensions/gsd/auto-post-unit.ts +16 -8
  312. package/src/resources/extensions/gsd/auto-prompts.ts +107 -9
  313. package/src/resources/extensions/gsd/auto-recovery.ts +50 -50
  314. package/src/resources/extensions/gsd/auto-runtime-state.ts +26 -0
  315. package/src/resources/extensions/gsd/auto-start.ts +25 -34
  316. package/src/resources/extensions/gsd/auto-timers.ts +16 -2
  317. package/src/resources/extensions/gsd/auto-tool-tracking.ts +35 -0
  318. package/src/resources/extensions/gsd/auto-unit-tool-scope.ts +9 -30
  319. package/src/resources/extensions/gsd/auto-verification.ts +7 -8
  320. package/src/resources/extensions/gsd/auto-worktree-repair.ts +13 -2
  321. package/src/resources/extensions/gsd/auto-worktree.ts +53 -306
  322. package/src/resources/extensions/gsd/auto.ts +27 -17
  323. package/src/resources/extensions/gsd/bootstrap/db-tools.ts +29 -37
  324. package/src/resources/extensions/gsd/bootstrap/dynamic-tools.ts +20 -43
  325. package/src/resources/extensions/gsd/bootstrap/query-tools.ts +2 -2
  326. package/src/resources/extensions/gsd/bootstrap/register-hooks.ts +147 -153
  327. package/src/resources/extensions/gsd/bootstrap/write-gate.ts +132 -6
  328. package/src/resources/extensions/gsd/captures.ts +5 -14
  329. package/src/resources/extensions/gsd/closeout-consistency-gate.ts +27 -5
  330. package/src/resources/extensions/gsd/closeout-recovery.ts +2 -1
  331. package/src/resources/extensions/gsd/codebase-generator.ts +9 -5
  332. package/src/resources/extensions/gsd/commands/catalog.ts +6 -68
  333. package/src/resources/extensions/gsd/commands/handlers/auto.ts +3 -0
  334. package/src/resources/extensions/gsd/commands-handlers.ts +18 -0
  335. package/src/resources/extensions/gsd/commands-inspect.ts +7 -8
  336. package/src/resources/extensions/gsd/commands-maintenance.ts +74 -40
  337. package/src/resources/extensions/gsd/commands-ship.ts +2 -2
  338. package/src/resources/extensions/gsd/commands-verdict.ts +19 -2
  339. package/src/resources/extensions/gsd/db/engine.ts +809 -0
  340. package/src/resources/extensions/gsd/db/queries.ts +453 -0
  341. package/src/resources/extensions/gsd/db/sql-constants.ts +12 -0
  342. package/src/resources/extensions/gsd/db/writers/cascades.ts +237 -0
  343. package/src/resources/extensions/gsd/db/writers/import-restore.ts +310 -0
  344. package/src/resources/extensions/gsd/db/writers/memory.ts +220 -0
  345. package/src/resources/extensions/gsd/db/writers/reconcile.ts +500 -0
  346. package/src/resources/extensions/gsd/db/writers/status.ts +88 -0
  347. package/src/resources/extensions/gsd/db-workspace.ts +170 -0
  348. package/src/resources/extensions/gsd/delegation-policy.ts +3 -11
  349. package/src/resources/extensions/gsd/discussion-handoff.ts +276 -0
  350. package/src/resources/extensions/gsd/docs/preferences-reference.md +9 -0
  351. package/src/resources/extensions/gsd/doctor-environment.ts +8 -11
  352. package/src/resources/extensions/gsd/doctor-git-checks.ts +3 -3
  353. package/src/resources/extensions/gsd/doctor-runtime-checks.ts +10 -3
  354. package/src/resources/extensions/gsd/doctor.ts +15 -5
  355. package/src/resources/extensions/gsd/error-classifier.ts +1 -1
  356. package/src/resources/extensions/gsd/git-conflict-state.ts +17 -1
  357. package/src/resources/extensions/gsd/git-service.ts +1 -0
  358. package/src/resources/extensions/gsd/gitignore.ts +3 -0
  359. package/src/resources/extensions/gsd/gsd-db.ts +185 -2373
  360. package/src/resources/extensions/gsd/guided-flow.ts +81 -561
  361. package/src/resources/extensions/gsd/guided-unit-completion.ts +275 -0
  362. package/src/resources/extensions/gsd/markdown-renderer.ts +2 -1
  363. package/src/resources/extensions/gsd/mcp-filter.ts +2 -1
  364. package/src/resources/extensions/gsd/mcp-tool-name.ts +35 -0
  365. package/src/resources/extensions/gsd/md-importer.ts +3 -3
  366. package/src/resources/extensions/gsd/migrate/safety.ts +17 -9
  367. package/src/resources/extensions/gsd/migration-auto-check.ts +30 -5
  368. package/src/resources/extensions/gsd/milestone-closeout-proof.ts +131 -0
  369. package/src/resources/extensions/gsd/milestone-closeout.ts +12 -4
  370. package/src/resources/extensions/gsd/milestone-merge-transaction.ts +47 -0
  371. package/src/resources/extensions/gsd/milestone-planning-persistence.ts +224 -0
  372. package/src/resources/extensions/gsd/milestone-readiness.ts +125 -0
  373. package/src/resources/extensions/gsd/milestone-settlement.ts +81 -0
  374. package/src/resources/extensions/gsd/milestone-validation-evidence.ts +95 -0
  375. package/src/resources/extensions/gsd/milestone-validation-verdict.ts +80 -0
  376. package/src/resources/extensions/gsd/model-cost-table.ts +1 -0
  377. package/src/resources/extensions/gsd/model-router.ts +3 -0
  378. package/src/resources/extensions/gsd/parallel-eligibility.ts +4 -5
  379. package/src/resources/extensions/gsd/parallel-merge.ts +12 -9
  380. package/src/resources/extensions/gsd/parallel-monitor-overlay.ts +6 -5
  381. package/src/resources/extensions/gsd/parallel-orchestrator.ts +6 -2
  382. package/src/resources/extensions/gsd/paths.ts +9 -22
  383. package/src/resources/extensions/gsd/preferences-diagnostics.ts +98 -0
  384. package/src/resources/extensions/gsd/preferences-types.ts +16 -0
  385. package/src/resources/extensions/gsd/preferences.ts +191 -28
  386. package/src/resources/extensions/gsd/prompts/complete-slice.md +1 -0
  387. package/src/resources/extensions/gsd/prompts/execute-task.md +2 -0
  388. package/src/resources/extensions/gsd/prompts/guided-discuss-project.md +3 -1
  389. package/src/resources/extensions/gsd/prompts/plan-milestone.md +2 -0
  390. package/src/resources/extensions/gsd/prompts/plan-slice.md +1 -0
  391. package/src/resources/extensions/gsd/prompts/refine-slice.md +1 -0
  392. package/src/resources/extensions/gsd/prompts/system.md +1 -1
  393. package/src/resources/extensions/gsd/provider-payload-policy.ts +140 -0
  394. package/src/resources/extensions/gsd/pull-request-process.ts +41 -0
  395. package/src/resources/extensions/gsd/quality-gate-closure.ts +140 -0
  396. package/src/resources/extensions/gsd/question-transport.ts +138 -0
  397. package/src/resources/extensions/gsd/recovery-classification.ts +14 -1
  398. package/src/resources/extensions/gsd/roadmap-slices.ts +8 -2
  399. package/src/resources/extensions/gsd/safety/evidence-collector.ts +36 -4
  400. package/src/resources/extensions/gsd/safety/evidence-cross-ref.ts +7 -2
  401. package/src/resources/extensions/gsd/safety/file-change-validator.ts +14 -0
  402. package/src/resources/extensions/gsd/slice-parallel-orchestrator.ts +6 -2
  403. package/src/resources/extensions/gsd/state-transition-matrix.ts +42 -0
  404. package/src/resources/extensions/gsd/state.ts +15 -5
  405. package/src/resources/extensions/gsd/status-guards.ts +59 -8
  406. package/src/resources/extensions/gsd/templates/plan.md +7 -0
  407. package/src/resources/extensions/gsd/templates/project.md +1 -0
  408. package/src/resources/extensions/gsd/templates/roadmap.md +1 -1
  409. package/src/resources/extensions/gsd/templates/uat.md +5 -1
  410. package/src/resources/extensions/gsd/tests/ask-user-questions-render.test.ts +92 -0
  411. package/src/resources/extensions/gsd/tests/auto-dashboard.test.ts +29 -1
  412. package/src/resources/extensions/gsd/tests/auto-loop.test.ts +444 -5
  413. package/src/resources/extensions/gsd/tests/auto-milestone-target.test.ts +23 -0
  414. package/src/resources/extensions/gsd/tests/auto-model-selection-tool-poisoning.test.ts +18 -0
  415. package/src/resources/extensions/gsd/tests/auto-orchestrator.test.ts +133 -4
  416. package/src/resources/extensions/gsd/tests/auto-paused-ui-cleanup.test.ts +3 -1
  417. package/src/resources/extensions/gsd/tests/auto-post-unit-evidence-crossref-4909.test.ts +46 -0
  418. package/src/resources/extensions/gsd/tests/auto-runtime-state.test.ts +34 -0
  419. package/src/resources/extensions/gsd/tests/auto-worktree-registry.test.ts +2 -2
  420. package/src/resources/extensions/gsd/tests/auto-worktree-repair.test.ts +4 -2
  421. package/src/resources/extensions/gsd/tests/canonical-milestone-root.test.ts +20 -0
  422. package/src/resources/extensions/gsd/tests/clear-stale-autostart.test.ts +22 -0
  423. package/src/resources/extensions/gsd/tests/codebase-generator.test.ts +22 -0
  424. package/src/resources/extensions/gsd/tests/commands-dispatcher-workspace-git.test.ts +11 -0
  425. package/src/resources/extensions/gsd/tests/commands-verdict.test.ts +38 -1
  426. package/src/resources/extensions/gsd/tests/dispatch-complete-milestone-guard.test.ts +34 -3
  427. package/src/resources/extensions/gsd/tests/dispatch-run-uat-browser-tools.test.ts +88 -0
  428. package/src/resources/extensions/gsd/tests/doctor-scope-db-unavailable.test.ts +18 -0
  429. package/src/resources/extensions/gsd/tests/evidence-xref-gsd-exec.test.ts +157 -0
  430. package/src/resources/extensions/gsd/tests/execute-task-rendering.test.ts +1 -0
  431. package/src/resources/extensions/gsd/tests/file-change-validator.test.ts +33 -1
  432. package/src/resources/extensions/gsd/tests/fixtures/pr-body/swarm-lane-no-blockers.md +1 -5
  433. package/src/resources/extensions/gsd/tests/fixtures/pr-body/swarm-lane-with-blockers.md +1 -5
  434. package/src/resources/extensions/gsd/tests/gate-state-canonicalization.test.ts +48 -1
  435. package/src/resources/extensions/gsd/tests/integration/auto-worktree-milestone-merge.test.ts +5 -4
  436. package/src/resources/extensions/gsd/tests/integration/auto-worktree.test.ts +1 -1
  437. package/src/resources/extensions/gsd/tests/integration/git-service.test.ts +3 -2
  438. package/src/resources/extensions/gsd/tests/mcp-tool-name.test.ts +34 -0
  439. package/src/resources/extensions/gsd/tests/migration-auto-check.test.ts +143 -1
  440. package/src/resources/extensions/gsd/tests/milestone-closeout-proof.test.ts +99 -0
  441. package/src/resources/extensions/gsd/tests/milestone-closeout.test.ts +25 -0
  442. package/src/resources/extensions/gsd/tests/milestone-merge-transaction.test.ts +46 -0
  443. package/src/resources/extensions/gsd/tests/milestone-readiness.test.ts +65 -0
  444. package/src/resources/extensions/gsd/tests/milestone-validation-evidence.test.ts +41 -0
  445. package/src/resources/extensions/gsd/tests/milestone-validation-verdict.test.ts +55 -0
  446. package/src/resources/extensions/gsd/tests/plan-milestone.test.ts +45 -0
  447. package/src/resources/extensions/gsd/tests/plan-slice-prompt.test.ts +2 -0
  448. package/src/resources/extensions/gsd/tests/planning-crossval.test.ts +45 -0
  449. package/src/resources/extensions/gsd/tests/preferences-diagnostics.test.ts +67 -0
  450. package/src/resources/extensions/gsd/tests/preferences.test.ts +183 -0
  451. package/src/resources/extensions/gsd/tests/prompt-contracts.test.ts +46 -0
  452. package/src/resources/extensions/gsd/tests/provider-errors.test.ts +9 -0
  453. package/src/resources/extensions/gsd/tests/provider-payload-policy.test.ts +165 -0
  454. package/src/resources/extensions/gsd/tests/pull-request-process.test.ts +47 -0
  455. package/src/resources/extensions/gsd/tests/recovery-classification-illegal-transition.test.ts +30 -0
  456. package/src/resources/extensions/gsd/tests/register-hooks-depth-verification.test.ts +185 -1
  457. package/src/resources/extensions/gsd/tests/roadmap-parse-regression.test.ts +40 -0
  458. package/src/resources/extensions/gsd/tests/runtime-invariant-modules.test.ts +25 -1
  459. package/src/resources/extensions/gsd/tests/safety-harness-false-positives.test.ts +38 -0
  460. package/src/resources/extensions/gsd/tests/session-start-footer.test.ts +80 -0
  461. package/src/resources/extensions/gsd/tests/session-switch-clears-pending-autostart.test.ts +108 -0
  462. package/src/resources/extensions/gsd/tests/single-writer-invariant.test.ts +144 -7
  463. package/src/resources/extensions/gsd/tests/stale-queued-milestone.test.ts +27 -0
  464. package/src/resources/extensions/gsd/tests/start-auto-detached.test.ts +2 -1
  465. package/src/resources/extensions/gsd/tests/state-transition-matrix.test.ts +36 -0
  466. package/src/resources/extensions/gsd/tests/status-guards.test.ts +38 -0
  467. package/src/resources/extensions/gsd/tests/tool-availability-audit.test.ts +35 -0
  468. package/src/resources/extensions/gsd/tests/tool-naming.test.ts +35 -42
  469. package/src/resources/extensions/gsd/tests/uat-policy.test.ts +23 -0
  470. package/src/resources/extensions/gsd/tests/unit-context-composer.test.ts +47 -0
  471. package/src/resources/extensions/gsd/tests/user-input-boundary.test.ts +86 -1
  472. package/src/resources/extensions/gsd/tests/validate-milestone-stuck-guard.test.ts +39 -0
  473. package/src/resources/extensions/gsd/tests/web-app-uat.test.ts +150 -0
  474. package/src/resources/extensions/gsd/tests/workflow-mcp.test.ts +126 -9
  475. package/src/resources/extensions/gsd/tests/workspace-git-preflight.test.ts +15 -0
  476. package/src/resources/extensions/gsd/tests/worktree-lifecycle.test.ts +41 -4
  477. package/src/resources/extensions/gsd/tests/worktree-manager.test.ts +43 -1
  478. package/src/resources/extensions/gsd/tests/worktree-placement.test.ts +113 -0
  479. package/src/resources/extensions/gsd/tests/worktree-projection-writers.test.ts +1 -1
  480. package/src/resources/extensions/gsd/tests/worktree-reentry.test.ts +1 -1
  481. package/src/resources/extensions/gsd/tests/worktree-safety.test.ts +3 -1
  482. package/src/resources/extensions/gsd/tests/worktree-symlink-removal.test.ts +12 -6
  483. package/src/resources/extensions/gsd/tests/worktree-teardown-safety.test.ts +2 -2
  484. package/src/resources/extensions/gsd/tests/worktree-telemetry.test.ts +22 -0
  485. package/src/resources/extensions/gsd/tests/write-gate.test.ts +121 -0
  486. package/src/resources/extensions/gsd/tool-contract.ts +86 -8
  487. package/src/resources/extensions/gsd/tool-presentation-plan.ts +16 -33
  488. package/src/resources/extensions/gsd/tool-surface-snapshot.ts +47 -0
  489. package/src/resources/extensions/gsd/tools/complete-slice.ts +23 -58
  490. package/src/resources/extensions/gsd/tools/exec-tool.ts +5 -5
  491. package/src/resources/extensions/gsd/tools/plan-milestone.ts +19 -160
  492. package/src/resources/extensions/gsd/tools/reassess-roadmap.ts +43 -0
  493. package/src/resources/extensions/gsd/tools/reopen-milestone.ts +11 -38
  494. package/src/resources/extensions/gsd/tools/reopen-slice.ts +14 -42
  495. package/src/resources/extensions/gsd/tools/skip-slice.ts +18 -44
  496. package/src/resources/extensions/gsd/tools/validate-milestone.ts +25 -84
  497. package/src/resources/extensions/gsd/uat-policy.ts +19 -10
  498. package/src/resources/extensions/gsd/uat-run.ts +10 -14
  499. package/src/resources/extensions/gsd/undo.ts +9 -8
  500. package/src/resources/extensions/gsd/unit-context-composer.ts +85 -20
  501. package/src/resources/extensions/gsd/unit-runtime.ts +3 -2
  502. package/src/resources/extensions/gsd/unit-tool-contracts.ts +2 -1
  503. package/src/resources/extensions/gsd/user-input-boundary.ts +18 -0
  504. package/src/resources/extensions/gsd/validation-block-guard.ts +2 -0
  505. package/src/resources/extensions/gsd/web-app-uat.ts +101 -0
  506. package/src/resources/extensions/gsd/workflow-mcp.ts +22 -110
  507. package/src/resources/extensions/gsd/workflow-reconcile.ts +3 -3
  508. package/src/resources/extensions/gsd/workflow-tool-surface.ts +73 -0
  509. package/src/resources/extensions/gsd/workspace-git-guard.ts +1 -0
  510. package/src/resources/extensions/gsd/worktree-git-recovery.ts +308 -0
  511. package/src/resources/extensions/gsd/worktree-lifecycle.ts +17 -17
  512. package/src/resources/extensions/gsd/worktree-manager.ts +47 -28
  513. package/src/resources/extensions/gsd/worktree-placement.ts +63 -0
  514. package/src/resources/extensions/gsd/worktree-reentry.ts +10 -7
  515. package/src/resources/extensions/gsd/worktree-root.ts +17 -6
  516. package/src/resources/extensions/gsd/worktree-safety.ts +8 -5
  517. package/src/resources/extensions/gsd/worktree-session-state.ts +12 -10
  518. package/src/resources/extensions/gsd/worktree-state-projection.ts +55 -7
  519. package/src/resources/extensions/gsd/worktree-telemetry.ts +16 -0
  520. package/src/resources/extensions/shared/interview-ui.ts +15 -2
  521. package/src/resources/shared/claude-runtime-floor.ts +248 -0
  522. package/src/resources/skills/gsd-browser/SKILL.md +1 -1
  523. package/dist/web/standalone/.next/static/chunks/2659.feb6499ca863ebfc.js +0 -1
  524. package/dist/web/standalone/.next/static/chunks/2772.151789db0edea835.js +0 -1
  525. package/dist/web/standalone/.next/static/chunks/4283.10a065467b5340d8.js +0 -2
  526. package/dist/web/standalone/.next/static/chunks/5826.960dc4634cc9b0d3.js +0 -1
  527. package/dist/web/standalone/.next/static/chunks/796.46f811c0fac23aab.js +0 -10
  528. package/dist/web/standalone/.next/static/chunks/8785.d32f7a61f55c1600.js +0 -1
  529. /package/dist/web/standalone/.next/static/{Qbr81pQ-pbQXP4bq2VXLv → C24pqUd-aru-l0Dp0gLZP}/_buildManifest.js +0 -0
  530. /package/dist/web/standalone/.next/static/{Qbr81pQ-pbQXP4bq2VXLv → C24pqUd-aru-l0Dp0gLZP}/_ssgManifest.js +0 -0
@@ -3,7 +3,8 @@
3
3
  /**
4
4
  * GSD Worktree Manager
5
5
  *
6
- * Creates and manages git worktrees under .gsd/worktrees/<name>/.
6
+ * Creates and manages git worktrees under .gsd-worktrees/<name>/ (canonical;
7
+ * legacy .gsd/worktrees/<name>/ stays recognized — see worktree-placement.ts).
7
8
  * Each worktree gets its own branch (worktree/<name>) and a full
8
9
  * working copy of the project, enabling parallel work streams.
9
10
  *
@@ -11,7 +12,7 @@
11
12
  * the main branch, then dispatches an LLM-guided merge flow.
12
13
  *
13
14
  * Flow:
14
- * 1. create() — git worktree add .gsd/worktrees/<name> -b worktree/<name>
15
+ * 1. create() — git worktree add .gsd-worktrees/<name> -b worktree/<name>
15
16
  * 2. user works in the worktree (new plans, milestones, etc.)
16
17
  * 3. merge() — LLM-guided reconciliation of .gsd/ artifacts back to main
17
18
  * 4. remove() — git worktree remove + branch cleanup
@@ -24,6 +25,7 @@ import { logWarning } from "./workflow-logger.js";
24
25
  import { nativeBranchList, nativeBranchDelete, nativeBranchExists, nativeBranchForceReset, nativeCommit, nativeDetectMainBranch, nativeDiffContent, nativeDiffNameStatus, nativeDiffNumstat, nativeGetCurrentBranch, nativeIsAncestor, nativeLogOneline, nativeMergeSquash, nativeWorktreeAdd, nativeWorktreeList, nativeWorktreePrune, nativeWorktreeRemove, } from "./native-git-bridge.js";
25
26
  import { emitCanonicalRootRedirect } from "./worktree-telemetry.js";
26
27
  import { isGsdWorktreePath, normalizeWorktreePathForCompare, resolveWorktreeProjectRoot, } from "./worktree-root.js";
28
+ import { canonicalWorktreesDir, worktreePathFor, worktreesDirs } from "./worktree-placement.js";
27
29
  function deleteBranchIfPresent(basePath, branch, warningPrefix) {
28
30
  try {
29
31
  if (!nativeBranchExists(basePath, branch))
@@ -81,30 +83,39 @@ export function resolveGitDir(basePath) {
81
83
  }
82
84
  return gitPath;
83
85
  }
86
+ /** Canonical container for new worktrees. For scans that must also see legacy
87
+ * worktrees, use allWorktreesDirs(). */
84
88
  export function worktreesDir(basePath) {
85
- return join(resolveWorktreeProjectRoot(basePath), ".gsd", "worktrees");
89
+ return canonicalWorktreesDir(resolveWorktreeProjectRoot(basePath));
86
90
  }
91
+ /** Every container a GSD worktree may live in (canonical + legacy), canonical first. */
92
+ export function allWorktreesDirs(basePath) {
93
+ return worktreesDirs(resolveWorktreeProjectRoot(basePath));
94
+ }
95
+ /** Path for worktree `name` — an existing legacy worktree keeps its location. */
87
96
  export function worktreePath(basePath, name) {
88
- return join(worktreesDir(basePath), name);
97
+ return worktreePathFor(resolveWorktreeProjectRoot(basePath), name);
89
98
  }
90
99
  export function worktreeBranchName(name) {
91
100
  return `worktree/${name}`;
92
101
  }
93
102
  /**
94
- * Validate that a path is inside the .gsd/worktrees/ directory.
95
- * Resolves symlinks and normalizes ".." traversals before comparison
96
- * so that a symlink-resolved or crafted path cannot escape containment.
103
+ * Validate that a path is inside a GSD worktrees container (canonical
104
+ * .gsd-worktrees/ or legacy .gsd/worktrees/). Resolves symlinks and
105
+ * normalizes ".." traversals before comparison so that a symlink-resolved
106
+ * or crafted path cannot escape containment.
97
107
  *
98
108
  * Used as a safety gate before any destructive operation (rmSync,
99
109
  * nativeWorktreeRemove --force) to prevent #2365-style data loss.
100
110
  */
101
111
  export function isInsideWorktreesDir(basePath, targetPath) {
102
- const wtDirPath = worktreesDir(basePath);
103
- const wtDir = existsSync(wtDirPath) ? realpathSync(wtDirPath) : resolve(wtDirPath);
104
112
  const resolved = existsSync(targetPath) ? realpathSync(targetPath) : resolve(targetPath);
105
- // The resolved path must start with the worktrees dir followed by a separator,
106
- // not merely be a prefix match (e.g. ".gsd/worktrees-extra" must not match).
107
- return resolved === wtDir || resolved.startsWith(wtDir + sep);
113
+ return allWorktreesDirs(basePath).some((wtDirPath) => {
114
+ const wtDir = existsSync(wtDirPath) ? realpathSync(wtDirPath) : resolve(wtDirPath);
115
+ // The resolved path must start with the worktrees dir followed by a separator,
116
+ // not merely be a prefix match (e.g. ".gsd/worktrees-extra" must not match).
117
+ return resolved === wtDir || resolved.startsWith(wtDir + sep);
118
+ });
108
119
  }
109
120
  function isRegisteredGitWorktreeAtPath(basePath, wtPath) {
110
121
  try {
@@ -200,11 +211,11 @@ export function buildManualValidationGuidance(basePath, milestoneId, opts = {})
200
211
  if (!milestoneId)
201
212
  return null;
202
213
  const validationRoot = resolveCanonicalMilestoneRoot(basePath, milestoneId);
203
- const inWorktree = validationRoot.includes(`${sep}.gsd${sep}worktrees${sep}`);
214
+ const inWorktree = isGsdWorktreePath(validationRoot);
204
215
  const lines = [`Validate the work here: ${validationRoot}`];
205
216
  if (inWorktree) {
206
- lines.push("This milestone runs in a git worktree, so the code lives under the hidden " +
207
- `\`.gsd/worktrees/\` path. Open it with: cd "${validationRoot}"`);
217
+ lines.push("This milestone runs in a git worktree, so the code lives under the " +
218
+ `GSD worktrees directory. Open it with: cd "${validationRoot}"`);
208
219
  }
209
220
  if (opts.uatPath) {
210
221
  lines.push(`Follow the UAT checklist at: ${opts.uatPath}`);
@@ -224,21 +235,29 @@ export function createWorktree(basePath, name, opts = {}) {
224
235
  if (!/^[a-zA-Z0-9_-]+$/.test(name)) {
225
236
  throw new GSDError(GSD_PARSE_ERROR, `Invalid worktree name "${name}". Use only letters, numbers, hyphens, and underscores.`);
226
237
  }
227
- const wtPath = worktreePath(basePath, name);
238
+ const existingPath = worktreePath(basePath, name);
228
239
  const branch = opts.branch ?? worktreeBranchName(name);
229
- if (existsSync(wtPath)) {
240
+ if (existsSync(existingPath)) {
230
241
  // A valid git worktree is registered in `git worktree list` and has a .git
231
242
  // *file* with a gitdir: pointer. Leftover directories (no .git, a standalone
232
243
  // .git directory from accidental `git init`, or an orphan pointer) block
233
244
  // creation unless removed.
234
- if (isRegisteredGitWorktreeAtPath(basePath, wtPath)) {
235
- throw new GSDError(GSD_STALE_STATE, `Worktree "${name}" already exists at ${wtPath}`);
245
+ if (isRegisteredGitWorktreeAtPath(basePath, existingPath)) {
246
+ throw new GSDError(GSD_STALE_STATE, `Worktree "${name}" already exists at ${existingPath}`);
236
247
  }
237
- removeStaleWorktreeDirectory(wtPath, name);
248
+ removeStaleWorktreeDirectory(existingPath, name);
238
249
  }
239
- // Ensure the .gsd/worktrees/ directory exists
250
+ // New worktrees always land in the canonical container, even when a stale
251
+ // legacy directory was just cleaned up.
240
252
  const wtDir = worktreesDir(basePath);
253
+ const wtPath = join(wtDir, name);
241
254
  mkdirSync(wtDir, { recursive: true });
255
+ // When existingPath resolved to a legacy location, the canonical target may
256
+ // still hold a stale directory from a prior aborted creation (no .git marker).
257
+ // Remove it so git worktree add does not fail with "path already exists".
258
+ if (existingPath !== wtPath && existsSync(wtPath) && !isRegisteredGitWorktreeAtPath(basePath, wtPath)) {
259
+ removeStaleWorktreeDirectory(wtPath, name);
260
+ }
242
261
  // Prune any stale worktree entries from a previous removal
243
262
  nativeWorktreePrune(basePath);
244
263
  // Use the explicit start point (e.g. integration branch) if provided,
@@ -305,7 +324,8 @@ export function createWorktree(basePath, name, opts = {}) {
305
324
  }
306
325
  /**
307
326
  * List all GSD-managed worktrees.
308
- * Uses native worktree list and filters to those under .gsd/worktrees/.
327
+ * Uses native worktree list and filters to those under a GSD worktrees
328
+ * container (canonical .gsd-worktrees/ or legacy .gsd/worktrees/).
309
329
  */
310
330
  export function listWorktrees(basePath) {
311
331
  basePath = normalizeBasePathForWorktreeOps(basePath);
@@ -315,12 +335,8 @@ export function listWorktrees(basePath) {
315
335
  }
316
336
  const seenRoots = new Set();
317
337
  const worktreeRoots = baseVariants
318
- .map(baseVariant => {
319
- const path = join(baseVariant, ".gsd", "worktrees");
320
- return {
321
- normalized: normalizePathForComparison(path),
322
- };
323
- })
338
+ .flatMap(baseVariant => worktreesDirs(baseVariant))
339
+ .map(path => ({ normalized: normalizePathForComparison(path) }))
324
340
  .filter(root => {
325
341
  if (seenRoots.has(root.normalized))
326
342
  return false;
@@ -645,6 +661,7 @@ export function removeWorktree(basePath, name, opts = {}) {
645
661
  * This module uses a split representation (paths/exact/prefixes) for efficient matching.
646
662
  */
647
663
  const SKIP_PATHS = [
664
+ ".gsd-worktrees/",
648
665
  ".gsd/worktrees/",
649
666
  ".gsd/runtime/",
650
667
  ".gsd/activity/",
@@ -0,0 +1,59 @@
1
+ /**
2
+ * Worktree Placement module — owns WHERE GSD worktrees physically live.
3
+ *
4
+ * Canonical placement: `<projectRoot>/.gsd-worktrees/<name>` — a real
5
+ * directory that never crosses the `.gsd` symlink managed by repo-identity.
6
+ * Under the external-state layout (`.gsd → ~/.gsd/projects/<hash>/`), the
7
+ * legacy `.gsd/worktrees/` location materialised worktrees inside the user's
8
+ * home directory behind an opaque hash path; the canonical sibling keeps the
9
+ * working copy at the project root regardless of where `.gsd` state lives.
10
+ *
11
+ * Legacy placement (`<projectRoot>/.gsd/worktrees/<name>`, possibly resolving
12
+ * through the symlink to `~/.gsd/projects/<hash>/worktrees/<name>`) stays
13
+ * recognized so in-flight milestones keep working across upgrades:
14
+ * - creation always uses the canonical location;
15
+ * - resolution prefers an existing legacy worktree for the same name;
16
+ * - containment checks accept membership in either location.
17
+ *
18
+ * Path → project identification lives in worktree-root.ts; this module owns
19
+ * only the forward direction (project + name → physical path).
20
+ */
21
+ import { existsSync } from "node:fs";
22
+ import { join } from "node:path";
23
+ /** Directory name of the canonical worktrees container at the project root. */
24
+ export const CANONICAL_WORKTREES_DIRNAME = ".gsd-worktrees";
25
+ /** Canonical container for newly created worktrees. Never crosses the `.gsd` symlink. */
26
+ export function canonicalWorktreesDir(projectRoot) {
27
+ return join(projectRoot, CANONICAL_WORKTREES_DIRNAME);
28
+ }
29
+ /** Legacy container (`.gsd/worktrees/`) — may resolve through the external-state symlink. */
30
+ export function legacyWorktreesDir(projectRoot) {
31
+ return join(projectRoot, ".gsd", "worktrees");
32
+ }
33
+ /**
34
+ * All containers a GSD worktree may live in, canonical first.
35
+ * Use for listing, scanning, and containment checks.
36
+ */
37
+ export function worktreesDirs(projectRoot) {
38
+ return [canonicalWorktreesDir(projectRoot), legacyWorktreesDir(projectRoot)];
39
+ }
40
+ /**
41
+ * Physical path for the worktree `name` under `projectRoot`.
42
+ *
43
+ * Canonical wins only when it has a `.git` marker (i.e. is a live worktree).
44
+ * A bare directory with no `.git` — a stale leftover from an aborted create
45
+ * or a partial cleanup — does not shadow an existing legacy worktree, so the
46
+ * legacy path is tried next. The legacy check remains a plain existsSync;
47
+ * callers that need a *registered* worktree validate the `.git` marker
48
+ * themselves (resolveCanonicalMilestoneRoot, getAutoWorktreePath).
49
+ * Falls back to canonical for new-worktree creation when neither path exists.
50
+ */
51
+ export function worktreePathFor(projectRoot, name) {
52
+ const canonical = join(canonicalWorktreesDir(projectRoot), name);
53
+ if (existsSync(canonical) && existsSync(join(canonical, ".git")))
54
+ return canonical;
55
+ const legacy = join(legacyWorktreesDir(projectRoot), name);
56
+ if (existsSync(legacy))
57
+ return legacy;
58
+ return canonical;
59
+ }
@@ -8,19 +8,23 @@
8
8
  import { readdirSync } from "node:fs";
9
9
  import { enterAutoWorktree, getAutoWorktreePath } from "./auto-worktree.js";
10
10
  import { getIsolationMode } from "./preferences.js";
11
- import { worktreesDir } from "./worktree-manager.js";
11
+ import { allWorktreesDirs } from "./worktree-manager.js";
12
12
  import { isGsdWorktreePath, resolveWorktreeProjectRoot } from "./worktree-root.js";
13
13
  /**
14
- * Enumerate the live (valid git) auto-worktrees under <projectRoot>/.gsd/worktrees/.
14
+ * Enumerate the live (valid git) auto-worktrees in the project's worktree
15
+ * containers (canonical .gsd-worktrees/ and legacy .gsd/worktrees/).
15
16
  * Reuses getAutoWorktreePath's validation so stray directories are ignored.
16
17
  */
17
18
  function liveMilestoneWorktrees(projectRoot) {
18
- let names;
19
- try {
20
- names = readdirSync(worktreesDir(projectRoot));
21
- }
22
- catch {
23
- return [];
19
+ const names = new Set();
20
+ for (const dir of allWorktreesDirs(projectRoot)) {
21
+ try {
22
+ for (const name of readdirSync(dir))
23
+ names.add(name);
24
+ }
25
+ catch {
26
+ // container absent — skip
27
+ }
24
28
  }
25
29
  const live = [];
26
30
  for (const id of names) {
@@ -14,10 +14,16 @@ export function normalizeWorktreePathForCompare(path) {
14
14
  return process.platform === "win32" ? (trimmed || "/").toLowerCase() : (trimmed || "/");
15
15
  }
16
16
  /**
17
- * Find the GSD worktree segment in both direct project layout and the
18
- * symlink-resolved external-state layout used by ~/.gsd/projects/<hash>.
17
+ * Find the GSD worktree segment in the canonical layout (.gsd-worktrees/),
18
+ * the legacy direct layout (.gsd/worktrees/), and the symlink-resolved
19
+ * external-state layout used by ~/.gsd/projects/<hash>.
19
20
  */
20
21
  export function findWorktreeSegment(normalizedPath) {
22
+ const canonicalMarker = "/.gsd-worktrees/";
23
+ const canonicalIdx = normalizedPath.indexOf(canonicalMarker);
24
+ if (canonicalIdx !== -1) {
25
+ return { gsdIdx: canonicalIdx, afterWorktrees: canonicalIdx + canonicalMarker.length };
26
+ }
21
27
  const directMarker = "/.gsd/worktrees/";
22
28
  const directIdx = normalizedPath.indexOf(directMarker);
23
29
  if (directIdx !== -1) {
@@ -60,7 +66,9 @@ export function isGsdWorktreePath(path) {
60
66
  */
61
67
  export function resolveExternalStateProjectGsdFromWorktreePath(projectPath) {
62
68
  const normalized = resolve(projectPath).replaceAll("\\", "/");
63
- // Direct layout — parent state is resolved via repoIdentity(git root).
69
+ // Canonical/direct layouts — parent state is resolved via repoIdentity(git root).
70
+ if (normalized.includes("/.gsd-worktrees/"))
71
+ return null;
64
72
  if (normalized.includes("/.gsd/worktrees/") && !normalized.includes("/.gsd/projects/")) {
65
73
  return null;
66
74
  }
@@ -117,12 +125,15 @@ function resolveProjectRootFromPath(path) {
117
125
  if (!segment) {
118
126
  return resolveNearestBootstrappedGsdRoot(path) ?? resolveGitWorkingTreeRoot(path) ?? path;
119
127
  }
128
+ // Slice at the first `.gsd` boundary, but never past the worktree segment:
129
+ // in the canonical layout (`<root>/.gsd-worktrees/<MID>/.gsd/...`) the first
130
+ // `/.gsd/` occurrence is the worktree-local projection dir, not the project
131
+ // root's state dir.
120
132
  const sepChar = path.includes("\\") ? "\\" : "/";
121
133
  const gsdMarker = `${sepChar}.gsd${sepChar}`;
122
134
  const markerIdx = path.indexOf(gsdMarker);
123
- const candidate = markerIdx !== -1
124
- ? path.slice(0, markerIdx)
125
- : path.slice(0, segment.gsdIdx);
135
+ const sliceIdx = markerIdx !== -1 ? Math.min(markerIdx, segment.gsdIdx) : segment.gsdIdx;
136
+ const candidate = path.slice(0, sliceIdx);
126
137
  const gsdHomeNorm = normalizeWorktreePathForCompare(gsdHome());
127
138
  const candidateGsdPath = normalizeWorktreePathForCompare(join(candidate, ".gsd"));
128
139
  if (candidateGsdPath === gsdHomeNorm || candidateGsdPath.startsWith(`${gsdHomeNorm}/`)) {
@@ -4,6 +4,7 @@ import { existsSync, lstatSync } from "node:fs";
4
4
  import { execFileSync } from "node:child_process";
5
5
  import { join, resolve } from "node:path";
6
6
  import { normalizeWorktreePathForCompare } from "./worktree-root.js";
7
+ import { worktreesDirs } from "./worktree-placement.js";
7
8
  import { listWorktrees } from "./worktree-manager.js";
8
9
  import { getCurrentBranch } from "./worktree.js";
9
10
  const fsOnlyDeps = {
@@ -59,15 +60,17 @@ export function createWorktreeSafetyModule(deps = defaultDeps) {
59
60
  const projectRoot = resolve(input.projectRoot);
60
61
  const unitRoot = resolve(input.unitRoot);
61
62
  const isolationMode = input.isolationMode ?? "worktree";
62
- const expectedRoot = isolationMode === "worktree"
63
- ? join(projectRoot, ".gsd", "worktrees", milestoneId)
64
- : projectRoot;
65
- if (!samePath(unitRoot, expectedRoot)) {
63
+ // A milestone worktree may live in the canonical container or the
64
+ // legacy one (pre-placement-change worktrees keep their location).
65
+ const expectedRoots = isolationMode === "worktree"
66
+ ? worktreesDirs(projectRoot).map((dir) => join(dir, milestoneId))
67
+ : [projectRoot];
68
+ if (!expectedRoots.some((expectedRoot) => samePath(unitRoot, expectedRoot))) {
66
69
  return failure("invalid-root", isolationMode === "worktree"
67
70
  ? `Unit root ${unitRoot} is not the expected worktree root for ${milestoneId}.`
68
71
  : `Unit root ${unitRoot} is not the project root while isolation mode is ${isolationMode}.`, isolationMode === "worktree"
69
72
  ? "Prepare the Unit in its canonical milestone worktree before allowing source writes."
70
- : "Run the Unit from the project root when worktree isolation is disabled.", { expectedRoot, unitRoot });
73
+ : "Run the Unit from the project root when worktree isolation is disabled.", { expectedRoot: expectedRoots[0], unitRoot });
71
74
  }
72
75
  if (!deps.existsSync(unitRoot)) {
73
76
  return failure("worktree-missing", `Worktree root ${unitRoot} does not exist.`, "Create or recover the milestone worktree before dispatching the source-writing Unit.", { unitRoot });
@@ -1,4 +1,5 @@
1
1
  // GSD worktree session state
2
+ import { findWorktreeSegment } from "./worktree-root.js";
2
3
  let originalCwd = null;
3
4
  export function getWorktreeOriginalCwd() {
4
5
  return originalCwd;
@@ -12,22 +13,23 @@ export function clearWorktreeOriginalCwd() {
12
13
  export function ensureWorktreeOriginalCwdFromPath(cwd = process.cwd()) {
13
14
  if (originalCwd)
14
15
  return originalCwd;
15
- const marker = `${/\\/.test(cwd) ? "\\" : "/"}.gsd${/\\/.test(cwd) ? "\\" : "/"}worktrees${/\\/.test(cwd) ? "\\" : "/"}`;
16
- const markerIdx = cwd.indexOf(marker);
17
- if (markerIdx !== -1) {
18
- originalCwd = cwd.slice(0, markerIdx);
16
+ const segment = findWorktreeSegment(cwd.replaceAll("\\", "/"));
17
+ if (segment) {
18
+ originalCwd = cwd.slice(0, segment.gsdIdx);
19
19
  }
20
20
  return originalCwd;
21
21
  }
22
22
  export function getActiveWorktreeName() {
23
23
  if (!originalCwd)
24
24
  return null;
25
- const cwd = process.cwd();
26
- const wtDir = `${originalCwd.replace(/[\\/]+$/, "")}/.gsd/worktrees`.replaceAll("\\", "/");
27
- const normalizedCwd = cwd.replaceAll("\\", "/");
28
- if (!normalizedCwd.startsWith(`${wtDir}/`))
25
+ const normalizedCwd = process.cwd().replaceAll("\\", "/");
26
+ const normalizedOriginal = originalCwd.replace(/[\\/]+$/, "").replaceAll("\\", "/");
27
+ const segment = findWorktreeSegment(normalizedCwd);
28
+ if (!segment)
29
29
  return null;
30
- const rel = normalizedCwd.slice(wtDir.length + 1);
31
- const name = rel.split("/")[0];
30
+ // Only treat the cwd as an active worktree of OUR project root.
31
+ if (normalizedCwd.slice(0, segment.gsdIdx) !== normalizedOriginal)
32
+ return null;
33
+ const name = normalizedCwd.slice(segment.afterWorktrees).split("/")[0];
32
34
  return name || null;
33
35
  }
@@ -60,6 +60,23 @@ const VERDICT_RE = /verdict:\s*[\w-]+/i;
60
60
  * Only overwrites when the source has a verdict — never clobbers a
61
61
  * worktree ASSESSMENT with a verdictless project-root copy.
62
62
  */
63
+ function forceOverwriteValidationWithVerdict(srcMilestoneDir, dstMilestoneDir, milestoneId) {
64
+ if (!existsSync(srcMilestoneDir) || !milestoneId)
65
+ return;
66
+ const srcFile = join(srcMilestoneDir, `${milestoneId}-VALIDATION.md`);
67
+ if (!existsSync(srcFile))
68
+ return;
69
+ try {
70
+ const srcContent = readFileSync(srcFile, "utf-8");
71
+ if (!VERDICT_RE.test(srcContent))
72
+ return;
73
+ mkdirSync(dstMilestoneDir, { recursive: true });
74
+ safeCopy(srcFile, join(dstMilestoneDir, `${milestoneId}-VALIDATION.md`), { force: true });
75
+ }
76
+ catch (err) {
77
+ logWarning("worktree", `validation force-copy failed: ${err instanceof Error ? err.message : String(err)}`);
78
+ }
79
+ }
63
80
  function forceOverwriteAssessmentsWithVerdict(srcMilestoneDir, dstMilestoneDir) {
64
81
  if (!existsSync(srcMilestoneDir))
65
82
  return;
@@ -211,7 +228,10 @@ export function _projectRootToWorktreeImpl(projectRoot, worktreePath_, milestone
211
228
  // session resume the DB is rebuilt from disk, and if the stale ASSESSMENT
212
229
  // persists, checkNeedsRunUat finds no passing verdict → re-dispatches
213
230
  // run-uat indefinitely (stuck-loop ×9).
214
- forceOverwriteAssessmentsWithVerdict(join(prGsd, "milestones", milestoneId), join(wtGsd, "milestones", milestoneId));
231
+ const prMilestoneDir = join(prGsd, "milestones", milestoneId);
232
+ const wtMilestoneDir = join(wtGsd, "milestones", milestoneId);
233
+ forceOverwriteValidationWithVerdict(prMilestoneDir, wtMilestoneDir, milestoneId);
234
+ forceOverwriteAssessmentsWithVerdict(prMilestoneDir, wtMilestoneDir);
215
235
  // Forward-sync completed-units.json from project root to worktree.
216
236
  // Project root is authoritative for completion state after crash recovery;
217
237
  // without this, the worktree re-dispatches already-completed units (#1886).
@@ -354,14 +374,20 @@ export class WorktreeStateProjection {
354
374
  * any Unit dispatches.
355
375
  */
356
376
  projectRootToWorktree(scope) {
357
- _projectRootToWorktreeImpl(scope.workspace.projectRoot, scope.workspace.worktreeRoot ?? scope.workspace.projectRoot, scope.milestoneId);
377
+ this.projectRootToWorktreePaths(scope.workspace.projectRoot, scope.workspace.worktreeRoot ?? scope.workspace.projectRoot, scope.milestoneId);
378
+ }
379
+ projectRootToWorktreePaths(projectRoot, worktreePath, milestoneId) {
380
+ _projectRootToWorktreeImpl(projectRoot, worktreePath, milestoneId);
358
381
  }
359
382
  /**
360
383
  * Project state from the auto-worktree back onto the project root for `scope`.
361
384
  * Called by the post-unit pipeline between Units.
362
385
  */
363
386
  projectWorktreeToRoot(scope) {
364
- _projectWorktreeToRootImpl(scope.workspace.worktreeRoot ?? scope.workspace.projectRoot, scope.workspace.projectRoot, scope.milestoneId);
387
+ this.projectWorktreeToRootPaths(scope.workspace.worktreeRoot ?? scope.workspace.projectRoot, scope.workspace.projectRoot, scope.milestoneId);
388
+ }
389
+ projectWorktreeToRootPaths(worktreePath, projectRoot, milestoneId) {
390
+ _projectWorktreeToRootImpl(worktreePath, projectRoot, milestoneId);
365
391
  }
366
392
  /**
367
393
  * Final projection from the auto-worktree to the project root before
@@ -373,6 +399,9 @@ export class WorktreeStateProjection {
373
399
  * telemetry on what crossed the boundary.
374
400
  */
375
401
  finalizeProjectionForMerge(scope) {
376
- return _finalizeProjectionForMergeImpl(scope.workspace.projectRoot, scope.workspace.worktreeRoot ?? scope.workspace.projectRoot, scope.milestoneId);
402
+ return this.finalizeProjectionForMergePaths(scope.workspace.projectRoot, scope.workspace.worktreeRoot ?? scope.workspace.projectRoot, scope.milestoneId);
403
+ }
404
+ finalizeProjectionForMergePaths(projectRoot, worktreePath, milestoneId) {
405
+ return _finalizeProjectionForMergeImpl(projectRoot, worktreePath, milestoneId);
377
406
  }
378
407
  }
@@ -63,6 +63,18 @@ export function normalizeAutoExitReason(rawReason) {
63
63
  ? reasonLc
64
64
  : "other";
65
65
  }
66
+ export function autoExitReasonForTerminalOutcome(outcome) {
67
+ switch (outcome?.code) {
68
+ case "all-complete":
69
+ return "all-complete";
70
+ case "settlement-blocked":
71
+ return "blocked";
72
+ case "no-remaining-units":
73
+ return "stop";
74
+ default:
75
+ return null;
76
+ }
77
+ }
66
78
  // ─── Emitters ────────────────────────────────────────────────────────────
67
79
  export function emitWorktreeCreated(projectRoot, milestoneId, meta = {}) {
68
80
  emitJournalEvent(projectRoot, baseEntry("worktree-created", {
@@ -146,7 +146,7 @@ export async function showInterviewRound(questions, opts, ctx) {
146
146
  }
147
147
  // External cancellation (e.g. remote channel won the race)
148
148
  if (opts.signal) {
149
- const onAbort = () => finish({ endInterview: false, answers: {} });
149
+ const onAbort = () => finish({ endInterview: false, answers: {}, interrupted: true });
150
150
  if (opts.signal.aborted) {
151
151
  onAbort();
152
152
  }
@@ -800,5 +800,5 @@ export async function showInterviewRound(questions, opts, ctx) {
800
800
  invalidate: () => { cachedLines = undefined; },
801
801
  handleInput,
802
802
  };
803
- });
803
+ }, opts.overlay ? { overlay: true } : undefined);
804
804
  }