gsd-pi 2.78.1-dev.84a383f51 → 2.78.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (474) hide show
  1. package/README.md +7 -7
  2. package/dist/cli.js +55 -95
  3. package/dist/headless-query.d.ts +0 -22
  4. package/dist/headless-query.js +4 -24
  5. package/dist/headless.d.ts +0 -10
  6. package/dist/headless.js +1 -16
  7. package/dist/loader.js +10 -7
  8. package/dist/onboarding.d.ts +0 -10
  9. package/dist/onboarding.js +2 -2
  10. package/dist/provider-migrations.d.ts +2 -2
  11. package/dist/provider-migrations.js +2 -5
  12. package/dist/resource-loader.d.ts +2 -5
  13. package/dist/resource-loader.js +5 -28
  14. package/dist/resources/extensions/browser-tools/tests/browser-tools-integration.test.mjs +601 -0
  15. package/dist/resources/extensions/browser-tools/tests/browser-tools-unit.test.cjs +651 -0
  16. package/dist/resources/extensions/browser-tools/tests/capture-sharp-optional.test.cjs +91 -0
  17. package/dist/resources/extensions/gsd/auto/loop.js +0 -23
  18. package/dist/resources/extensions/gsd/auto/phases.js +2 -2
  19. package/dist/resources/extensions/gsd/auto/run-unit.js +1 -3
  20. package/dist/resources/extensions/gsd/auto/session.js +0 -3
  21. package/dist/resources/extensions/gsd/auto-recovery.js +4 -43
  22. package/dist/resources/extensions/gsd/auto-start.js +1 -1
  23. package/dist/resources/extensions/gsd/auto-tool-tracking.js +2 -2
  24. package/dist/resources/extensions/gsd/auto-worktree.js +0 -30
  25. package/dist/resources/extensions/gsd/auto.js +5 -14
  26. package/dist/resources/extensions/gsd/bootstrap/db-tools.js +2 -14
  27. package/dist/resources/extensions/gsd/bootstrap/exec-tools.js +5 -7
  28. package/dist/resources/extensions/gsd/bootstrap/query-tools.js +2 -2
  29. package/dist/resources/extensions/gsd/bootstrap/register-extension.js +4 -5
  30. package/dist/resources/extensions/gsd/bootstrap/register-hooks.js +31 -94
  31. package/dist/resources/extensions/gsd/bootstrap/register-shortcuts.js +6 -11
  32. package/dist/resources/extensions/gsd/bootstrap/system-context.js +8 -34
  33. package/dist/resources/extensions/gsd/bootstrap/write-gate.js +2 -38
  34. package/dist/resources/extensions/gsd/commands/catalog.js +5 -69
  35. package/dist/resources/extensions/gsd/commands/handlers/core.js +1 -22
  36. package/dist/resources/extensions/gsd/commands-mcp-status.js +1 -3
  37. package/dist/resources/extensions/gsd/commands-prefs-wizard.js +1 -10
  38. package/dist/resources/extensions/gsd/dashboard-overlay.js +1 -1
  39. package/dist/resources/extensions/gsd/docs/preferences-reference.md +0 -4
  40. package/dist/resources/extensions/gsd/doctor-runtime-checks.js +1 -39
  41. package/dist/resources/extensions/gsd/error-classifier.js +1 -1
  42. package/dist/resources/extensions/gsd/forensics.js +2 -2
  43. package/dist/resources/extensions/gsd/git-service.js +5 -12
  44. package/dist/resources/extensions/gsd/gsd-db.js +2 -11
  45. package/dist/resources/extensions/gsd/guided-flow.js +23 -23
  46. package/dist/resources/extensions/gsd/memory-store.js +31 -66
  47. package/dist/resources/extensions/gsd/model-router.js +9 -114
  48. package/dist/resources/extensions/gsd/native-git-bridge.js +1 -7
  49. package/dist/resources/extensions/gsd/preferences-models.js +15 -91
  50. package/dist/resources/extensions/gsd/preferences-types.js +0 -2
  51. package/dist/resources/extensions/gsd/preferences-validation.js +0 -32
  52. package/dist/resources/extensions/gsd/preferences.js +3 -5
  53. package/dist/resources/extensions/gsd/prompt-loader.js +12 -23
  54. package/dist/resources/extensions/gsd/slice-parallel-orchestrator.js +3 -9
  55. package/dist/resources/extensions/gsd/state.js +0 -42
  56. package/dist/resources/extensions/gsd/templates/PREFERENCES.md +0 -1
  57. package/dist/resources/extensions/gsd/tests/auto-supervisor.test.mjs +53 -0
  58. package/dist/resources/extensions/gsd/tests/dist-redirect.mjs +112 -0
  59. package/dist/resources/extensions/gsd/tests/resolve-ts-hooks.mjs +23 -0
  60. package/dist/resources/extensions/gsd/tests/resolve-ts.mjs +5 -0
  61. package/dist/resources/extensions/gsd/tools/memory-tools.js +1 -18
  62. package/dist/resources/extensions/gsd/visualizer-overlay.js +1 -1
  63. package/dist/resources/extensions/gsd/watch/header-renderer.js +1 -3
  64. package/dist/resources/extensions/gsd/worktree-command.js +46 -26
  65. package/dist/resources/extensions/mcp-client/index.js +3 -6
  66. package/dist/resources/extensions/slash-commands/create-extension.js +22 -36
  67. package/dist/resources/skills/create-gsd-extension/SKILL.md +5 -9
  68. package/dist/resources/skills/create-gsd-extension/references/custom-commands.md +1 -1
  69. package/dist/resources/skills/create-gsd-extension/references/custom-rendering.md +5 -5
  70. package/dist/resources/skills/create-gsd-extension/references/custom-tools.md +4 -4
  71. package/dist/resources/skills/create-gsd-extension/references/custom-ui.md +6 -6
  72. package/dist/resources/skills/create-gsd-extension/references/events-reference.md +3 -3
  73. package/dist/resources/skills/create-gsd-extension/references/packaging-distribution.md +1 -1
  74. package/dist/resources/skills/create-gsd-extension/references/remote-execution-overrides.md +3 -3
  75. package/dist/resources/skills/create-gsd-extension/workflows/create-extension.md +12 -32
  76. package/dist/resources/skills/github-workflows/references/gh/tests/__init__.py +0 -0
  77. package/dist/resources/skills/github-workflows/references/gh/tests/test_github_project_setup.py +608 -0
  78. package/dist/rtk-shared.d.ts +0 -3
  79. package/dist/rtk-shared.js +0 -17
  80. package/dist/rtk.d.ts +5 -2
  81. package/dist/rtk.js +20 -3
  82. package/dist/tsconfig.extensions.tsbuildinfo +1 -1
  83. package/dist/web/standalone/.next/BUILD_ID +1 -1
  84. package/dist/web/standalone/.next/app-path-routes-manifest.json +13 -13
  85. package/dist/web/standalone/.next/build-manifest.json +4 -4
  86. package/dist/web/standalone/.next/prerender-manifest.json +3 -3
  87. package/dist/web/standalone/.next/react-loadable-manifest.json +4 -44
  88. package/dist/web/standalone/.next/required-server-files.json +3 -3
  89. package/dist/web/standalone/.next/server/app/_global-error/page.js +3 -3
  90. package/dist/web/standalone/.next/server/app/_global-error/page_client-reference-manifest.js +1 -1
  91. package/dist/web/standalone/.next/server/app/_global-error.html +1 -1
  92. package/dist/web/standalone/.next/server/app/_global-error.rsc +1 -1
  93. package/dist/web/standalone/.next/server/app/_global-error.segments/_full.segment.rsc +1 -1
  94. package/dist/web/standalone/.next/server/app/_global-error.segments/_global-error/__PAGE__.segment.rsc +1 -1
  95. package/dist/web/standalone/.next/server/app/_global-error.segments/_global-error.segment.rsc +1 -1
  96. package/dist/web/standalone/.next/server/app/_global-error.segments/_head.segment.rsc +1 -1
  97. package/dist/web/standalone/.next/server/app/_global-error.segments/_index.segment.rsc +1 -1
  98. package/dist/web/standalone/.next/server/app/_global-error.segments/_tree.segment.rsc +1 -1
  99. package/dist/web/standalone/.next/server/app/_not-found/page.js +2 -2
  100. package/dist/web/standalone/.next/server/app/_not-found/page_client-reference-manifest.js +1 -1
  101. package/dist/web/standalone/.next/server/app/_not-found.html +1 -1
  102. package/dist/web/standalone/.next/server/app/_not-found.rsc +3 -3
  103. package/dist/web/standalone/.next/server/app/_not-found.segments/_full.segment.rsc +3 -3
  104. package/dist/web/standalone/.next/server/app/_not-found.segments/_head.segment.rsc +1 -1
  105. package/dist/web/standalone/.next/server/app/_not-found.segments/_index.segment.rsc +3 -3
  106. package/dist/web/standalone/.next/server/app/_not-found.segments/_not-found/__PAGE__.segment.rsc +1 -1
  107. package/dist/web/standalone/.next/server/app/_not-found.segments/_not-found.segment.rsc +1 -1
  108. package/dist/web/standalone/.next/server/app/_not-found.segments/_tree.segment.rsc +1 -1
  109. package/dist/web/standalone/.next/server/app/api/boot/route.js +1 -1
  110. package/dist/web/standalone/.next/server/app/api/boot/route_client-reference-manifest.js +1 -1
  111. package/dist/web/standalone/.next/server/app/api/bridge-terminal/input/route.js +1 -1
  112. package/dist/web/standalone/.next/server/app/api/bridge-terminal/input/route_client-reference-manifest.js +1 -1
  113. package/dist/web/standalone/.next/server/app/api/bridge-terminal/resize/route.js +1 -1
  114. package/dist/web/standalone/.next/server/app/api/bridge-terminal/resize/route_client-reference-manifest.js +1 -1
  115. package/dist/web/standalone/.next/server/app/api/bridge-terminal/stream/route.js +2 -2
  116. package/dist/web/standalone/.next/server/app/api/bridge-terminal/stream/route_client-reference-manifest.js +1 -1
  117. package/dist/web/standalone/.next/server/app/api/browse-directories/route.js +1 -1
  118. package/dist/web/standalone/.next/server/app/api/browse-directories/route_client-reference-manifest.js +1 -1
  119. package/dist/web/standalone/.next/server/app/api/captures/route.js +1 -1
  120. package/dist/web/standalone/.next/server/app/api/captures/route_client-reference-manifest.js +1 -1
  121. package/dist/web/standalone/.next/server/app/api/cleanup/route.js +1 -1
  122. package/dist/web/standalone/.next/server/app/api/cleanup/route_client-reference-manifest.js +1 -1
  123. package/dist/web/standalone/.next/server/app/api/dev-mode/route.js +1 -1
  124. package/dist/web/standalone/.next/server/app/api/dev-mode/route_client-reference-manifest.js +1 -1
  125. package/dist/web/standalone/.next/server/app/api/doctor/route.js +1 -1
  126. package/dist/web/standalone/.next/server/app/api/doctor/route_client-reference-manifest.js +1 -1
  127. package/dist/web/standalone/.next/server/app/api/experimental/route.js +2 -2
  128. package/dist/web/standalone/.next/server/app/api/experimental/route_client-reference-manifest.js +1 -1
  129. package/dist/web/standalone/.next/server/app/api/export-data/route.js +1 -1
  130. package/dist/web/standalone/.next/server/app/api/export-data/route_client-reference-manifest.js +1 -1
  131. package/dist/web/standalone/.next/server/app/api/files/route.js +1 -1
  132. package/dist/web/standalone/.next/server/app/api/files/route_client-reference-manifest.js +1 -1
  133. package/dist/web/standalone/.next/server/app/api/forensics/route.js +1 -1
  134. package/dist/web/standalone/.next/server/app/api/forensics/route_client-reference-manifest.js +1 -1
  135. package/dist/web/standalone/.next/server/app/api/git/route.js +1 -1
  136. package/dist/web/standalone/.next/server/app/api/git/route_client-reference-manifest.js +1 -1
  137. package/dist/web/standalone/.next/server/app/api/history/route.js +1 -1
  138. package/dist/web/standalone/.next/server/app/api/history/route_client-reference-manifest.js +1 -1
  139. package/dist/web/standalone/.next/server/app/api/hooks/route.js +1 -1
  140. package/dist/web/standalone/.next/server/app/api/hooks/route_client-reference-manifest.js +1 -1
  141. package/dist/web/standalone/.next/server/app/api/inspect/route.js +1 -1
  142. package/dist/web/standalone/.next/server/app/api/inspect/route_client-reference-manifest.js +1 -1
  143. package/dist/web/standalone/.next/server/app/api/knowledge/route.js +1 -1
  144. package/dist/web/standalone/.next/server/app/api/knowledge/route_client-reference-manifest.js +1 -1
  145. package/dist/web/standalone/.next/server/app/api/live-state/route.js +1 -1
  146. package/dist/web/standalone/.next/server/app/api/live-state/route_client-reference-manifest.js +1 -1
  147. package/dist/web/standalone/.next/server/app/api/notifications/route.js +2 -2
  148. package/dist/web/standalone/.next/server/app/api/notifications/route_client-reference-manifest.js +1 -1
  149. package/dist/web/standalone/.next/server/app/api/onboarding/route.js +1 -1
  150. package/dist/web/standalone/.next/server/app/api/onboarding/route_client-reference-manifest.js +1 -1
  151. package/dist/web/standalone/.next/server/app/api/preferences/route.js +1 -1
  152. package/dist/web/standalone/.next/server/app/api/preferences/route_client-reference-manifest.js +1 -1
  153. package/dist/web/standalone/.next/server/app/api/projects/route.js +1 -1
  154. package/dist/web/standalone/.next/server/app/api/projects/route_client-reference-manifest.js +1 -1
  155. package/dist/web/standalone/.next/server/app/api/recovery/route.js +1 -1
  156. package/dist/web/standalone/.next/server/app/api/recovery/route_client-reference-manifest.js +1 -1
  157. package/dist/web/standalone/.next/server/app/api/remote-questions/route.js +2 -2
  158. package/dist/web/standalone/.next/server/app/api/remote-questions/route_client-reference-manifest.js +1 -1
  159. package/dist/web/standalone/.next/server/app/api/session/browser/route.js +1 -1
  160. package/dist/web/standalone/.next/server/app/api/session/browser/route_client-reference-manifest.js +1 -1
  161. package/dist/web/standalone/.next/server/app/api/session/command/route.js +1 -1
  162. package/dist/web/standalone/.next/server/app/api/session/command/route_client-reference-manifest.js +1 -1
  163. package/dist/web/standalone/.next/server/app/api/session/events/route.js +2 -4
  164. package/dist/web/standalone/.next/server/app/api/session/events/route_client-reference-manifest.js +1 -1
  165. package/dist/web/standalone/.next/server/app/api/session/manage/route.js +1 -1
  166. package/dist/web/standalone/.next/server/app/api/session/manage/route_client-reference-manifest.js +1 -1
  167. package/dist/web/standalone/.next/server/app/api/settings-data/route.js +1 -1
  168. package/dist/web/standalone/.next/server/app/api/settings-data/route_client-reference-manifest.js +1 -1
  169. package/dist/web/standalone/.next/server/app/api/shutdown/route.js +1 -1
  170. package/dist/web/standalone/.next/server/app/api/shutdown/route_client-reference-manifest.js +1 -1
  171. package/dist/web/standalone/.next/server/app/api/skill-health/route.js +1 -1
  172. package/dist/web/standalone/.next/server/app/api/skill-health/route_client-reference-manifest.js +1 -1
  173. package/dist/web/standalone/.next/server/app/api/steer/route.js +1 -1
  174. package/dist/web/standalone/.next/server/app/api/steer/route_client-reference-manifest.js +1 -1
  175. package/dist/web/standalone/.next/server/app/api/switch-root/route.js +1 -1
  176. package/dist/web/standalone/.next/server/app/api/switch-root/route_client-reference-manifest.js +1 -1
  177. package/dist/web/standalone/.next/server/app/api/terminal/input/route.js +2 -2
  178. package/dist/web/standalone/.next/server/app/api/terminal/input/route_client-reference-manifest.js +1 -1
  179. package/dist/web/standalone/.next/server/app/api/terminal/resize/route.js +2 -2
  180. package/dist/web/standalone/.next/server/app/api/terminal/resize/route_client-reference-manifest.js +1 -1
  181. package/dist/web/standalone/.next/server/app/api/terminal/sessions/route.js +2 -2
  182. package/dist/web/standalone/.next/server/app/api/terminal/sessions/route_client-reference-manifest.js +1 -1
  183. package/dist/web/standalone/.next/server/app/api/terminal/stream/route.js +4 -4
  184. package/dist/web/standalone/.next/server/app/api/terminal/stream/route_client-reference-manifest.js +1 -1
  185. package/dist/web/standalone/.next/server/app/api/terminal/upload/route.js +1 -1
  186. package/dist/web/standalone/.next/server/app/api/terminal/upload/route_client-reference-manifest.js +1 -1
  187. package/dist/web/standalone/.next/server/app/api/undo/route.js +1 -1
  188. package/dist/web/standalone/.next/server/app/api/undo/route_client-reference-manifest.js +1 -1
  189. package/dist/web/standalone/.next/server/app/api/update/route.js +1 -1
  190. package/dist/web/standalone/.next/server/app/api/update/route_client-reference-manifest.js +1 -1
  191. package/dist/web/standalone/.next/server/app/api/visualizer/route.js +1 -1
  192. package/dist/web/standalone/.next/server/app/api/visualizer/route_client-reference-manifest.js +1 -1
  193. package/dist/web/standalone/.next/server/app/index.html +1 -1
  194. package/dist/web/standalone/.next/server/app/index.rsc +4 -4
  195. package/dist/web/standalone/.next/server/app/index.segments/__PAGE__.segment.rsc +2 -2
  196. package/dist/web/standalone/.next/server/app/index.segments/_full.segment.rsc +4 -4
  197. package/dist/web/standalone/.next/server/app/index.segments/_head.segment.rsc +1 -1
  198. package/dist/web/standalone/.next/server/app/index.segments/_index.segment.rsc +3 -3
  199. package/dist/web/standalone/.next/server/app/index.segments/_tree.segment.rsc +1 -1
  200. package/dist/web/standalone/.next/server/app/page.js +2 -2
  201. package/dist/web/standalone/.next/server/app/page_client-reference-manifest.js +1 -1
  202. package/dist/web/standalone/.next/server/app-paths-manifest.json +13 -13
  203. package/dist/web/standalone/.next/server/chunks/63.js +3 -3
  204. package/dist/web/standalone/.next/server/chunks/6897.js +1 -1
  205. package/dist/web/standalone/.next/server/middleware-build-manifest.js +1 -1
  206. package/dist/web/standalone/.next/server/middleware-manifest.json +5 -5
  207. package/dist/web/standalone/.next/server/middleware-react-loadable-manifest.js +1 -1
  208. package/dist/web/standalone/.next/server/middleware.js +2 -2
  209. package/dist/web/standalone/.next/server/next-font-manifest.js +1 -1
  210. package/dist/web/standalone/.next/server/next-font-manifest.json +1 -1
  211. package/dist/web/standalone/.next/server/pages/404.html +1 -1
  212. package/dist/web/standalone/.next/server/pages/500.html +1 -1
  213. package/dist/web/standalone/.next/server/server-reference-manifest.json +1 -1
  214. package/dist/web/standalone/.next/server/webpack-runtime.js +1 -1
  215. package/dist/web/standalone/.next/static/chunks/2826.e9f5195e91f9cad2.js +11 -0
  216. package/dist/web/standalone/.next/static/chunks/3621.fc7480022c972438.js +20 -0
  217. package/dist/web/standalone/.next/static/chunks/app/_not-found/{page-f2a7482d42a5614b.js → page-2f24283c162b6ab3.js} +1 -1
  218. package/dist/web/standalone/.next/static/chunks/app/{layout-a16c7a7ecdf0c2cf.js → layout-9ecfd95f343793f0.js} +1 -1
  219. package/dist/web/standalone/.next/static/chunks/app/page-151349214571e2b6.js +1 -0
  220. package/dist/web/standalone/.next/static/chunks/main-app-d3d4c336195465f9.js +1 -0
  221. package/dist/web/standalone/.next/static/chunks/next/dist/client/components/builtin/global-error-ab5a8926e07ec673.js +1 -0
  222. package/dist/web/standalone/.next/static/chunks/webpack-2e68521d7c82f7c2.js +1 -0
  223. package/dist/web/standalone/node_modules/node-pty/build/Makefile +2 -2
  224. package/dist/web/standalone/node_modules/node-pty/build/Release/pty.node +0 -0
  225. package/dist/web/standalone/node_modules/node-pty/build/pty.target.mk +14 -14
  226. package/dist/web/standalone/node_modules/node-pty/node-addon-api/node_addon_api.target.mk +14 -14
  227. package/dist/web/standalone/node_modules/node-pty/node-addon-api/node_addon_api_except.target.mk +14 -14
  228. package/dist/web/standalone/node_modules/node-pty/node-addon-api/node_addon_api_maybe.target.mk +14 -14
  229. package/dist/web/standalone/package.json +1 -2
  230. package/dist/web/standalone/server.js +1 -1
  231. package/package.json +1 -1
  232. package/packages/mcp-server/dist/workflow-tools.d.ts.map +1 -1
  233. package/packages/mcp-server/dist/workflow-tools.js +46 -74
  234. package/packages/mcp-server/dist/workflow-tools.js.map +1 -1
  235. package/packages/mcp-server/src/workflow-tools.test.ts +0 -26
  236. package/packages/mcp-server/src/workflow-tools.ts +58 -93
  237. package/packages/mcp-server/tsconfig.tsbuildinfo +1 -1
  238. package/packages/pi-agent-core/tsconfig.tsbuildinfo +1 -1
  239. package/packages/pi-ai/dist/providers/anthropic-shared.d.ts.map +1 -1
  240. package/packages/pi-ai/dist/providers/anthropic-shared.js +19 -48
  241. package/packages/pi-ai/dist/providers/anthropic-shared.js.map +1 -1
  242. package/packages/pi-ai/dist/types.d.ts +0 -13
  243. package/packages/pi-ai/dist/types.d.ts.map +1 -1
  244. package/packages/pi-ai/dist/types.js.map +1 -1
  245. package/packages/pi-ai/dist/utils/repair-tool-json.d.ts.map +1 -1
  246. package/packages/pi-ai/dist/utils/repair-tool-json.js +3 -24
  247. package/packages/pi-ai/dist/utils/repair-tool-json.js.map +1 -1
  248. package/packages/pi-ai/dist/utils/tests/repair-tool-json.test.js +0 -26
  249. package/packages/pi-ai/dist/utils/tests/repair-tool-json.test.js.map +1 -1
  250. package/packages/pi-ai/src/providers/anthropic-shared.ts +20 -52
  251. package/packages/pi-ai/src/types.ts +0 -13
  252. package/packages/pi-ai/src/utils/repair-tool-json.ts +3 -24
  253. package/packages/pi-ai/src/utils/tests/repair-tool-json.test.ts +0 -32
  254. package/packages/pi-ai/tsconfig.tsbuildinfo +1 -1
  255. package/packages/pi-coding-agent/dist/core/agent-session.d.ts.map +1 -1
  256. package/packages/pi-coding-agent/dist/core/agent-session.js +0 -6
  257. package/packages/pi-coding-agent/dist/core/agent-session.js.map +1 -1
  258. package/packages/pi-coding-agent/dist/core/messages.d.ts.map +1 -1
  259. package/packages/pi-coding-agent/dist/core/messages.js +0 -4
  260. package/packages/pi-coding-agent/dist/core/messages.js.map +1 -1
  261. package/packages/pi-coding-agent/dist/core/model-registry-auth-mode.test.js +2 -19
  262. package/packages/pi-coding-agent/dist/core/model-registry-auth-mode.test.js.map +1 -1
  263. package/packages/pi-coding-agent/dist/core/model-registry.d.ts +0 -10
  264. package/packages/pi-coding-agent/dist/core/model-registry.d.ts.map +1 -1
  265. package/packages/pi-coding-agent/dist/core/model-registry.js +0 -18
  266. package/packages/pi-coding-agent/dist/core/model-registry.js.map +1 -1
  267. package/packages/pi-coding-agent/dist/core/system-prompt.d.ts +0 -13
  268. package/packages/pi-coding-agent/dist/core/system-prompt.d.ts.map +1 -1
  269. package/packages/pi-coding-agent/dist/core/system-prompt.js +16 -20
  270. package/packages/pi-coding-agent/dist/core/system-prompt.js.map +1 -1
  271. package/packages/pi-coding-agent/dist/modes/interactive/controllers/input-controller.js +1 -1
  272. package/packages/pi-coding-agent/dist/modes/interactive/controllers/input-controller.js.map +1 -1
  273. package/packages/pi-coding-agent/dist/modes/interactive/controllers/input-controller.test.js +1 -14
  274. package/packages/pi-coding-agent/dist/modes/interactive/controllers/input-controller.test.js.map +1 -1
  275. package/packages/pi-coding-agent/src/core/agent-session.ts +0 -7
  276. package/packages/pi-coding-agent/src/core/messages.ts +0 -4
  277. package/packages/pi-coding-agent/src/core/model-registry-auth-mode.test.ts +2 -32
  278. package/packages/pi-coding-agent/src/core/model-registry.ts +0 -21
  279. package/packages/pi-coding-agent/src/core/system-prompt.ts +15 -33
  280. package/packages/pi-coding-agent/src/modes/interactive/controllers/input-controller.test.ts +1 -17
  281. package/packages/pi-coding-agent/src/modes/interactive/controllers/input-controller.ts +1 -1
  282. package/packages/pi-coding-agent/tsconfig.tsbuildinfo +1 -1
  283. package/packages/pi-tui/dist/__tests__/autocomplete.test.js +3 -17
  284. package/packages/pi-tui/dist/__tests__/autocomplete.test.js.map +1 -1
  285. package/packages/pi-tui/src/__tests__/autocomplete.test.ts +3 -20
  286. package/packages/pi-tui/tsconfig.tsbuildinfo +1 -1
  287. package/src/resources/extensions/gsd/auto/loop.ts +2 -24
  288. package/src/resources/extensions/gsd/auto/phases.ts +3 -3
  289. package/src/resources/extensions/gsd/auto/run-unit.ts +1 -3
  290. package/src/resources/extensions/gsd/auto/session.ts +0 -3
  291. package/src/resources/extensions/gsd/auto/types.ts +0 -1
  292. package/src/resources/extensions/gsd/auto-recovery.ts +8 -46
  293. package/src/resources/extensions/gsd/auto-start.ts +1 -1
  294. package/src/resources/extensions/gsd/auto-tool-tracking.ts +4 -2
  295. package/src/resources/extensions/gsd/auto-worktree.ts +0 -38
  296. package/src/resources/extensions/gsd/auto.ts +4 -14
  297. package/src/resources/extensions/gsd/bootstrap/db-tools.ts +13 -15
  298. package/src/resources/extensions/gsd/bootstrap/exec-tools.ts +7 -8
  299. package/src/resources/extensions/gsd/bootstrap/query-tools.ts +2 -2
  300. package/src/resources/extensions/gsd/bootstrap/register-extension.ts +9 -10
  301. package/src/resources/extensions/gsd/bootstrap/register-hooks.ts +31 -102
  302. package/src/resources/extensions/gsd/bootstrap/register-shortcuts.ts +6 -12
  303. package/src/resources/extensions/gsd/bootstrap/system-context.ts +8 -39
  304. package/src/resources/extensions/gsd/bootstrap/write-gate.ts +11 -39
  305. package/src/resources/extensions/gsd/commands/catalog.ts +5 -75
  306. package/src/resources/extensions/gsd/commands/handlers/core.ts +1 -22
  307. package/src/resources/extensions/gsd/commands-mcp-status.ts +1 -3
  308. package/src/resources/extensions/gsd/commands-prefs-wizard.ts +1 -15
  309. package/src/resources/extensions/gsd/dashboard-overlay.ts +1 -1
  310. package/src/resources/extensions/gsd/docs/preferences-reference.md +0 -4
  311. package/src/resources/extensions/gsd/doctor-runtime-checks.ts +1 -39
  312. package/src/resources/extensions/gsd/doctor-types.ts +1 -3
  313. package/src/resources/extensions/gsd/error-classifier.ts +1 -1
  314. package/src/resources/extensions/gsd/forensics.ts +2 -2
  315. package/src/resources/extensions/gsd/git-service.ts +5 -13
  316. package/src/resources/extensions/gsd/gsd-db.ts +2 -12
  317. package/src/resources/extensions/gsd/guided-flow.ts +25 -25
  318. package/src/resources/extensions/gsd/memory-store.ts +28 -81
  319. package/src/resources/extensions/gsd/model-router.ts +9 -172
  320. package/src/resources/extensions/gsd/native-git-bridge.ts +1 -7
  321. package/src/resources/extensions/gsd/preferences-models.ts +15 -101
  322. package/src/resources/extensions/gsd/preferences-types.ts +0 -6
  323. package/src/resources/extensions/gsd/preferences-validation.ts +0 -35
  324. package/src/resources/extensions/gsd/preferences.ts +2 -16
  325. package/src/resources/extensions/gsd/prompt-loader.ts +12 -26
  326. package/src/resources/extensions/gsd/slice-parallel-orchestrator.ts +3 -9
  327. package/src/resources/extensions/gsd/state.ts +0 -42
  328. package/src/resources/extensions/gsd/templates/PREFERENCES.md +0 -1
  329. package/src/resources/extensions/gsd/tests/auto-loop.test.ts +1 -178
  330. package/src/resources/extensions/gsd/tests/auto-recovery.test.ts +0 -58
  331. package/src/resources/extensions/gsd/tests/auto-session-encapsulation.test.ts +5 -9
  332. package/src/resources/extensions/gsd/tests/auto-supervisor.test.mjs +4 -21
  333. package/src/resources/extensions/gsd/tests/bootstrap-derive-state-db-open.test.ts +1 -1
  334. package/src/resources/extensions/gsd/tests/budget-prediction.test.ts +211 -138
  335. package/src/resources/extensions/gsd/tests/complete-slice-verification-gate.test.ts +59 -142
  336. package/src/resources/extensions/gsd/tests/complete-slice.test.ts +4 -7
  337. package/src/resources/extensions/gsd/tests/completed-at-reconcile.test.ts +32 -89
  338. package/src/resources/extensions/gsd/tests/copy-planning-artifacts-samepath.test.ts +22 -0
  339. package/src/resources/extensions/gsd/tests/custom-engine-loop-integration.test.ts +23 -41
  340. package/src/resources/extensions/gsd/tests/db-path-worktree-symlink.test.ts +43 -3
  341. package/src/resources/extensions/gsd/tests/debug-logger.test.ts +3 -5
  342. package/src/resources/extensions/gsd/tests/discuss-empty-db-fallback.test.ts +87 -22
  343. package/src/resources/extensions/gsd/tests/discuss-queued-milestones.test.ts +118 -7
  344. package/src/resources/extensions/gsd/tests/discuss-slice-structured-questions.test.ts +47 -0
  345. package/src/resources/extensions/gsd/tests/discuss-tool-scope-leak.test.ts +60 -18
  346. package/src/resources/extensions/gsd/tests/double-merge-guard.test.ts +76 -14
  347. package/src/resources/extensions/gsd/tests/empty-content-abort-loop.test.ts +75 -0
  348. package/src/resources/extensions/gsd/tests/false-degraded-mode-warning.test.ts +83 -22
  349. package/src/resources/extensions/gsd/tests/finalize-timeout-guard.test.ts +63 -1
  350. package/src/resources/extensions/gsd/tests/forensics-stuck-loops.test.ts +1 -26
  351. package/src/resources/extensions/gsd/tests/gsd-db.test.ts +0 -30
  352. package/src/resources/extensions/gsd/tests/headless-answers.test.ts +4 -14
  353. package/src/resources/extensions/gsd/tests/health-widget.test.ts +12 -22
  354. package/src/resources/extensions/gsd/tests/init-prefs-routing.test.ts +1 -64
  355. package/src/resources/extensions/gsd/tests/integration/auto-worktree.test.ts +0 -22
  356. package/src/resources/extensions/gsd/tests/integration/token-savings.test.ts +23 -0
  357. package/src/resources/extensions/gsd/tests/memory-store.test.ts +0 -128
  358. package/src/resources/extensions/gsd/tests/memory-tools.test.ts +1 -33
  359. package/src/resources/extensions/gsd/tests/model-router.test.ts +8 -169
  360. package/src/resources/extensions/gsd/tests/orphaned-worktree-audit.test.ts +0 -8
  361. package/src/resources/extensions/gsd/tests/parallel-crash-recovery.test.ts +43 -32
  362. package/src/resources/extensions/gsd/tests/phases-merge-error-stops-auto.test.ts +10 -4
  363. package/src/resources/extensions/gsd/tests/preferences.test.ts +0 -127
  364. package/src/resources/extensions/gsd/tests/prompt-step-ordering.test.ts +0 -16
  365. package/src/resources/extensions/gsd/tests/provider-errors.test.ts +0 -7
  366. package/src/resources/extensions/gsd/tests/quick-turn-end-cleanup.test.ts +6 -6
  367. package/src/resources/extensions/gsd/tests/session-start-footer.test.ts +19 -168
  368. package/src/resources/extensions/gsd/tests/slice-parallel-orchestrator.test.ts +1 -7
  369. package/src/resources/extensions/gsd/tests/smart-entry-complete.test.ts +1 -23
  370. package/src/resources/extensions/gsd/tests/token-profile.test.ts +4 -51
  371. package/src/resources/extensions/gsd/tests/turn-epoch.test.ts +16 -7
  372. package/src/resources/extensions/gsd/tests/unstructured-continue-context-injection.test.ts +7 -5
  373. package/src/resources/extensions/gsd/tests/uok-gitops-turn-action.test.ts +1 -15
  374. package/src/resources/extensions/gsd/tests/visualizer-overlay.test.ts +6 -6
  375. package/src/resources/extensions/gsd/tests/write-gate-planning-unit.test.ts +0 -15
  376. package/src/resources/extensions/gsd/tools/memory-tools.ts +1 -17
  377. package/src/resources/extensions/gsd/unit-context-manifest.ts +8 -8
  378. package/src/resources/extensions/gsd/visualizer-overlay.ts +1 -1
  379. package/src/resources/extensions/gsd/watch/header-renderer.ts +1 -3
  380. package/src/resources/extensions/gsd/workflow-logger.ts +0 -1
  381. package/src/resources/extensions/gsd/worktree-command.ts +44 -31
  382. package/src/resources/extensions/mcp-client/index.ts +3 -6
  383. package/src/resources/extensions/slash-commands/create-extension.ts +24 -38
  384. package/src/resources/skills/create-gsd-extension/SKILL.md +5 -9
  385. package/src/resources/skills/create-gsd-extension/references/custom-commands.md +1 -1
  386. package/src/resources/skills/create-gsd-extension/references/custom-rendering.md +5 -5
  387. package/src/resources/skills/create-gsd-extension/references/custom-tools.md +4 -4
  388. package/src/resources/skills/create-gsd-extension/references/custom-ui.md +6 -6
  389. package/src/resources/skills/create-gsd-extension/references/events-reference.md +3 -3
  390. package/src/resources/skills/create-gsd-extension/references/packaging-distribution.md +1 -1
  391. package/src/resources/skills/create-gsd-extension/references/remote-execution-overrides.md +3 -3
  392. package/src/resources/skills/create-gsd-extension/templates/extension-skeleton.ts +2 -2
  393. package/src/resources/skills/create-gsd-extension/templates/stateful-tool-skeleton.ts +3 -3
  394. package/src/resources/skills/create-gsd-extension/workflows/create-extension.md +12 -32
  395. package/dist/cli-policy.d.ts +0 -13
  396. package/dist/cli-policy.js +0 -17
  397. package/dist/resources/.managed-resources-content-hash +0 -1
  398. package/dist/resources/extensions/gsd/auto-runtime-state.js +0 -31
  399. package/dist/resources/extensions/gsd/milestone-id-reservation.js +0 -36
  400. package/dist/resources/extensions/gsd/worktree-session-state.js +0 -33
  401. package/dist/runtime-checks.d.ts +0 -27
  402. package/dist/runtime-checks.js +0 -38
  403. package/dist/web/standalone/.next/static/chunks/2556.0527fea66e123b7f.js +0 -1
  404. package/dist/web/standalone/.next/static/chunks/2824.08296bc2f9654698.js +0 -1
  405. package/dist/web/standalone/.next/static/chunks/3026.3af53b279375f082.js +0 -1
  406. package/dist/web/standalone/.next/static/chunks/315.6f68ae79b67d25cf.js +0 -1
  407. package/dist/web/standalone/.next/static/chunks/3497.4bfc60a3b3dea717.js +0 -1
  408. package/dist/web/standalone/.next/static/chunks/5516.4a07c872b5c3a663.js +0 -1
  409. package/dist/web/standalone/.next/static/chunks/8336.31b019697882acfb.js +0 -10
  410. package/dist/web/standalone/.next/static/chunks/8845.c9702695e8c5a9c5.js +0 -2
  411. package/dist/web/standalone/.next/static/chunks/9058.01ef3a463bda88f1.js +0 -20
  412. package/dist/web/standalone/.next/static/chunks/9441.1081da1125d1764f.js +0 -1
  413. package/dist/web/standalone/.next/static/chunks/app/page-9bf2e0c50fb2ca05.js +0 -1
  414. package/dist/web/standalone/.next/static/chunks/main-app-fdab67f7802d7832.js +0 -1
  415. package/dist/web/standalone/.next/static/chunks/next/dist/client/components/builtin/global-error-459824ffb8c323dd.js +0 -1
  416. package/dist/web/standalone/.next/static/chunks/webpack-f9f0dc45e4f3ac10.js +0 -1
  417. package/dist/worktree-status-banner.d.ts +0 -1
  418. package/dist/worktree-status-banner.js +0 -132
  419. package/packages/mcp-server/dist/alias-telemetry.d.ts +0 -8
  420. package/packages/mcp-server/dist/alias-telemetry.d.ts.map +0 -1
  421. package/packages/mcp-server/dist/alias-telemetry.js +0 -30
  422. package/packages/mcp-server/dist/alias-telemetry.js.map +0 -1
  423. package/packages/mcp-server/src/alias-telemetry.test.ts +0 -78
  424. package/packages/mcp-server/src/alias-telemetry.ts +0 -30
  425. package/packages/pi-ai/dist/providers/anthropic-shared.cache-breakpoint.test.d.ts +0 -2
  426. package/packages/pi-ai/dist/providers/anthropic-shared.cache-breakpoint.test.d.ts.map +0 -1
  427. package/packages/pi-ai/dist/providers/anthropic-shared.cache-breakpoint.test.js +0 -231
  428. package/packages/pi-ai/dist/providers/anthropic-shared.cache-breakpoint.test.js.map +0 -1
  429. package/packages/pi-ai/src/providers/anthropic-shared.cache-breakpoint.test.ts +0 -289
  430. package/packages/pi-coding-agent/dist/core/token-telemetry.d.ts +0 -37
  431. package/packages/pi-coding-agent/dist/core/token-telemetry.d.ts.map +0 -1
  432. package/packages/pi-coding-agent/dist/core/token-telemetry.js +0 -49
  433. package/packages/pi-coding-agent/dist/core/token-telemetry.js.map +0 -1
  434. package/packages/pi-coding-agent/dist/modes/interactive/components/tool-card-cleanup-and-success-runtime.test.d.ts +0 -2
  435. package/packages/pi-coding-agent/dist/modes/interactive/components/tool-card-cleanup-and-success-runtime.test.d.ts.map +0 -1
  436. package/packages/pi-coding-agent/dist/modes/interactive/components/tool-card-cleanup-and-success-runtime.test.js +0 -133
  437. package/packages/pi-coding-agent/dist/modes/interactive/components/tool-card-cleanup-and-success-runtime.test.js.map +0 -1
  438. package/packages/pi-coding-agent/dist/tests/system-prompt-cache-stability.test.d.ts +0 -2
  439. package/packages/pi-coding-agent/dist/tests/system-prompt-cache-stability.test.d.ts.map +0 -1
  440. package/packages/pi-coding-agent/dist/tests/system-prompt-cache-stability.test.js +0 -78
  441. package/packages/pi-coding-agent/dist/tests/system-prompt-cache-stability.test.js.map +0 -1
  442. package/packages/pi-coding-agent/dist/tests/token-telemetry.test.d.ts +0 -2
  443. package/packages/pi-coding-agent/dist/tests/token-telemetry.test.d.ts.map +0 -1
  444. package/packages/pi-coding-agent/dist/tests/token-telemetry.test.js +0 -181
  445. package/packages/pi-coding-agent/dist/tests/token-telemetry.test.js.map +0 -1
  446. package/packages/pi-coding-agent/src/core/token-telemetry.ts +0 -77
  447. package/packages/pi-coding-agent/src/modes/interactive/components/tool-card-cleanup-and-success-runtime.test.ts +0 -212
  448. package/packages/pi-coding-agent/src/tests/system-prompt-cache-stability.test.ts +0 -102
  449. package/packages/pi-coding-agent/src/tests/token-telemetry.test.ts +0 -200
  450. package/packages/pi-tui/dist/components/__tests__/leak-fixes-runtime.test.d.ts +0 -2
  451. package/packages/pi-tui/dist/components/__tests__/leak-fixes-runtime.test.d.ts.map +0 -1
  452. package/packages/pi-tui/dist/components/__tests__/leak-fixes-runtime.test.js +0 -161
  453. package/packages/pi-tui/dist/components/__tests__/leak-fixes-runtime.test.js.map +0 -1
  454. package/packages/pi-tui/src/components/__tests__/leak-fixes-runtime.test.ts +0 -219
  455. package/src/resources/extensions/gsd/auto-runtime-state.ts +0 -51
  456. package/src/resources/extensions/gsd/milestone-id-reservation.ts +0 -47
  457. package/src/resources/extensions/gsd/tests/deferred-milestone-dir-4996.test.ts +0 -116
  458. package/src/resources/extensions/gsd/tests/doctor-orphan-milestone-4996.test.ts +0 -100
  459. package/src/resources/extensions/gsd/tests/ensure-preconditions-guard-4996.test.ts +0 -93
  460. package/src/resources/extensions/gsd/tests/find-missing-summaries-closed-runtime.test.ts +0 -47
  461. package/src/resources/extensions/gsd/tests/gitignore-bg-shell-runtime.test.ts +0 -63
  462. package/src/resources/extensions/gsd/tests/gsd-no-project-error-runtime.test.ts +0 -81
  463. package/src/resources/extensions/gsd/tests/help-menu-coverage.test.ts +0 -57
  464. package/src/resources/extensions/gsd/tests/import-done-milestones-runtime.test.ts +0 -145
  465. package/src/resources/extensions/gsd/tests/merge-self-branch-guard.test.ts +0 -124
  466. package/src/resources/extensions/gsd/tests/milestone-id-gap-reuse-4996.test.ts +0 -152
  467. package/src/resources/extensions/gsd/tests/native-git-infra-errors.test.ts +0 -50
  468. package/src/resources/extensions/gsd/tests/register-hooks-compaction-checkpoint.test.ts +0 -93
  469. package/src/resources/extensions/gsd/tests/system-context-message-routing.test.ts +0 -101
  470. package/src/resources/extensions/gsd/worktree-session-state.ts +0 -35
  471. package/src/resources/extensions/mcp-client/tests/global-config.test.ts +0 -91
  472. package/src/resources/skills/create-gsd-extension/templates/templates.test.ts +0 -58
  473. /package/dist/web/standalone/.next/static/{UF5VF4F1tB0miEtJS7LyX → 7afp7gq8-DVbxum83zRQ-}/_buildManifest.js +0 -0
  474. /package/dist/web/standalone/.next/static/{UF5VF4F1tB0miEtJS7LyX → 7afp7gq8-DVbxum83zRQ-}/_ssgManifest.js +0 -0
@@ -1,14 +1,22 @@
1
1
  import { join } from "node:path";
2
2
  import { isToolCallEventType } from "@gsd/pi-coding-agent";
3
3
  import { updateSnapshot } from "../ecosystem/gsd-extension-api.js";
4
+ import { getEcosystemReadyPromise } from "../ecosystem/loader.js";
4
5
  import { buildMilestoneFileName, resolveMilestonePath, resolveSliceFile, resolveSlicePath } from "../paths.js";
5
- import { clearDiscussionFlowState, isDepthConfirmationAnswer, isQueuePhaseActive, markDepthVerified, resetWriteGateState, shouldBlockContextWrite, shouldBlockPlanningUnit, shouldBlockQueueExecution, isGateQuestionId, setPendingGate, clearPendingGate, getPendingGate, shouldBlockPendingGate, shouldBlockPendingGateBash, extractDepthVerificationMilestoneId } from "./write-gate.js";
6
- import { resolveManifest } from "../unit-context-manifest.js";
6
+ import { buildBeforeAgentStartResult } from "./system-context.js";
7
+ import { handleAgentEnd } from "./agent-end-recovery.js";
8
+ import { clearDiscussionFlowState, isDepthConfirmationAnswer, isQueuePhaseActive, markDepthVerified, resetWriteGateState, shouldBlockContextWrite, shouldBlockQueueExecution, isGateQuestionId, setPendingGate, clearPendingGate, getPendingGate, shouldBlockPendingGate, shouldBlockPendingGateBash, extractDepthVerificationMilestoneId } from "./write-gate.js";
7
9
  import { isBlockedStateFile, isBashWriteToStateFile, BLOCKED_WRITE_ERROR } from "../write-intercept.js";
10
+ import { cleanupQuickBranch } from "../quick.js";
11
+ import { getDiscussionMilestoneId } from "../guided-flow.js";
12
+ import { loadToolApiKeys } from "../commands-config.js";
8
13
  import { loadFile, saveFile, formatContinue } from "../files.js";
9
- import { getAutoRuntimeSnapshot, isAutoActive, isAutoPaused, markToolEnd, markToolStart, recordToolInvocationError } from "../auto-runtime-state.js";
14
+ import { deriveState } from "../state.js";
15
+ import { getAutoDashboardData, isAutoActive, isAutoPaused, markToolEnd, markToolStart, recordToolInvocationError } from "../auto.js";
16
+ import { isParallelActive, shutdownParallel } from "../parallel-orchestrator.js";
10
17
  import { checkToolCallLoop, resetToolCallLoopGuard } from "./tool-call-loop-guard.js";
11
18
  import { saveActivityLog } from "../activity-log.js";
19
+ import { resetAskUserQuestionsCache } from "../../ask-user-questions.js";
12
20
  import { recordToolCall as safetyRecordToolCall, recordToolResult as safetyRecordToolResult, saveEvidenceToDisk } from "../safety/evidence-collector.js";
13
21
  import { parseUnitId } from "../unit-id.js";
14
22
  import { classifyCommand } from "../safety/destructive-guard.js";
@@ -16,52 +24,26 @@ import { logWarning as safetyLogWarning } from "../workflow-logger.js";
16
24
  import { installNotifyInterceptor } from "./notify-interceptor.js";
17
25
  import { initNotificationStore } from "../notification-store.js";
18
26
  import { initNotificationWidget } from "../notification-widget.js";
27
+ import { initHealthWidget } from "../health-widget.js";
19
28
  // Skip the welcome screen on the very first session_start — cli.ts already
20
29
  // printed it before the TUI launched. Only re-print on /clear (subsequent sessions).
21
30
  let isFirstSession = true;
22
- async function deriveGsdState(basePath) {
23
- const { deriveState } = await import("../state.js");
24
- return deriveState(basePath);
25
- }
26
- async function getDiscussionMilestoneIdFor(basePath) {
27
- const { getDiscussionMilestoneId } = await import("../guided-flow.js");
28
- return getDiscussionMilestoneId(basePath);
29
- }
30
- async function loadToolApiKeysForSession() {
31
- const { loadToolApiKeys } = await import("../commands-config.js");
32
- loadToolApiKeys();
33
- }
34
- async function resetAskUserQuestionsTurnCache() {
35
- const { resetAskUserQuestionsCache } = await import("../../ask-user-questions.js");
36
- resetAskUserQuestionsCache();
37
- }
38
31
  async function syncServiceTierStatus(ctx) {
39
32
  const { getEffectiveServiceTier, formatServiceTierFooterStatus } = await import("../service-tier.js");
40
33
  ctx.ui.setStatus("gsd-fast", formatServiceTierFooterStatus(getEffectiveServiceTier(), ctx.model?.id));
41
34
  }
42
- async function applyDisabledModelProviderPolicy(ctx) {
43
- try {
44
- const { resolveDisabledModelProvidersFromPreferences } = await import("../preferences.js");
45
- ctx.modelRegistry.setDisabledModelProviders(resolveDisabledModelProvidersFromPreferences());
46
- }
47
- catch {
48
- // Non-fatal: keep default provider visibility if preferences cannot be loaded.
49
- }
50
- }
51
35
  export function registerHooks(pi, ecosystemHandlers) {
52
36
  pi.on("session_start", async (_event, ctx) => {
53
37
  initNotificationStore(process.cwd());
54
38
  installNotifyInterceptor(ctx);
55
39
  initNotificationWidget(ctx);
56
40
  if (!isAutoActive()) {
57
- const { initHealthWidget } = await import("../health-widget.js");
58
41
  initHealthWidget(ctx);
59
42
  }
60
43
  resetWriteGateState();
61
44
  resetToolCallLoopGuard();
62
- await resetAskUserQuestionsTurnCache();
45
+ resetAskUserQuestionsCache();
63
46
  await syncServiceTierStatus(ctx);
64
- await applyDisabledModelProviderPolicy(ctx);
65
47
  // Skip MCP auto-prep when running inside an auto-worktree (see session_switch below).
66
48
  const { isInAutoWorktree } = await import("../auto-worktree.js");
67
49
  if (!isInAutoWorktree(process.cwd())) {
@@ -97,7 +79,7 @@ export function registerHooks(pi, ecosystemHandlers) {
97
79
  }
98
80
  catch { /* non-fatal */ }
99
81
  }
100
- await loadToolApiKeysForSession();
82
+ loadToolApiKeys();
101
83
  if (isAutoActive()) {
102
84
  ctx.ui.setWidget("gsd-health", undefined);
103
85
  }
@@ -107,10 +89,9 @@ export function registerHooks(pi, ecosystemHandlers) {
107
89
  installNotifyInterceptor(ctx);
108
90
  resetWriteGateState();
109
91
  resetToolCallLoopGuard();
110
- await resetAskUserQuestionsTurnCache();
92
+ resetAskUserQuestionsCache();
111
93
  clearDiscussionFlowState();
112
94
  await syncServiceTierStatus(ctx);
113
- await applyDisabledModelProviderPolicy(ctx);
114
95
  // Skip MCP auto-prep when running inside an auto-worktree. The worktree
115
96
  // already has .mcp.json from createAutoWorktree, and re-running the writer
116
97
  // post-chdir rewrites the file mid-run (non-idempotent due to cwd-relative
@@ -120,26 +101,20 @@ export function registerHooks(pi, ecosystemHandlers) {
120
101
  const { prepareWorkflowMcpForProject } = await import("../workflow-mcp-auto-prep.js");
121
102
  prepareWorkflowMcpForProject(ctx, process.cwd());
122
103
  }
123
- await loadToolApiKeysForSession();
124
- if (!isAutoActive()) {
125
- const { initHealthWidget } = await import("../health-widget.js");
126
- initHealthWidget(ctx);
127
- }
128
- else {
104
+ loadToolApiKeys();
105
+ if (isAutoActive()) {
129
106
  ctx.ui.setWidget("gsd-health", undefined);
130
107
  }
131
108
  });
132
109
  pi.on("before_agent_start", async (event, ctx) => {
133
110
  // Wait for ecosystem loader to finish (no-op after first turn).
134
- const { getEcosystemReadyPromise } = await import("../ecosystem/loader.js");
135
111
  await getEcosystemReadyPromise();
136
112
  // GSD's own context injection (existing behavior — unchanged).
137
- const { buildBeforeAgentStartResult } = await import("./system-context.js");
138
113
  const gsdResult = await buildBeforeAgentStartResult(event, ctx);
139
114
  // Refresh the snapshot used by ecosystem getPhase()/getActiveUnit().
140
115
  // deriveState has its own ~100ms cache so this is cheap on repeat calls.
141
116
  try {
142
- const state = await deriveGsdState(process.cwd());
117
+ const state = await deriveState(process.cwd());
143
118
  updateSnapshot(state);
144
119
  }
145
120
  catch {
@@ -173,8 +148,7 @@ export function registerHooks(pi, ecosystemHandlers) {
173
148
  });
174
149
  pi.on("agent_end", async (event, ctx) => {
175
150
  resetToolCallLoopGuard();
176
- await resetAskUserQuestionsTurnCache();
177
- const { handleAgentEnd } = await import("./agent-end-recovery.js");
151
+ resetAskUserQuestionsCache();
178
152
  await handleAgentEnd(pi, event, ctx);
179
153
  });
180
154
  // Squash-merge quick-task branch back to the original branch after the
@@ -182,7 +156,6 @@ export function registerHooks(pi, ecosystemHandlers) {
182
156
  // quick-return state is pending, so this is safe to call on every turn.
183
157
  pi.on("turn_end", async () => {
184
158
  try {
185
- const { cleanupQuickBranch } = await import("../quick.js");
186
159
  cleanupQuickBranch();
187
160
  }
188
161
  catch {
@@ -199,8 +172,8 @@ export function registerHooks(pi, ecosystemHandlers) {
199
172
  const basePath = process.cwd();
200
173
  const { ensureDbOpen } = await import("./dynamic-tools.js");
201
174
  await ensureDbOpen();
202
- const state = await deriveGsdState(basePath);
203
- if (!state.activeMilestone || !state.activeSlice)
175
+ const state = await deriveState(basePath);
176
+ if (!state.activeMilestone || !state.activeSlice || !state.activeTask)
204
177
  return;
205
178
  // Write checkpoint for ALL phases, not just "executing" — discuss, research,
206
179
  // and planning also carry in-memory state (user answers, gate verification)
@@ -216,30 +189,21 @@ export function registerHooks(pi, ecosystemHandlers) {
216
189
  if (await loadFile(legacyContinue))
217
190
  return;
218
191
  const continuePath = join(sliceDir, `${state.activeSlice.id}-CONTINUE.md`);
219
- const taskId = state.activeTask?.id ?? "none";
220
- const taskTitle = state.activeTask?.title ?? "";
221
- const phaseLabel = state.phase.replace(/-/g, " ");
222
192
  await saveFile(continuePath, formatContinue({
223
193
  frontmatter: {
224
194
  milestone: state.activeMilestone.id,
225
195
  slice: state.activeSlice.id,
226
- task: taskId,
196
+ task: state.activeTask.id,
227
197
  step: 0,
228
198
  totalSteps: 0,
229
199
  status: "compacted",
230
200
  savedAt: new Date().toISOString(),
231
201
  },
232
- completedWork: state.activeTask
233
- ? `Task ${taskId} (${taskTitle}) was in progress when compaction occurred.`
234
- : `Slice ${state.activeSlice.id} was in ${phaseLabel} phase when compaction occurred.`,
235
- remainingWork: state.activeTask
236
- ? "Check the task plan for remaining steps."
237
- : "Continue this slice from the latest planning/research/discussion artifacts.",
202
+ completedWork: `Task ${state.activeTask.id} (${state.activeTask.title}) was in progress when compaction occurred.`,
203
+ remainingWork: "Check the task plan for remaining steps.",
238
204
  decisions: "Check task summary files for prior decisions.",
239
205
  context: "Session was auto-compacted by Pi. Resume with /gsd.",
240
- nextAction: state.activeTask
241
- ? `Resume task ${taskId}: ${taskTitle}.`
242
- : `Resume ${phaseLabel} work for slice ${state.activeSlice.id}.`,
206
+ nextAction: `Resume task ${state.activeTask.id}: ${state.activeTask.title}.`,
243
207
  }));
244
208
  });
245
209
  // Context-mode snapshot: write .gsd/last-snapshot.md before compaction so
@@ -261,7 +225,7 @@ export function registerHooks(pi, ecosystemHandlers) {
261
225
  const basePath = process.cwd();
262
226
  let activeContext = null;
263
227
  try {
264
- const state = await deriveGsdState(basePath);
228
+ const state = await deriveState(basePath);
265
229
  if (state.activeMilestone && state.activeSlice && state.activeTask) {
266
230
  activeContext =
267
231
  `Active: ${state.activeMilestone.id} / ${state.activeSlice.id} / ${state.activeTask.id}` +
@@ -278,7 +242,6 @@ export function registerHooks(pi, ecosystemHandlers) {
278
242
  }
279
243
  });
280
244
  pi.on("session_shutdown", async (_event, ctx) => {
281
- const { isParallelActive, shutdownParallel } = await import("../parallel-orchestrator.js");
282
245
  if (isParallelActive()) {
283
246
  try {
284
247
  await shutdownParallel(process.cwd());
@@ -289,7 +252,7 @@ export function registerHooks(pi, ecosystemHandlers) {
289
252
  }
290
253
  if (!isAutoActive() && !isAutoPaused())
291
254
  return;
292
- const dash = getAutoRuntimeSnapshot();
255
+ const dash = getAutoDashboardData();
293
256
  if (dash.currentUnit) {
294
257
  saveActivityLog(ctx, dash.basePath, dash.currentUnit.type, dash.currentUnit.id);
295
258
  }
@@ -315,7 +278,7 @@ export function registerHooks(pi, ecosystemHandlers) {
315
278
  // If ask_user_questions was called with a gate ID but hasn't been confirmed,
316
279
  // block all non-read-only tool calls to prevent the model from skipping gates.
317
280
  if (getPendingGate()) {
318
- const milestoneId = await getDiscussionMilestoneIdFor(discussionBasePath);
281
+ const milestoneId = getDiscussionMilestoneId(discussionBasePath);
319
282
  if (isToolCallEventType("bash", event)) {
320
283
  const bashGuard = shouldBlockPendingGateBash(event.input.command, milestoneId, isQueuePhaseActive());
321
284
  if (bashGuard.block)
@@ -346,32 +309,6 @@ export function registerHooks(pi, ecosystemHandlers) {
346
309
  if (queueGuard.block)
347
310
  return queueGuard;
348
311
  }
349
- // ── Planning-unit tools-policy enforcement (#4934): runtime half ─────
350
- // The active auto-mode unit's manifest declares a ToolsPolicy. For
351
- // planning/docs/read-only modes, deny writes outside .gsd/ (or the
352
- // manifest's allowedPathGlobs), bash that isn't read-only, and
353
- // subagent dispatch. Closes the b23 bug class where a discuss-milestone
354
- // turn used the host Edit tool to modify user source files.
355
- const dash = getAutoRuntimeSnapshot();
356
- const activeUnitType = dash.currentUnit?.type;
357
- if (activeUnitType) {
358
- const manifest = resolveManifest(activeUnitType);
359
- if (manifest) {
360
- let planningInput = "";
361
- if (isToolCallEventType("write", event)) {
362
- planningInput = event.input.path;
363
- }
364
- else if (isToolCallEventType("edit", event)) {
365
- planningInput = event.input.path;
366
- }
367
- else if (isToolCallEventType("bash", event)) {
368
- planningInput = event.input.command;
369
- }
370
- const planningGuard = shouldBlockPlanningUnit(event.toolName, planningInput, dash.basePath || discussionBasePath, activeUnitType, manifest.tools);
371
- if (planningGuard.block)
372
- return planningGuard;
373
- }
374
- }
375
312
  // ── Single-writer engine: block direct writes to STATE.md ──────────
376
313
  // Covers write, edit, and bash tools to prevent bypass vectors.
377
314
  if (isToolCallEventType("write", event)) {
@@ -391,7 +328,7 @@ export function registerHooks(pi, ecosystemHandlers) {
391
328
  }
392
329
  if (!isToolCallEventType("write", event))
393
330
  return;
394
- const result = shouldBlockContextWrite(event.toolName, event.input.path, await getDiscussionMilestoneIdFor(discussionBasePath), isQueuePhaseActive());
331
+ const result = shouldBlockContextWrite(event.toolName, event.input.path, getDiscussionMilestoneId(discussionBasePath), isQueuePhaseActive());
395
332
  if (result.block)
396
333
  return result;
397
334
  });
@@ -431,7 +368,7 @@ export function registerHooks(pi, ecosystemHandlers) {
431
368
  }
432
369
  if (event.toolName !== "ask_user_questions")
433
370
  return;
434
- const milestoneId = await getDiscussionMilestoneIdFor(process.cwd());
371
+ const milestoneId = getDiscussionMilestoneId(process.cwd());
435
372
  const queueActive = isQueuePhaseActive();
436
373
  const details = event.details;
437
374
  // ── Discussion gate enforcement: handle gate question responses ──
@@ -527,7 +464,7 @@ export function registerHooks(pi, ecosystemHandlers) {
527
464
  safetyRecordToolResult(event.toolCallId, event.toolName, event.result, event.isError);
528
465
  // Persist evidence to disk after each tool result so it survives a session
529
466
  // restart mid-unit (Bug #4385 — non-persisted evidence false positives).
530
- const dash = getAutoRuntimeSnapshot();
467
+ const dash = getAutoDashboardData();
531
468
  if (dash.basePath && dash.currentUnit?.type === "execute-task") {
532
469
  const { milestone: pMid, slice: pSid, task: pTid } = parseUnitId(dash.currentUnit.id);
533
470
  if (pMid && pSid && pTid) {
@@ -1,12 +1,12 @@
1
1
  import { existsSync } from "node:fs";
2
2
  import { join } from "node:path";
3
3
  import { Key } from "@gsd/pi-tui";
4
+ import { GSDDashboardOverlay } from "../dashboard-overlay.js";
5
+ import { GSDNotificationOverlay } from "../notification-overlay.js";
6
+ import { ParallelMonitorOverlay } from "../parallel-monitor-overlay.js";
4
7
  import { GSD_SHORTCUTS } from "../shortcut-defs.js";
8
+ import { projectRoot } from "../commands/context.js";
5
9
  import { shortcutDesc } from "../../shared/mod.js";
6
- async function getProjectRoot() {
7
- const { projectRoot } = await import("../commands/context.js");
8
- return projectRoot();
9
- }
10
10
  export function registerShortcuts(pi) {
11
11
  const overlayOptions = {
12
12
  width: "90%",
@@ -15,10 +15,7 @@ export function registerShortcuts(pi) {
15
15
  anchor: "center",
16
16
  };
17
17
  const openDashboardOverlay = async (ctx) => {
18
- const [{ GSDDashboardOverlay }, basePath] = await Promise.all([
19
- import("../dashboard-overlay.js"),
20
- getProjectRoot(),
21
- ]);
18
+ const basePath = projectRoot();
22
19
  if (!existsSync(join(basePath, ".gsd"))) {
23
20
  ctx.ui.notify("No .gsd/ directory found. Run /gsd to start.", "info");
24
21
  return;
@@ -29,7 +26,6 @@ export function registerShortcuts(pi) {
29
26
  });
30
27
  };
31
28
  const openNotificationsOverlay = async (ctx) => {
32
- const { GSDNotificationOverlay } = await import("../notification-overlay.js");
33
29
  await ctx.ui.custom((tui, theme, _kb, done) => new GSDNotificationOverlay(tui, theme, () => done(true)), {
34
30
  overlay: true,
35
31
  overlayOptions: {
@@ -42,13 +38,12 @@ export function registerShortcuts(pi) {
42
38
  });
43
39
  };
44
40
  const openParallelOverlay = async (ctx) => {
45
- const basePath = await getProjectRoot();
41
+ const basePath = projectRoot();
46
42
  const parallelDir = join(basePath, ".gsd", "parallel");
47
43
  if (!existsSync(parallelDir)) {
48
44
  ctx.ui.notify("No parallel workers found. Run /gsd parallel start first.", "info");
49
45
  return;
50
46
  }
51
- const { ParallelMonitorOverlay } = await import("../parallel-monitor-overlay.js");
52
47
  await ctx.ui.custom((tui, theme, _kb, done) => new ParallelMonitorOverlay(tui, theme, () => done(true), basePath), {
53
48
  overlay: true,
54
49
  overlayOptions,
@@ -12,7 +12,7 @@ import { resolveGsdRootFile, resolveSliceFile, resolveSlicePath, resolveTaskFile
12
12
  import { ensureCodebaseMapFresh, readCodebaseMap } from "../codebase-generator.js";
13
13
  import { hasSkillSnapshot, detectNewSkills, formatSkillsXml } from "../skill-discovery.js";
14
14
  import { getActiveAutoWorktreeContext } from "../auto-worktree.js";
15
- import { getActiveWorktreeName, getWorktreeOriginalCwd } from "../worktree-session-state.js";
15
+ import { getActiveWorktreeName, getWorktreeOriginalCwd } from "../worktree-command.js";
16
16
  import { deriveState } from "../state.js";
17
17
  import { formatOverridesSection, formatShortcut, loadActiveOverrides, loadFile, parseContinue, parseSummary } from "../files.js";
18
18
  import { toPosixPath } from "../../shared/mod.js";
@@ -177,50 +177,24 @@ export async function buildBeforeAgentStartResult(event, ctx) {
177
177
  const subagentModelBlock = subagentModelConfig
178
178
  ? `\n\n## Subagent Model\n\nWhen spawning subagents via the \`subagent\` tool, always pass \`model: "${subagentModelConfig.primary}"\` in the tool call parameters. Never omit this — always specify it explicitly.`
179
179
  : "";
180
- // memoryBlock is FTS-queried against the user prompt and changes per call.
181
- // Removing it from `fullSystem` keeps the system-prompt cache breakpoint
182
- // stable across calls — the only scoped goal of this fix. The pi-ai
183
- // Anthropic adapter additionally cache-marks the last user turn, so the
184
- // memoryBlock injected via the context message may itself be cached up to
185
- // that boundary; that's orthogonal and unchanged from prior behavior. The
186
- // load-bearing win here is preserving the system+tools cache hit. (#5019)
187
- const fullSystem = `${event.systemPrompt}\n\n[SYSTEM CONTEXT — GSD]\n\n${systemContent}${preferenceBlock}${knowledgeBlock}${codebaseBlock}${newSkillsBlock}${worktreeBlock}${subagentModelBlock}`;
180
+ const fullSystem = `${event.systemPrompt}\n\n[SYSTEM CONTEXT GSD]\n\n${systemContent}${preferenceBlock}${knowledgeBlock}${codebaseBlock}${memoryBlock}${newSkillsBlock}${worktreeBlock}${subagentModelBlock}`;
188
181
  stopContextTimer({
189
182
  systemPromptSize: fullSystem.length,
190
183
  injectionSize: injection?.length ?? forensicsInjection?.length ?? 0,
191
184
  hasPreferences: preferenceBlock.length > 0,
192
185
  hasNewSkills: newSkillsBlock.length > 0,
193
186
  });
194
- const contextMessage = buildContextMessage({ memoryBlock, injection, forensicsInjection });
187
+ // Determine which context message to inject (guided execute takes priority)
188
+ const contextMessage = injection
189
+ ? { customType: "gsd-guided-context", content: injection, display: false }
190
+ : forensicsInjection
191
+ ? { customType: "gsd-forensics", content: forensicsInjection, display: false }
192
+ : null;
195
193
  return {
196
194
  systemPrompt: fullSystem,
197
195
  ...(contextMessage ? { message: contextMessage } : {}),
198
196
  };
199
197
  }
200
- /**
201
- * Route the per-call dynamic blocks (memory, guided-execute, forensics) into a
202
- * single user-message context payload so they ride the volatile suffix instead
203
- * of the cached system prefix. Priority when both memory and an injection are
204
- * present: guided > forensics > memory-only. (#5019)
205
- *
206
- * Exported for direct unit testing — the surrounding bootstrap has too many
207
- * filesystem and DB dependencies to exercise this routing logic in-place.
208
- */
209
- export function buildContextMessage(opts) {
210
- const memoryContent = opts.memoryBlock.trim();
211
- if (opts.injection) {
212
- const content = memoryContent ? `${memoryContent}\n\n${opts.injection}` : opts.injection;
213
- return { customType: "gsd-guided-context", content, display: false };
214
- }
215
- if (opts.forensicsInjection) {
216
- const content = memoryContent ? `${memoryContent}\n\n${opts.forensicsInjection}` : opts.forensicsInjection;
217
- return { customType: "gsd-forensics", content, display: false };
218
- }
219
- if (memoryContent) {
220
- return { customType: "gsd-memory", content: memoryContent, display: false };
221
- }
222
- return null;
223
- }
224
198
  /**
225
199
  * ADR-013 step 4 — auto-injection parity for the memories table.
226
200
  *
@@ -441,31 +441,8 @@ export function shouldBlockQueueExecutionInSnapshot(snapshot, toolName, input, q
441
441
  };
442
442
  }
443
443
  // ─── Planning-unit tools-policy enforcement (#4934) ───────────────────────
444
- //
445
- // Runtime half of the declarative ToolsPolicy on UnitContextManifest. The
446
- // manifest assigns each unit type a tools mode; this predicate is what
447
- // actually rejects a tool call that violates it.
448
- //
449
- // Forensics: a discuss-milestone LLM turn used the host Edit tool to modify
450
- // index.html in test app b23 (~/Github/test-apps/b23). With this predicate
451
- // wired into the tool_call hook, the same call returns block=true with a
452
- // HARD BLOCK reason that the model cannot rationalize past.
453
- //
454
- // Activation: the hook supplies the policy resolved from the active unit's
455
- // manifest. When no unit is active (interactive sessions, unknown unit
456
- // types), the hook passes null and this predicate is a no-op — falling
457
- // through to the existing pendingGate / queue-execution / context-write
458
- // guards.
459
444
  const PLANNING_WRITE_TOOLS = new Set(["write", "edit", "multi_edit", "notebook_edit"]);
460
445
  const PLANNING_SUBAGENT_TOOLS = new Set(["subagent", "task"]);
461
- /**
462
- * Read-only / planning-safe tools that any non-"all" mode allows. Mirrors
463
- * QUEUE_SAFE_TOOLS / GATE_SAFE_TOOLS but is the inclusive default for
464
- * planning units (which need their full discussion + research surface).
465
- *
466
- * gsd_* MCP tools are passed through unconditionally — they have their own
467
- * domain validation (e.g. depth-verification gate, single-writer DB).
468
- */
469
446
  const PLANNING_SAFE_TOOLS = new Set([
470
447
  "read", "grep", "find", "ls", "glob",
471
448
  "ask_user_questions",
@@ -481,7 +458,6 @@ function matchesAllowedGlob(absPath, basePath, globs) {
481
458
  const rel = relative(basePath, absPath);
482
459
  if (rel.startsWith("..") || isAbsolute(rel))
483
460
  return false;
484
- // Normalize Windows separators for minimatch.
485
461
  const posix = rel.split(sep).join("/");
486
462
  return globs.some(g => minimatch(posix, g, { dot: false, nocase: false }));
487
463
  }
@@ -504,12 +480,7 @@ function blockReason(unitType, mode, what) {
504
480
  * - "docs" → like "planning" but also allows writes to paths
505
481
  * matching `allowedPathGlobs` relative to basePath.
506
482
  *
507
- * `pathOrCommand` is the file path for write/edit-shaped tools and the
508
- * shell command for bash. Other tools ignore this argument.
509
- *
510
- * `policy` of null means "no manifest resolved" — pass-through. Callers
511
- * that have no active unit (interactive sessions) pass null and this
512
- * predicate is a no-op.
483
+ * `policy` of null means "no manifest resolved" pass-through.
513
484
  */
514
485
  export function shouldBlockPlanningUnit(toolName, pathOrCommand, basePath, unitType, policy) {
515
486
  if (!policy)
@@ -517,7 +488,6 @@ export function shouldBlockPlanningUnit(toolName, pathOrCommand, basePath, unitT
517
488
  if (policy.mode === "all")
518
489
  return { block: false };
519
490
  const tool = toolName;
520
- // Read-only mode: only Read-class tools are permitted.
521
491
  if (policy.mode === "read-only") {
522
492
  if (PLANNING_SAFE_TOOLS.has(tool))
523
493
  return { block: false };
@@ -526,10 +496,9 @@ export function shouldBlockPlanningUnit(toolName, pathOrCommand, basePath, unitT
526
496
  if (PLANNING_WRITE_TOOLS.has(tool) || tool === "bash" || PLANNING_SUBAGENT_TOOLS.has(tool)) {
527
497
  return { block: true, reason: blockReason(unitType, policy.mode, `${tool} is not permitted (read-only)`) };
528
498
  }
529
- // Unknown tool in read-only mode — block by default.
530
499
  return { block: true, reason: blockReason(unitType, policy.mode, `tool "${tool}" is not on the read-only allowlist`) };
531
500
  }
532
- // planning / docs modes share the same surface for safe tools, bash, and subagent.
501
+ // planning / docs modes
533
502
  if (PLANNING_SAFE_TOOLS.has(tool))
534
503
  return { block: false };
535
504
  if (tool.startsWith("gsd_"))
@@ -550,10 +519,8 @@ export function shouldBlockPlanningUnit(toolName, pathOrCommand, basePath, unitT
550
519
  return { block: true, reason: blockReason(unitType, policy.mode, `${tool} called with empty path`) };
551
520
  }
552
521
  const absPath = isAbsolute(pathOrCommand) ? pathOrCommand : resolve(basePath, pathOrCommand);
553
- // Always allow .gsd/ writes — that's where planning artifacts live.
554
522
  if (isPathUnderGsd(absPath, basePath))
555
523
  return { block: false };
556
- // docs mode additionally allows the manifest's allowedPathGlobs.
557
524
  if (policy.mode === "docs" && matchesAllowedGlob(absPath, basePath, policy.allowedPathGlobs)) {
558
525
  return { block: false };
559
526
  }
@@ -562,8 +529,5 @@ export function shouldBlockPlanningUnit(toolName, pathOrCommand, basePath, unitT
562
529
  reason: blockReason(unitType, policy.mode, `cannot ${tool} "${pathOrCommand}" — writes are restricted to .gsd/${policy.mode === "docs" ? " and " + policy.allowedPathGlobs.join(", ") : ""}`),
563
530
  };
564
531
  }
565
- // Unknown tool name — pass through. Other layers (queue, pending-gate,
566
- // CONTEXT.md write) catch known mutating shapes; defaulting to allow here
567
- // avoids breaking gsd_* MCP tools or future safe additions.
568
532
  return { block: false };
569
533
  }
@@ -1,9 +1,10 @@
1
1
  import { existsSync, readFileSync, readdirSync } from "node:fs";
2
2
  import { homedir } from "node:os";
3
- import { join, resolve } from "node:path";
3
+ import { join } from "node:path";
4
4
  import { loadRegistry } from "../workflow-templates.js";
5
+ import { resolveProjectRoot } from "../worktree.js";
5
6
  const gsdHome = process.env.GSD_HOME || join(homedir(), ".gsd");
6
- export const GSD_COMMAND_DESCRIPTION = "GSD — Get Shit Done: /gsd help|start|templates|next|auto|stop|pause|status|widget|visualize|queue|quick|discuss|capture|triage|dispatch|history|undo|undo-task|reset-slice|rate|skip|export|cleanup|model|mode|prefs|config|keys|hooks|run-hook|skill-health|doctor|debug|logs|forensics|changelog|migrate|remote|steer|knowledge|new-milestone|parallel|cmux|park|unpark|init|setup|onboarding|inspect|extensions|update|fast|mcp|rethink|workflow|codebase|notifications|ship|do|session-report|backlog|pr-branch|add-tests|scan|language";
7
+ export const GSD_COMMAND_DESCRIPTION = "GSD — Get Shit Done: /gsd help|start|templates|next|auto|stop|pause|status|widget|visualize|queue|quick|discuss|capture|triage|dispatch|history|undo|undo-task|reset-slice|rate|skip|export|cleanup|model|mode|prefs|config|keys|hooks|run-hook|skill-health|doctor|debug|logs|forensics|changelog|migrate|remote|steer|knowledge|new-milestone|parallel|cmux|park|unpark|init|setup|onboarding|inspect|extensions|update|fast|mcp|rethink|codebase|notifications|ship|do|session-report|backlog|pr-branch|add-tests|scan|language";
7
8
  export const TOP_LEVEL_SUBCOMMANDS = [
8
9
  { cmd: "help", desc: "Categorized command reference with descriptions" },
9
10
  { cmd: "next", desc: "Explicit step mode (same as /gsd)" },
@@ -329,71 +330,6 @@ function getExtensionCompletions(prefix, action) {
329
330
  return [];
330
331
  }
331
332
  }
332
- function normalizePathForCompare(path) {
333
- return path.replaceAll("\\", "/").replace(/\/+$/, "");
334
- }
335
- function findWorktreeSegment(normalizedPath) {
336
- const directMarker = "/.gsd/worktrees/";
337
- const directIdx = normalizedPath.indexOf(directMarker);
338
- if (directIdx !== -1) {
339
- return { gsdIdx: directIdx, afterWorktrees: directIdx + directMarker.length };
340
- }
341
- const symlinkMatch = normalizedPath.match(/\/\.gsd\/projects\/[a-f0-9]+\/worktrees\//);
342
- if (symlinkMatch?.index !== undefined) {
343
- return { gsdIdx: symlinkMatch.index, afterWorktrees: symlinkMatch.index + symlinkMatch[0].length };
344
- }
345
- return null;
346
- }
347
- function resolveProjectRootFromGitFile(worktreePath) {
348
- try {
349
- let dir = worktreePath;
350
- for (let i = 0; i < 30; i++) {
351
- const gitPath = join(dir, ".git");
352
- if (existsSync(gitPath)) {
353
- const content = readFileSync(gitPath, "utf8").trim();
354
- if (content.startsWith("gitdir: ")) {
355
- const gitDir = resolve(dir, content.slice(8));
356
- const dotGitDir = resolve(gitDir, "..", "..");
357
- if (dotGitDir.endsWith(".git") || dotGitDir.endsWith(".git/") || dotGitDir.endsWith(".git\\")) {
358
- return resolve(dotGitDir, "..");
359
- }
360
- const commonDirPath = join(gitDir, "commondir");
361
- if (existsSync(commonDirPath)) {
362
- const commonDir = readFileSync(commonDirPath, "utf8").trim();
363
- return resolve(resolve(gitDir, commonDir), "..");
364
- }
365
- }
366
- break;
367
- }
368
- const parent = resolve(dir, "..");
369
- if (parent === dir)
370
- break;
371
- dir = parent;
372
- }
373
- }
374
- catch {
375
- // Completion must stay best-effort.
376
- }
377
- return null;
378
- }
379
- function resolveProjectRootForCompletion(basePath) {
380
- if (process.env.GSD_PROJECT_ROOT)
381
- return process.env.GSD_PROJECT_ROOT;
382
- const normalizedPath = normalizePathForCompare(basePath);
383
- const segment = findWorktreeSegment(normalizedPath);
384
- if (!segment)
385
- return basePath;
386
- const separator = basePath.includes("\\") ? "\\" : "/";
387
- const gsdMarker = `${separator}.gsd${separator}`;
388
- const gsdIdx = basePath.indexOf(gsdMarker);
389
- const candidate = gsdIdx !== -1 ? basePath.slice(0, gsdIdx) : basePath.slice(0, segment.gsdIdx);
390
- const normalizedGsdHome = normalizePathForCompare(gsdHome);
391
- const candidateGsdPath = normalizePathForCompare(join(candidate, ".gsd"));
392
- if (candidateGsdPath === normalizedGsdHome || candidateGsdPath.startsWith(`${normalizedGsdHome}/`)) {
393
- return resolveProjectRootFromGitFile(basePath) ?? basePath;
394
- }
395
- return candidate;
396
- }
397
333
  export function getGsdArgumentCompletions(prefix) {
398
334
  const hasTrailingSpace = prefix.endsWith(" ");
399
335
  const parts = prefix.trim().split(/\s+/);
@@ -448,7 +384,7 @@ export function getGsdArgumentCompletions(prefix) {
448
384
  // Workflow definition-name completion for `workflow run <name>` and `workflow validate <name>`
449
385
  if (command === "workflow" && (subcommand === "run" || subcommand === "validate") && parts.length <= 3) {
450
386
  try {
451
- const defsDir = join(resolveProjectRootForCompletion(process.cwd()), ".gsd", "workflow-defs");
387
+ const defsDir = join(resolveProjectRoot(process.cwd()), ".gsd", "workflow-defs");
452
388
  if (existsSync(defsDir)) {
453
389
  return readdirSync(defsDir)
454
390
  .filter((f) => f.endsWith(".yaml") && f.startsWith(third))
@@ -490,7 +426,7 @@ export function getGsdArgumentCompletions(prefix) {
490
426
  catch { /* ignore */ }
491
427
  };
492
428
  try {
493
- const base = resolveProjectRootForCompletion(process.cwd());
429
+ const base = resolveProjectRoot(process.cwd());
494
430
  scanDir(join(base, ".gsd", "workflows"), "project");
495
431
  scanDir(join(base, ".gsd", "workflow-defs"), "project-legacy");
496
432
  scanDir(join(gsdHome, "workflows"), "global");