@shepai/cli 1.107.1 → 1.107.2

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 (211) hide show
  1. package/dist/packages/core/src/application/use-cases/features/create/create-feature.use-case.d.ts.map +1 -1
  2. package/dist/packages/core/src/application/use-cases/features/create/create-feature.use-case.js +2 -2
  3. package/dist/packages/core/src/application/use-cases/features/create/metadata-generator.d.ts +5 -0
  4. package/dist/packages/core/src/application/use-cases/features/create/metadata-generator.d.ts.map +1 -1
  5. package/dist/packages/core/src/application/use-cases/features/create/metadata-generator.js +31 -13
  6. package/dist/packages/core/src/application/use-cases/repositories/add-repository.use-case.d.ts.map +1 -1
  7. package/dist/packages/core/src/application/use-cases/repositories/add-repository.use-case.js +6 -2
  8. package/dist/packages/core/src/infrastructure/di/container.d.ts.map +1 -1
  9. package/dist/packages/core/src/infrastructure/di/container.js +13 -3
  10. package/dist/packages/core/src/infrastructure/repositories/sqlite-feature.repository.js +4 -4
  11. package/dist/packages/core/src/infrastructure/repositories/sqlite-repository.repository.js +4 -4
  12. package/dist/packages/core/src/infrastructure/services/agents/common/executors/claude-code-executor.service.d.ts.map +1 -1
  13. package/dist/packages/core/src/infrastructure/services/agents/common/executors/claude-code-executor.service.js +9 -0
  14. package/dist/packages/core/src/infrastructure/services/agents/common/executors/cursor-executor.service.d.ts.map +1 -1
  15. package/dist/packages/core/src/infrastructure/services/agents/common/executors/cursor-executor.service.js +17 -7
  16. package/dist/packages/core/src/infrastructure/services/agents/common/executors/dev-executor.service.d.ts.map +1 -1
  17. package/dist/packages/core/src/infrastructure/services/agents/common/executors/dev-executor.service.js +5 -3
  18. package/dist/packages/core/src/infrastructure/services/agents/feature-agent/nodes/node-helpers.d.ts.map +1 -1
  19. package/dist/packages/core/src/infrastructure/services/agents/feature-agent/nodes/node-helpers.js +1 -0
  20. package/dist/packages/core/src/infrastructure/services/agents/feature-agent/nodes/prompts/evidence-prompts.d.ts.map +1 -1
  21. package/dist/packages/core/src/infrastructure/services/agents/feature-agent/nodes/prompts/evidence-prompts.js +4 -3
  22. package/dist/packages/core/src/infrastructure/services/agents/feature-agent/nodes/repair.node.d.ts.map +1 -1
  23. package/dist/packages/core/src/infrastructure/services/agents/feature-agent/nodes/repair.node.js +2 -1
  24. package/dist/packages/core/src/infrastructure/services/agents/sessions/claude-code-session.repository.js +1 -1
  25. package/dist/packages/core/src/infrastructure/services/attachment-storage.service.js +3 -3
  26. package/dist/packages/core/src/infrastructure/services/deployment/deployment.service.d.ts +1 -1
  27. package/dist/packages/core/src/infrastructure/services/deployment/deployment.service.d.ts.map +1 -1
  28. package/dist/packages/core/src/infrastructure/services/deployment/deployment.service.js +8 -7
  29. package/dist/packages/core/src/infrastructure/services/git/worktree.service.d.ts.map +1 -1
  30. package/dist/packages/core/src/infrastructure/services/git/worktree.service.js +18 -5
  31. package/dist/packages/core/src/infrastructure/services/ide-launchers/compute-worktree-path.js +1 -1
  32. package/dist/packages/core/src/infrastructure/services/ide-launchers/json-driven-ide-launcher.service.d.ts.map +1 -1
  33. package/dist/packages/core/src/infrastructure/services/ide-launchers/json-driven-ide-launcher.service.js +6 -8
  34. package/dist/packages/core/src/infrastructure/services/process/tree-kill.d.ts +12 -0
  35. package/dist/packages/core/src/infrastructure/services/process/tree-kill.d.ts.map +1 -0
  36. package/dist/packages/core/src/infrastructure/services/process/tree-kill.js +11 -0
  37. package/dist/packages/core/src/infrastructure/services/tool-installer/binary-exists.d.ts +25 -0
  38. package/dist/packages/core/src/infrastructure/services/tool-installer/binary-exists.d.ts.map +1 -0
  39. package/dist/packages/core/src/infrastructure/services/tool-installer/binary-exists.js +32 -0
  40. package/dist/packages/core/src/infrastructure/services/tool-installer/tool-installer.service.d.ts.map +1 -1
  41. package/dist/packages/core/src/infrastructure/services/tool-installer/tool-installer.service.js +4 -27
  42. package/dist/packages/core/src/infrastructure/services/tool-installer/tools/alacritty.json +3 -2
  43. package/dist/packages/core/src/infrastructure/services/tool-installer/tools/claude-code.json +3 -2
  44. package/dist/packages/core/src/infrastructure/services/tool-installer/tools/cursor-cli.json +3 -2
  45. package/dist/packages/core/src/infrastructure/services/tool-installer/tools/cursor.json +2 -1
  46. package/dist/packages/core/src/infrastructure/services/tool-installer/tools/gh.json +2 -1
  47. package/dist/packages/core/src/infrastructure/services/tool-installer/tools/git.json +2 -1
  48. package/dist/packages/core/src/infrastructure/services/tool-installer/tools/vscode.json +2 -1
  49. package/dist/packages/core/src/infrastructure/services/tool-installer/tools/warp.json +3 -2
  50. package/dist/packages/core/src/infrastructure/services/tool-installer/tools/windsurf.json +3 -2
  51. package/dist/packages/core/src/infrastructure/services/tool-installer/tools/zed.json +3 -2
  52. package/dist/src/presentation/cli/commands/daemon/start-daemon.d.ts.map +1 -1
  53. package/dist/src/presentation/cli/commands/daemon/start-daemon.js +1 -0
  54. package/dist/src/presentation/cli/commands/daemon/stop-daemon.d.ts.map +1 -1
  55. package/dist/src/presentation/cli/commands/daemon/stop-daemon.js +5 -4
  56. package/dist/src/presentation/cli/commands/upgrade.command.d.ts.map +1 -1
  57. package/dist/src/presentation/cli/commands/upgrade.command.js +4 -0
  58. package/dist/src/presentation/web/app/actions/deploy-repository.d.ts.map +1 -1
  59. package/dist/src/presentation/web/app/actions/deploy-repository.js +2 -1
  60. package/dist/src/presentation/web/app/actions/open-folder.d.ts.map +1 -1
  61. package/dist/src/presentation/web/app/actions/open-folder.js +4 -2
  62. package/dist/src/presentation/web/app/actions/open-ide.d.ts.map +1 -1
  63. package/dist/src/presentation/web/app/actions/open-ide.js +2 -1
  64. package/dist/src/presentation/web/app/actions/open-shell.d.ts.map +1 -1
  65. package/dist/src/presentation/web/app/actions/open-shell.js +4 -2
  66. package/dist/src/presentation/web/app/build-graph-nodes.d.ts.map +1 -1
  67. package/dist/src/presentation/web/app/build-graph-nodes.js +8 -5
  68. package/dist/src/presentation/web/components/common/control-center-drawer/feature-drawer-client.d.ts.map +1 -1
  69. package/dist/src/presentation/web/components/common/control-center-drawer/feature-drawer-client.js +10 -20
  70. package/dist/src/presentation/web/components/common/merge-review/diff-view.js +1 -1
  71. package/dist/src/presentation/web/components/features/control-center/control-center-inner.d.ts.map +1 -1
  72. package/dist/src/presentation/web/components/features/control-center/control-center-inner.js +12 -0
  73. package/dist/src/presentation/web/components/features/control-center/use-control-center-state.d.ts.map +1 -1
  74. package/dist/src/presentation/web/components/features/control-center/use-control-center-state.js +32 -8
  75. package/dist/src/presentation/web/hooks/use-graph-state.d.ts +14 -0
  76. package/dist/src/presentation/web/hooks/use-graph-state.d.ts.map +1 -1
  77. package/dist/src/presentation/web/hooks/use-graph-state.js +35 -1
  78. package/dist/src/presentation/web/lib/derive-graph.d.ts.map +1 -1
  79. package/dist/src/presentation/web/lib/derive-graph.js +4 -2
  80. package/dist/tsconfig.build.tsbuildinfo +1 -1
  81. package/package.json +10 -6
  82. package/web/.next/BUILD_ID +1 -1
  83. package/web/.next/build-manifest.json +2 -2
  84. package/web/.next/fallback-build-manifest.json +2 -2
  85. package/web/.next/prerender-manifest.json +3 -3
  86. package/web/.next/required-server-files.js +2 -2
  87. package/web/.next/required-server-files.json +2 -2
  88. package/web/.next/server/app/(dashboard)/@drawer/create/page/server-reference-manifest.json +20 -20
  89. package/web/.next/server/app/(dashboard)/@drawer/create/page.js.nft.json +1 -1
  90. package/web/.next/server/app/(dashboard)/@drawer/create/page_client-reference-manifest.js +1 -1
  91. package/web/.next/server/app/(dashboard)/@drawer/feature/[featureId]/[tab]/page/server-reference-manifest.json +26 -26
  92. package/web/.next/server/app/(dashboard)/@drawer/feature/[featureId]/[tab]/page.js.nft.json +1 -1
  93. package/web/.next/server/app/(dashboard)/@drawer/feature/[featureId]/[tab]/page_client-reference-manifest.js +1 -1
  94. package/web/.next/server/app/(dashboard)/@drawer/feature/[featureId]/page/server-reference-manifest.json +26 -26
  95. package/web/.next/server/app/(dashboard)/@drawer/feature/[featureId]/page.js.nft.json +1 -1
  96. package/web/.next/server/app/(dashboard)/@drawer/feature/[featureId]/page_client-reference-manifest.js +1 -1
  97. package/web/.next/server/app/(dashboard)/@drawer/repository/[repositoryId]/page/server-reference-manifest.json +18 -18
  98. package/web/.next/server/app/(dashboard)/@drawer/repository/[repositoryId]/page.js.nft.json +1 -1
  99. package/web/.next/server/app/(dashboard)/@drawer/repository/[repositoryId]/page_client-reference-manifest.js +1 -1
  100. package/web/.next/server/app/(dashboard)/create/page/server-reference-manifest.json +20 -20
  101. package/web/.next/server/app/(dashboard)/create/page.js.nft.json +1 -1
  102. package/web/.next/server/app/(dashboard)/create/page_client-reference-manifest.js +1 -1
  103. package/web/.next/server/app/(dashboard)/feature/[featureId]/[tab]/page/server-reference-manifest.json +26 -26
  104. package/web/.next/server/app/(dashboard)/feature/[featureId]/[tab]/page.js.nft.json +1 -1
  105. package/web/.next/server/app/(dashboard)/feature/[featureId]/[tab]/page_client-reference-manifest.js +1 -1
  106. package/web/.next/server/app/(dashboard)/feature/[featureId]/page/server-reference-manifest.json +26 -26
  107. package/web/.next/server/app/(dashboard)/feature/[featureId]/page.js.nft.json +1 -1
  108. package/web/.next/server/app/(dashboard)/feature/[featureId]/page_client-reference-manifest.js +1 -1
  109. package/web/.next/server/app/(dashboard)/page/server-reference-manifest.json +18 -18
  110. package/web/.next/server/app/(dashboard)/page.js.nft.json +1 -1
  111. package/web/.next/server/app/(dashboard)/page_client-reference-manifest.js +1 -1
  112. package/web/.next/server/app/(dashboard)/repository/[repositoryId]/page/server-reference-manifest.json +18 -18
  113. package/web/.next/server/app/(dashboard)/repository/[repositoryId]/page.js.nft.json +1 -1
  114. package/web/.next/server/app/(dashboard)/repository/[repositoryId]/page_client-reference-manifest.js +1 -1
  115. package/web/.next/server/app/_global-error.html +2 -2
  116. package/web/.next/server/app/_global-error.rsc +1 -1
  117. package/web/.next/server/app/_global-error.segments/__PAGE__.segment.rsc +1 -1
  118. package/web/.next/server/app/_global-error.segments/_full.segment.rsc +1 -1
  119. package/web/.next/server/app/_global-error.segments/_head.segment.rsc +1 -1
  120. package/web/.next/server/app/_global-error.segments/_index.segment.rsc +1 -1
  121. package/web/.next/server/app/_global-error.segments/_tree.segment.rsc +1 -1
  122. package/web/.next/server/app/_not-found/page/server-reference-manifest.json +1 -1
  123. package/web/.next/server/app/_not-found/page_client-reference-manifest.js +1 -1
  124. package/web/.next/server/app/settings/page/server-reference-manifest.json +5 -5
  125. package/web/.next/server/app/settings/page.js.nft.json +1 -1
  126. package/web/.next/server/app/settings/page_client-reference-manifest.js +1 -1
  127. package/web/.next/server/app/skills/page/server-reference-manifest.json +6 -6
  128. package/web/.next/server/app/skills/page_client-reference-manifest.js +1 -1
  129. package/web/.next/server/app/tools/page/server-reference-manifest.json +6 -6
  130. package/web/.next/server/app/tools/page_client-reference-manifest.js +1 -1
  131. package/web/.next/server/app/version/page/server-reference-manifest.json +1 -1
  132. package/web/.next/server/app/version/page_client-reference-manifest.js +1 -1
  133. package/web/.next/server/chunks/403f9_next_dist_esm_build_templates_app-route_370c43b1.js +1 -1
  134. package/web/.next/server/chunks/403f9_next_dist_esm_build_templates_app-route_370c43b1.js.map +1 -1
  135. package/web/.next/server/chunks/[root-of-the-server]__a402b567._.js +1 -1
  136. package/web/.next/server/chunks/ssr/744ca_web_components_common_control-center-drawer_create-drawer-client_tsx_5e26fc0a._.js +1 -1
  137. package/web/.next/server/chunks/ssr/744ca_web_components_common_control-center-drawer_create-drawer-client_tsx_5e26fc0a._.js.map +1 -1
  138. package/web/.next/server/chunks/ssr/8ba4b_server_app_(dashboard)_@drawer_repository_[repositoryId]_page_actions_a1104008.js +1 -1
  139. package/web/.next/server/chunks/ssr/8ba4b_server_app_(dashboard)_@drawer_repository_[repositoryId]_page_actions_a1104008.js.map +1 -1
  140. package/web/.next/server/chunks/ssr/8ba4b_server_app_(dashboard)_repository_[repositoryId]_page_actions_92642200.js +1 -1
  141. package/web/.next/server/chunks/ssr/8ba4b_server_app_(dashboard)_repository_[repositoryId]_page_actions_92642200.js.map +1 -1
  142. package/web/.next/server/chunks/ssr/[root-of-the-server]__039967e3._.js +1 -1
  143. package/web/.next/server/chunks/ssr/[root-of-the-server]__039967e3._.js.map +1 -1
  144. package/web/.next/server/chunks/ssr/[root-of-the-server]__07a39ff2._.js +1 -1
  145. package/web/.next/server/chunks/ssr/[root-of-the-server]__11033878._.js +1 -1
  146. package/web/.next/server/chunks/ssr/[root-of-the-server]__11033878._.js.map +1 -1
  147. package/web/.next/server/chunks/ssr/[root-of-the-server]__24dd0927._.js +2 -2
  148. package/web/.next/server/chunks/ssr/[root-of-the-server]__24dd0927._.js.map +1 -1
  149. package/web/.next/server/chunks/ssr/[root-of-the-server]__2773312c._.js +1 -1
  150. package/web/.next/server/chunks/ssr/[root-of-the-server]__2773312c._.js.map +1 -1
  151. package/web/.next/server/chunks/ssr/[root-of-the-server]__5d87af2e._.js +1 -1
  152. package/web/.next/server/chunks/ssr/[root-of-the-server]__845a9d2a._.js +1 -1
  153. package/web/.next/server/chunks/ssr/[root-of-the-server]__845a9d2a._.js.map +1 -1
  154. package/web/.next/server/chunks/ssr/[root-of-the-server]__89e8a5cc._.js +2 -2
  155. package/web/.next/server/chunks/ssr/[root-of-the-server]__89e8a5cc._.js.map +1 -1
  156. package/web/.next/server/chunks/ssr/[root-of-the-server]__aad040c0._.js +2 -2
  157. package/web/.next/server/chunks/ssr/[root-of-the-server]__aad040c0._.js.map +1 -1
  158. package/web/.next/server/chunks/ssr/[root-of-the-server]__cbd8062c._.js +1 -1
  159. package/web/.next/server/chunks/ssr/[root-of-the-server]__cbd8062c._.js.map +1 -1
  160. package/web/.next/server/chunks/ssr/[root-of-the-server]__e70c5627._.js +1 -1
  161. package/web/.next/server/chunks/ssr/[root-of-the-server]__e70c5627._.js.map +1 -1
  162. package/web/.next/server/chunks/ssr/[root-of-the-server]__fdc75809._.js +1 -1
  163. package/web/.next/server/chunks/ssr/[root-of-the-server]__fdc75809._.js.map +1 -1
  164. package/web/.next/server/chunks/ssr/_135edb9c._.js +1 -1
  165. package/web/.next/server/chunks/ssr/_135edb9c._.js.map +1 -1
  166. package/web/.next/server/chunks/ssr/_8dacd1e7._.js +1 -1
  167. package/web/.next/server/chunks/ssr/_8dacd1e7._.js.map +1 -1
  168. package/web/.next/server/chunks/ssr/_cc77a143._.js +1 -1
  169. package/web/.next/server/chunks/ssr/_cc77a143._.js.map +1 -1
  170. package/web/.next/server/chunks/ssr/{_3c0076bc._.js → _e2681489._.js} +2 -2
  171. package/web/.next/server/chunks/ssr/{_3c0076bc._.js.map → _e2681489._.js.map} +1 -1
  172. package/web/.next/server/chunks/ssr/{_89745126._.js → _f3612e5a._.js} +2 -2
  173. package/web/.next/server/chunks/ssr/{_89745126._.js.map → _f3612e5a._.js.map} +1 -1
  174. package/web/.next/server/chunks/ssr/{_4d49c223._.js → _f891c054._.js} +2 -2
  175. package/web/.next/server/chunks/ssr/_f891c054._.js.map +1 -0
  176. package/web/.next/server/chunks/ssr/b1a17_presentation_web_components_features_settings_settings-page-client_tsx_6ed9d5f8._.js +1 -1
  177. package/web/.next/server/chunks/ssr/b1a17_presentation_web_components_features_settings_settings-page-client_tsx_6ed9d5f8._.js.map +1 -1
  178. package/web/.next/server/chunks/ssr/src_presentation_web__next-internal_server_app_(dashboard)_page_actions_888633e1.js +1 -1
  179. package/web/.next/server/chunks/ssr/src_presentation_web__next-internal_server_app_(dashboard)_page_actions_888633e1.js.map +1 -1
  180. package/web/.next/server/chunks/ssr/src_presentation_web__next-internal_server_app_skills_page_actions_1fa8042e.js +1 -1
  181. package/web/.next/server/chunks/ssr/src_presentation_web__next-internal_server_app_skills_page_actions_1fa8042e.js.map +1 -1
  182. package/web/.next/server/chunks/ssr/src_presentation_web__next-internal_server_app_tools_page_actions_24684200.js +1 -1
  183. package/web/.next/server/chunks/ssr/src_presentation_web__next-internal_server_app_tools_page_actions_24684200.js.map +1 -1
  184. package/web/.next/server/chunks/ssr/src_presentation_web_ca99d62d._.js +1 -1
  185. package/web/.next/server/chunks/ssr/src_presentation_web_ca99d62d._.js.map +1 -1
  186. package/web/.next/server/chunks/ssr/src_presentation_web_ce7cbc3c._.js +2 -2
  187. package/web/.next/server/chunks/ssr/src_presentation_web_ce7cbc3c._.js.map +1 -1
  188. package/web/.next/server/chunks/ssr/src_presentation_web_components_bf50c527._.js +1 -1
  189. package/web/.next/server/chunks/ssr/src_presentation_web_components_de814675._.js +1 -1
  190. package/web/.next/server/chunks/ssr/src_presentation_web_components_features_control-center_7ac3562e._.js +1 -1
  191. package/web/.next/server/chunks/ssr/src_presentation_web_components_features_control-center_7ac3562e._.js.map +1 -1
  192. package/web/.next/server/chunks/ssr/src_presentation_web_e2604413._.js +2 -2
  193. package/web/.next/server/chunks/ssr/src_presentation_web_e2604413._.js.map +1 -1
  194. package/web/.next/server/pages/500.html +2 -2
  195. package/web/.next/server/server-reference-manifest.js +1 -1
  196. package/web/.next/server/server-reference-manifest.json +31 -31
  197. package/web/.next/static/chunks/{9751a0c871920841.js → 2ffe2f11f4ca9bb4.js} +1 -1
  198. package/web/.next/static/chunks/{fa27e698e0daf727.js → 430e372a1ef8e0a1.js} +1 -1
  199. package/web/.next/static/chunks/{e429067d6277ac20.js → 87488a543d25cd04.js} +1 -1
  200. package/web/.next/static/chunks/{dd30ae99bcec5f69.js → 8f1322aea6f75e2d.js} +2 -2
  201. package/web/.next/static/chunks/{2c6298885de1484c.js → acce61815a6260e7.js} +1 -1
  202. package/web/.next/static/chunks/{eed22af4cf55faea.js → c3253a63b95ec66e.js} +1 -1
  203. package/web/.next/static/chunks/{2eab3bb5550eccac.js → f60e223f91508b6e.js} +1 -1
  204. package/web/.next/static/chunks/{5ebc63ae73de50a3.js → f7d21f36df719f6f.js} +1 -1
  205. package/web/.next/static/chunks/f8672a435cc52ee8.js +2 -0
  206. package/web/.next/static/chunks/{f28d2411c36c308b.js → fc986ec4aa601f4d.js} +1 -1
  207. package/web/.next/server/chunks/ssr/_4d49c223._.js.map +0 -1
  208. package/web/.next/static/chunks/281782a712ea79cb.js +0 -2
  209. /package/web/.next/static/{OYucSKP83TUMTV1zRbeB8 → ITseKg4TnnrOWm79esrvr}/_buildManifest.js +0 -0
  210. /package/web/.next/static/{OYucSKP83TUMTV1zRbeB8 → ITseKg4TnnrOWm79esrvr}/_clientMiddlewareManifest.json +0 -0
  211. /package/web/.next/static/{OYucSKP83TUMTV1zRbeB8 → ITseKg4TnnrOWm79esrvr}/_ssgManifest.js +0 -0
@@ -19,5 +19,5 @@ import { getShepHomeDir } from '../filesystem/shep-directory.service.js';
19
19
  export function computeWorktreePath(repoPath, branch) {
20
20
  const repoHash = createHash('sha256').update(repoPath).digest('hex').slice(0, 16);
21
21
  const slug = branch.replace(/\//g, '-');
22
- return join(getShepHomeDir(), 'repos', repoHash, 'wt', slug);
22
+ return join(getShepHomeDir(), 'repos', repoHash, 'wt', slug).replace(/\\/g, '/');
23
23
  }
@@ -1 +1 @@
1
- {"version":3,"file":"json-driven-ide-launcher.service.d.ts","sourceRoot":"","sources":["../../../../../../../packages/core/src/infrastructure/services/ide-launchers/json-driven-ide-launcher.service.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAKH,OAAO,KAAK,EACV,mBAAmB,EACnB,eAAe,EAChB,MAAM,8EAA8E,CAAC;AAetF;;;;;GAKG;AACH,wBAAgB,oBAAoB,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAAG,MAAM,CAGnF;AAED,qBACa,4BAA6B,YAAW,mBAAmB;IACtE,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAwB;;IAiB1C,MAAM,CACV,QAAQ,EAAE,MAAM,EAChB,aAAa,EAAE,MAAM,EACrB,OAAO,CAAC,EAAE;QAAE,QAAQ,CAAC,EAAE,OAAO,CAAA;KAAE,GAC/B,OAAO,CAAC,eAAe,CAAC;IA8D3B,iBAAiB,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC;CAWtD"}
1
+ {"version":3,"file":"json-driven-ide-launcher.service.d.ts","sourceRoot":"","sources":["../../../../../../../packages/core/src/infrastructure/services/ide-launchers/json-driven-ide-launcher.service.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAMH,OAAO,KAAK,EACV,mBAAmB,EACnB,eAAe,EAChB,MAAM,8EAA8E,CAAC;AAetF;;;;;GAKG;AACH,wBAAgB,oBAAoB,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAAG,MAAM,CAGnF;AAED,qBACa,4BAA6B,YAAW,mBAAmB;IACtE,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAwB;;IAiB1C,MAAM,CACV,QAAQ,EAAE,MAAM,EAChB,aAAa,EAAE,MAAM,EACrB,OAAO,CAAC,EAAE;QAAE,QAAQ,CAAC,EAAE,OAAO,CAAA;KAAE,GAC/B,OAAO,CAAC,eAAe,CAAC;IA8DrB,iBAAiB,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC;CAQ5D"}
@@ -16,8 +16,9 @@ var __metadata = (this && this.__metadata) || function (k, v) {
16
16
  if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
17
17
  };
18
18
  import { injectable } from 'tsyringe';
19
- import { spawn, execFile } from 'node:child_process';
19
+ import { spawn } from 'node:child_process';
20
20
  import { platform } from 'node:os';
21
+ import { checkBinaryExists } from '../tool-installer/binary-exists.js';
21
22
  import { TOOL_METADATA } from '../tool-installer/tool-metadata.js';
22
23
  /**
23
24
  * Resolve a platform-specific value from a string or per-platform record.
@@ -101,16 +102,13 @@ let JsonDrivenIdeLauncherService = class JsonDrivenIdeLauncherService {
101
102
  };
102
103
  }
103
104
  }
104
- checkAvailability(editorId) {
105
+ async checkAvailability(editorId) {
105
106
  const entry = this.editors.get(editorId);
106
107
  if (!entry)
107
- return Promise.resolve(false);
108
+ return false;
108
109
  const binary = resolvePlatformValue(entry.binary);
109
- return new Promise((resolve) => {
110
- execFile('which', [binary], (err) => {
111
- resolve(!err);
112
- });
113
- });
110
+ const result = await checkBinaryExists(binary);
111
+ return result.found;
114
112
  }
115
113
  };
116
114
  JsonDrivenIdeLauncherService = __decorate([
@@ -0,0 +1,12 @@
1
+ /**
2
+ * Cross-platform process tree termination.
3
+ *
4
+ * Re-exports the npm `tree-kill` package for use by the presentation layer,
5
+ * which cannot resolve packages installed in packages/core/node_modules
6
+ * directly (pnpm workspace isolation).
7
+ *
8
+ * Uses taskkill /T /F on Windows, kill/ps/pgrep on Unix.
9
+ */
10
+ import treeKill from 'tree-kill';
11
+ export { treeKill };
12
+ //# sourceMappingURL=tree-kill.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"tree-kill.d.ts","sourceRoot":"","sources":["../../../../../../../packages/core/src/infrastructure/services/process/tree-kill.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AAEH,OAAO,QAAQ,MAAM,WAAW,CAAC;AAEjC,OAAO,EAAE,QAAQ,EAAE,CAAC"}
@@ -0,0 +1,11 @@
1
+ /**
2
+ * Cross-platform process tree termination.
3
+ *
4
+ * Re-exports the npm `tree-kill` package for use by the presentation layer,
5
+ * which cannot resolve packages installed in packages/core/node_modules
6
+ * directly (pnpm workspace isolation).
7
+ *
8
+ * Uses taskkill /T /F on Windows, kill/ps/pgrep on Unix.
9
+ */
10
+ import treeKill from 'tree-kill';
11
+ export { treeKill };
@@ -0,0 +1,25 @@
1
+ /**
2
+ * Cross-platform binary existence check.
3
+ *
4
+ * Wraps the npm `which` package to provide a single cross-platform API
5
+ * for checking if a binary exists in the system PATH. Works on Unix
6
+ * (which) and Windows (where.exe + PATHEXT resolution) without platform
7
+ * branching.
8
+ */
9
+ /**
10
+ * Check if a binary exists in the system PATH.
11
+ *
12
+ * Uses the npm `which` package which handles Windows PATHEXT resolution
13
+ * internally (.exe, .cmd, .bat extensions).
14
+ *
15
+ * Returns:
16
+ * - `{ found: true }` when the binary is on PATH
17
+ * - `{ found: false, notInPath: true }` when the binary is not on PATH
18
+ * - `{ found: false, error }` for genuine errors (e.g. permission denied)
19
+ */
20
+ export declare const checkBinaryExists: (binary: string) => Promise<{
21
+ found: boolean;
22
+ notInPath?: boolean;
23
+ error?: Error;
24
+ }>;
25
+ //# sourceMappingURL=binary-exists.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"binary-exists.d.ts","sourceRoot":"","sources":["../../../../../../../packages/core/src/infrastructure/services/tool-installer/binary-exists.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAIH;;;;;;;;;;GAUG;AACH,eAAO,MAAM,iBAAiB,GAC5B,QAAQ,MAAM,KACb,OAAO,CAAC;IAAE,KAAK,EAAE,OAAO,CAAC;IAAC,SAAS,CAAC,EAAE,OAAO,CAAC;IAAC,KAAK,CAAC,EAAE,KAAK,CAAA;CAAE,CAUhE,CAAC"}
@@ -0,0 +1,32 @@
1
+ /**
2
+ * Cross-platform binary existence check.
3
+ *
4
+ * Wraps the npm `which` package to provide a single cross-platform API
5
+ * for checking if a binary exists in the system PATH. Works on Unix
6
+ * (which) and Windows (where.exe + PATHEXT resolution) without platform
7
+ * branching.
8
+ */
9
+ import which from 'which';
10
+ /**
11
+ * Check if a binary exists in the system PATH.
12
+ *
13
+ * Uses the npm `which` package which handles Windows PATHEXT resolution
14
+ * internally (.exe, .cmd, .bat extensions).
15
+ *
16
+ * Returns:
17
+ * - `{ found: true }` when the binary is on PATH
18
+ * - `{ found: false, notInPath: true }` when the binary is not on PATH
19
+ * - `{ found: false, error }` for genuine errors (e.g. permission denied)
20
+ */
21
+ export const checkBinaryExists = async (binary) => {
22
+ try {
23
+ const result = await which(binary, { nothrow: true });
24
+ if (result !== null) {
25
+ return { found: true };
26
+ }
27
+ return { found: false, notInPath: true };
28
+ }
29
+ catch (error) {
30
+ return { found: false, error: error instanceof Error ? error : new Error(String(error)) };
31
+ }
32
+ };
@@ -1 +1 @@
1
- {"version":3,"file":"tool-installer.service.d.ts","sourceRoot":"","sources":["../../../../../../../packages/core/src/infrastructure/services/tool-installer/tool-installer.service.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAKH,OAAO,KAAK,EAAE,qBAAqB,EAAE,MAAM,sEAAsE,CAAC;AAClH,OAAO,KAAK,EACV,sBAAsB,EACtB,kBAAkB,EAEnB,MAAM,qCAAqC,CAAC;AAsD7C,qBACa,wBAAyB,YAAW,qBAAqB;IACpE;;;OAGG;IACG,iBAAiB,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,sBAAsB,CAAC;IAoC1E;;;OAGG;IACH,iBAAiB,CAAC,QAAQ,EAAE,MAAM,GAAG,kBAAkB,GAAG,IAAI;IAqB9D;;;OAGG;IACG,cAAc,CAClB,QAAQ,EAAE,MAAM,EAChB,QAAQ,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,GAChC,OAAO,CAAC,sBAAsB,CAAC;IAgFlC;;OAEG;IACH,OAAO,CAAC,6BAA6B;CA4BtC"}
1
+ {"version":3,"file":"tool-installer.service.d.ts","sourceRoot":"","sources":["../../../../../../../packages/core/src/infrastructure/services/tool-installer/tool-installer.service.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAKH,OAAO,KAAK,EAAE,qBAAqB,EAAE,MAAM,sEAAsE,CAAC;AAClH,OAAO,KAAK,EACV,sBAAsB,EACtB,kBAAkB,EAEnB,MAAM,qCAAqC,CAAC;AA2B7C,qBACa,wBAAyB,YAAW,qBAAqB;IACpE;;;OAGG;IACG,iBAAiB,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,sBAAsB,CAAC;IAoC1E;;;OAGG;IACH,iBAAiB,CAAC,QAAQ,EAAE,MAAM,GAAG,kBAAkB,GAAG,IAAI;IAqB9D;;;OAGG;IACG,cAAc,CAClB,QAAQ,EAAE,MAAM,EAChB,QAAQ,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,GAChC,OAAO,CAAC,sBAAsB,CAAC;IAgFlC;;OAEG;IACH,OAAO,CAAC,6BAA6B;CA4BtC"}
@@ -18,10 +18,11 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key,
18
18
  return c > 3 && r && Object.defineProperty(target, key, r), r;
19
19
  };
20
20
  import { injectable } from 'tsyringe';
21
- import { exec, execFile, spawn } from 'node:child_process';
21
+ import { exec, spawn } from 'node:child_process';
22
22
  import { platform } from 'node:os';
23
23
  import { createAvailableStatus, createMissingStatus, createErrorStatus, } from '../../../domain/value-objects/tool-installation-status.js';
24
24
  import { TOOL_METADATA } from './tool-metadata.js';
25
+ import { checkBinaryExists } from './binary-exists.js';
25
26
  /**
26
27
  * Resolve binary name for the current platform.
27
28
  * Supports both simple string binaries and per-platform maps.
@@ -31,30 +32,6 @@ function resolveBinary(metadata) {
31
32
  return metadata.binary;
32
33
  return metadata.binary[platform()] ?? Object.values(metadata.binary)[0];
33
34
  }
34
- /**
35
- * Check if a binary exists in the system PATH using 'which' command.
36
- *
37
- * `which` exits with code 1 when the binary is simply not in PATH.
38
- * Node's execFile wraps that as an Error, but it's a normal "not found"
39
- * result. Only truly unexpected failures (ENOENT for `which` itself,
40
- * EACCES, signals, etc.) are surfaced via the `error` field.
41
- */
42
- const checkBinaryExists = (binary) => {
43
- return new Promise((resolve) => {
44
- execFile('which', [binary], (err) => {
45
- if (!err)
46
- return resolve({ found: true });
47
- // execFile errors from a non-zero exit code have a numeric `code` property.
48
- // That's the normal "binary not found in PATH" case.
49
- const code = err.code;
50
- if (code === undefined || typeof code === 'number') {
51
- return resolve({ found: false, notInPath: true });
52
- }
53
- // Anything else (ENOENT for `which` itself, EACCES, etc.) is a real error.
54
- resolve({ found: false, error: err });
55
- });
56
- });
57
- };
58
35
  /**
59
36
  * Run a shell command and resolve true when it exits 0, false otherwise.
60
37
  * Used as a fallback for GUI apps whose binary isn't in PATH (e.g. Warp, iTerm2).
@@ -130,8 +107,8 @@ let ToolInstallerServiceImpl = class ToolInstallerServiceImpl {
130
107
  }
131
108
  return new Promise((resolve) => {
132
109
  let output = '';
133
- const child = spawn('sh', ['-c', installCommand.command], {
134
- shell: false,
110
+ const child = spawn(installCommand.command, [], {
111
+ shell: true,
135
112
  stdio: ['pipe', 'pipe', 'pipe'],
136
113
  env: {
137
114
  ...process.env,
@@ -5,13 +5,14 @@
5
5
  "tags": ["terminal"],
6
6
  "author": "Alacritty Contributors",
7
7
  "website": "https://alacritty.org",
8
- "platforms": ["linux", "darwin"],
8
+ "platforms": ["linux", "darwin", "win32"],
9
9
  "iconUrl": "https://cdn.simpleicons.org/alacritty",
10
10
  "binary": "alacritty",
11
11
  "packageManager": "brew",
12
12
  "commands": {
13
13
  "darwin": "brew install --cask alacritty",
14
- "linux": "sudo apt-get update && sudo apt-get install -y alacritty"
14
+ "linux": "sudo apt-get update && sudo apt-get install -y alacritty",
15
+ "win32": "winget install --id Alacritty.Alacritty -e --source winget"
15
16
  },
16
17
  "timeout": 300000,
17
18
  "documentationUrl": "https://alacritty.org/",
@@ -5,13 +5,14 @@
5
5
  "tags": ["cli-agent"],
6
6
  "author": "Anthropic",
7
7
  "website": "https://claude.ai/code",
8
- "platforms": ["linux", "darwin"],
8
+ "platforms": ["linux", "darwin", "win32"],
9
9
  "iconUrl": "https://cdn.simpleicons.org/claude",
10
10
  "binary": "claude",
11
11
  "packageManager": "curl",
12
12
  "commands": {
13
13
  "linux": "curl -fsSL https://claude.ai/install.sh | bash",
14
- "darwin": "curl -fsSL https://claude.ai/install.sh | bash"
14
+ "darwin": "curl -fsSL https://claude.ai/install.sh | bash",
15
+ "win32": "npm install -g @anthropic-ai/claude-code"
15
16
  },
16
17
  "timeout": 300000,
17
18
  "documentationUrl": "https://code.claude.com/docs/en/overview",
@@ -5,13 +5,14 @@
5
5
  "tags": ["cli-agent"],
6
6
  "author": "Anysphere",
7
7
  "website": "https://cursor.com",
8
- "platforms": ["linux", "darwin"],
8
+ "platforms": ["linux", "darwin", "win32"],
9
9
  "iconUrl": "https://cdn.simpleicons.org/cursor",
10
10
  "binary": "cursor-agent",
11
11
  "packageManager": "curl",
12
12
  "commands": {
13
13
  "linux": "curl https://cursor.com/install -fsS | bash",
14
- "darwin": "curl https://cursor.com/install -fsS | bash"
14
+ "darwin": "curl https://cursor.com/install -fsS | bash",
15
+ "win32": "powershell -Command \"irm 'https://cursor.com/install?win32=true' | iex\""
15
16
  },
16
17
  "timeout": 300000,
17
18
  "documentationUrl": "https://www.codecademy.com/article/getting-started-with-cursor-cli",
@@ -11,7 +11,8 @@
11
11
  "packageManager": "manual",
12
12
  "commands": {
13
13
  "linux": "Download from https://cursor.com/download and install the AppImage manually",
14
- "darwin": "Download from https://cursor.com/download or use: brew install --cask cursor"
14
+ "darwin": "Download from https://cursor.com/download or use: brew install --cask cursor",
15
+ "win32": "winget install --id Anysphere.Cursor -e --source winget"
15
16
  },
16
17
  "timeout": 600000,
17
18
  "documentationUrl": "https://cursor.com/download",
@@ -11,7 +11,8 @@
11
11
  "packageManager": "apt",
12
12
  "commands": {
13
13
  "linux": "(type -p wget >/dev/null || (sudo apt update && sudo apt-get install wget -y)) && sudo mkdir -p -m 755 /etc/apt/keyrings && out=$(mktemp) && wget -nv -O$out https://cli.github.com/packages/githubcli-archive-keyring.gpg && cat $out | sudo tee /etc/apt/keyrings/githubcli-archive-keyring.gpg > /dev/null && sudo chmod go+r /etc/apt/keyrings/githubcli-archive-keyring.gpg && echo \"deb [arch=$(dpkg --print-architecture) signed-by=/etc/apt/keyrings/githubcli-archive-keyring.gpg] https://cli.github.com/packages stable main\" | sudo tee /etc/apt/sources.list.d/github-cli.list > /dev/null && sudo apt update && sudo apt install gh -y",
14
- "darwin": "brew install gh"
14
+ "darwin": "brew install gh",
15
+ "win32": "winget install --id GitHub.cli -e --source winget"
15
16
  },
16
17
  "timeout": 300000,
17
18
  "documentationUrl": "https://cli.github.com/manual/",
@@ -11,7 +11,8 @@
11
11
  "packageManager": "apt",
12
12
  "commands": {
13
13
  "linux": "sudo apt-get update && sudo apt-get install -y git",
14
- "darwin": "xcode-select --install"
14
+ "darwin": "xcode-select --install",
15
+ "win32": "winget install --id Git.Git -e --source winget"
15
16
  },
16
17
  "timeout": 300000,
17
18
  "documentationUrl": "https://git-scm.com/doc",
@@ -11,7 +11,8 @@
11
11
  "packageManager": "apt",
12
12
  "commands": {
13
13
  "linux": "curl -fsSL https://packages.microsoft.com/keys/microsoft.asc | sudo gpg --yes --dearmor -o /usr/share/keyrings/packages.microsoft.gpg && echo \"deb [arch=amd64 signed-by=/usr/share/keyrings/packages.microsoft.gpg] https://packages.microsoft.com/repos/code stable main\" | sudo tee /etc/apt/sources.list.d/vscode.list > /dev/null && sudo apt-get update && sudo apt-get install -y code",
14
- "darwin": "brew install visual-studio-code"
14
+ "darwin": "brew install visual-studio-code",
15
+ "win32": "winget install --id Microsoft.VisualStudioCode -e --source winget"
15
16
  },
16
17
  "timeout": 300000,
17
18
  "documentationUrl": "https://code.visualstudio.com/docs/setup/linux",
@@ -5,12 +5,13 @@
5
5
  "tags": ["terminal"],
6
6
  "author": "Warp",
7
7
  "website": "https://www.warp.dev",
8
- "platforms": ["darwin"],
8
+ "platforms": ["darwin", "win32"],
9
9
  "iconUrl": "https://cdn.simpleicons.org/warp",
10
10
  "binary": "warp",
11
11
  "packageManager": "brew",
12
12
  "commands": {
13
- "darwin": "brew install --cask warp"
13
+ "darwin": "brew install --cask warp",
14
+ "win32": "winget install --id Warp.Warp -e --source winget"
14
15
  },
15
16
  "timeout": 300000,
16
17
  "documentationUrl": "https://docs.warp.dev/",
@@ -5,13 +5,14 @@
5
5
  "tags": ["ide"],
6
6
  "author": "Codeium",
7
7
  "website": "https://codeium.com/windsurf",
8
- "platforms": ["linux", "darwin"],
8
+ "platforms": ["linux", "darwin", "win32"],
9
9
  "iconUrl": "https://cdn.simpleicons.org/windsurf",
10
10
  "binary": "windsurf",
11
11
  "packageManager": "apt",
12
12
  "commands": {
13
13
  "linux": "curl -fsSL \"https://windsurf-stable.codeiumdata.com/wVxQEIWkwPUEAGf3/windsurf.gpg\" | sudo gpg --yes --dearmor -o /usr/share/keyrings/windsurf-stable-archive-keyring.gpg && echo \"deb [signed-by=/usr/share/keyrings/windsurf-stable-archive-keyring.gpg arch=amd64] https://windsurf-stable.codeiumdata.com/wVxQEIWkwPUEAGf3/apt stable main\" | sudo tee /etc/apt/sources.list.d/windsurf.list > /dev/null && sudo apt-get update && sudo apt-get install -y windsurf",
14
- "darwin": "brew install --cask windsurf"
14
+ "darwin": "brew install --cask windsurf",
15
+ "win32": "winget install --id Codeium.Windsurf -e --source winget"
15
16
  },
16
17
  "timeout": 300000,
17
18
  "documentationUrl": "https://docs.windsurf.com/windsurf/getting-started",
@@ -5,13 +5,14 @@
5
5
  "tags": ["ide"],
6
6
  "author": "Zed Industries",
7
7
  "website": "https://zed.dev",
8
- "platforms": ["linux", "darwin"],
8
+ "platforms": ["linux", "darwin", "win32"],
9
9
  "iconUrl": "https://cdn.simpleicons.org/zedindustries",
10
10
  "binary": "zed",
11
11
  "packageManager": "curl",
12
12
  "commands": {
13
13
  "linux": "curl -f https://zed.dev/install.sh | sh",
14
- "darwin": "curl -f https://zed.dev/install.sh | sh"
14
+ "darwin": "curl -f https://zed.dev/install.sh | sh",
15
+ "win32": "winget install --id ZedIndustries.Zed -e --source winget"
15
16
  },
16
17
  "timeout": 300000,
17
18
  "documentationUrl": "https://zed.dev/docs/installation",
@@ -1 +1 @@
1
- {"version":3,"file":"start-daemon.d.ts","sourceRoot":"","sources":["../../../../../../src/presentation/cli/commands/daemon/start-daemon.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;GAiBG;AAoBH,MAAM,WAAW,kBAAkB;IACjC,IAAI,CAAC,EAAE,MAAM,CAAC;CACf;AAED;;;GAGG;AACH,wBAAsB,WAAW,CAAC,IAAI,GAAE,kBAAuB,GAAG,OAAO,CAAC,IAAI,CAAC,CA+F9E"}
1
+ {"version":3,"file":"start-daemon.d.ts","sourceRoot":"","sources":["../../../../../../src/presentation/cli/commands/daemon/start-daemon.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;GAiBG;AAoBH,MAAM,WAAW,kBAAkB;IACjC,IAAI,CAAC,EAAE,MAAM,CAAC;CACf;AAED;;;GAGG;AACH,wBAAsB,WAAW,CAAC,IAAI,GAAE,kBAAuB,GAAG,OAAO,CAAC,IAAI,CAAC,CAgG9E"}
@@ -67,6 +67,7 @@ export async function startDaemon(opts = {}) {
67
67
  const child = spawn(process.execPath, [...process.execArgv, process.argv[1], '_serve', '--port', String(port)], {
68
68
  detached: true,
69
69
  stdio: ['ignore', logFd, logFd],
70
+ windowsHide: true,
70
71
  });
71
72
  // Wait briefly for the child to either settle or crash.
72
73
  const exitCode = await Promise.race([
@@ -1 +1 @@
1
- {"version":3,"file":"stop-daemon.d.ts","sourceRoot":"","sources":["../../../../../../src/presentation/cli/commands/daemon/stop-daemon.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;GAmBG;AAEH,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,iEAAiE,CAAC;AA0BtG;;;GAGG;AACH,wBAAsB,UAAU,CAAC,aAAa,EAAE,cAAc,GAAG,OAAO,CAAC,IAAI,CAAC,CAyC7E"}
1
+ {"version":3,"file":"stop-daemon.d.ts","sourceRoot":"","sources":["../../../../../../src/presentation/cli/commands/daemon/stop-daemon.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;GAmBG;AAGH,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,iEAAiE,CAAC;AA0BtG;;;GAGG;AACH,wBAAsB,UAAU,CAAC,aAAa,EAAE,cAAc,GAAG,OAAO,CAAC,IAAI,CAAC,CAyC7E"}
@@ -18,6 +18,7 @@
18
18
  *
19
19
  * @param daemonService - IDaemonService instance (injected by caller for testability, NFR-4)
20
20
  */
21
+ import { treeKill } from '../../../../../packages/core/src/infrastructure/services/process/tree-kill.js';
21
22
  import { messages } from '../../ui/index.js';
22
23
  const POLL_INTERVAL_MS = 200;
23
24
  const MAX_WAIT_MS = 5000;
@@ -54,15 +55,15 @@ export async function stopDaemon(daemonService) {
54
55
  }
55
56
  try {
56
57
  messages.info(`Stopping Shep daemon (PID ${pid})...`);
57
- // Send SIGTERM — request graceful shutdown
58
- process.kill(pid, 'SIGTERM');
58
+ // Send SIGTERM to process tree — request graceful shutdown
59
+ treeKill(pid, 'SIGTERM');
59
60
  // Poll for up to 5s waiting for the process to exit
60
61
  const died = await pollUntilDead(daemonService, pid, MAX_WAIT_MS, POLL_INTERVAL_MS);
61
62
  if (!died) {
62
- // Graceful shutdown timed out — force kill
63
+ // Graceful shutdown timed out — force kill process tree
63
64
  messages.info('Daemon did not stop gracefully, sending SIGKILL...');
64
65
  try {
65
- process.kill(pid, 'SIGKILL');
66
+ treeKill(pid, 'SIGKILL');
66
67
  }
67
68
  catch {
68
69
  // Process may have exited between the check and the kill — ignore
@@ -1 +1 @@
1
- {"version":3,"file":"upgrade.command.d.ts","sourceRoot":"","sources":["../../../../../src/presentation/cli/commands/upgrade.command.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AACpC,OAAO,EAAE,KAAK,IAAI,YAAY,EAAqB,MAAM,oBAAoB,CAAC;AAQ9E,KAAK,OAAO,GAAG,OAAO,YAAY,CAAC;AAyEnC;;GAEG;AACH,wBAAgB,oBAAoB,CAAC,OAAO,GAAE,OAAsB,GAAG,OAAO,CA+D7E"}
1
+ {"version":3,"file":"upgrade.command.d.ts","sourceRoot":"","sources":["../../../../../src/presentation/cli/commands/upgrade.command.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AACpC,OAAO,EAAE,KAAK,IAAI,YAAY,EAAqB,MAAM,oBAAoB,CAAC;AAQ9E,KAAK,OAAO,GAAG,OAAO,YAAY,CAAC;AA8EnC;;GAEG;AACH,wBAAgB,oBAAoB,CAAC,OAAO,GAAE,OAAsB,GAAG,OAAO,CA+D7E"}
@@ -13,6 +13,8 @@ import { messages } from '../ui/index.js';
13
13
  import { stopDaemon } from './daemon/stop-daemon.js';
14
14
  import { startDaemon } from './daemon/start-daemon.js';
15
15
  const VERSION_CHECK_TIMEOUT_MS = 10_000;
16
+ /** On Windows, npm is a .cmd batch file — spawn() needs shell: true to resolve it. */
17
+ const IS_WINDOWS = process.platform === 'win32';
16
18
  /**
17
19
  * Get the latest published version of @shepai/cli from npm registry.
18
20
  * Returns null if the check fails (fail-open).
@@ -23,6 +25,7 @@ function getLatestVersion(spawnFn) {
23
25
  let settled = false;
24
26
  const child = spawnFn('npm', ['view', '@shepai/cli', 'version'], {
25
27
  stdio: ['ignore', 'pipe', 'pipe'],
28
+ ...(IS_WINDOWS && { shell: true }),
26
29
  });
27
30
  const timeout = setTimeout(() => {
28
31
  if (!settled) {
@@ -65,6 +68,7 @@ function runNpmInstall(spawnFn) {
65
68
  return new Promise((resolve, reject) => {
66
69
  const child = spawnFn('npm', ['i', '-g', '@shepai/cli@latest'], {
67
70
  stdio: 'inherit',
71
+ ...(IS_WINDOWS && { shell: true }),
68
72
  });
69
73
  child.on('close', (code) => {
70
74
  resolve(code ?? 1);
@@ -1 +1 @@
1
- {"version":3,"file":"deploy-repository.d.ts","sourceRoot":"","sources":["../../../../../../src/presentation/web/app/actions/deploy-repository.ts"],"names":[],"mappings":"AAMA,OAAO,EAAE,eAAe,EAAE,MAAM,sCAAsC,CAAC;AAIvE,wBAAsB,gBAAgB,CACpC,cAAc,EAAE,MAAM,GACrB,OAAO,CAAC;IAAE,OAAO,EAAE,OAAO,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAC;IAAC,KAAK,CAAC,EAAE,eAAe,CAAA;CAAE,CAAC,CAyBxE"}
1
+ {"version":3,"file":"deploy-repository.d.ts","sourceRoot":"","sources":["../../../../../../src/presentation/web/app/actions/deploy-repository.ts"],"names":[],"mappings":"AAOA,OAAO,EAAE,eAAe,EAAE,MAAM,sCAAsC,CAAC;AAIvE,wBAAsB,gBAAgB,CACpC,cAAc,EAAE,MAAM,GACrB,OAAO,CAAC;IAAE,OAAO,EAAE,OAAO,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAC;IAAC,KAAK,CAAC,EAAE,eAAe,CAAA;CAAE,CAAC,CAyBxE"}
@@ -1,12 +1,13 @@
1
1
  'use server';
2
2
  import { existsSync } from 'node:fs';
3
+ import { isAbsolute } from 'node:path';
3
4
  import { resolve } from '../../lib/server-container.js';
4
5
  import { createDeploymentLogger } from '../../../../../packages/core/src/infrastructure/services/deployment/deployment-logger.js';
5
6
  import { DeploymentState } from '../../../../../packages/core/src/domain/generated/output.js';
6
7
  const log = createDeploymentLogger('[deployRepository]');
7
8
  export async function deployRepository(repositoryPath) {
8
9
  log.info(`called — repositoryPath="${repositoryPath}"`);
9
- if (!repositoryPath?.startsWith('/')) {
10
+ if (!repositoryPath || !isAbsolute(repositoryPath)) {
10
11
  log.warn('rejected — not an absolute path');
11
12
  return { success: false, error: 'repositoryPath must be an absolute path' };
12
13
  }
@@ -1 +1 @@
1
- {"version":3,"file":"open-folder.d.ts","sourceRoot":"","sources":["../../../../../../src/presentation/web/app/actions/open-folder.ts"],"names":[],"mappings":"AAeA,wBAAsB,UAAU,CAC9B,cAAc,EAAE,MAAM,GACrB,OAAO,CAAC;IAAE,OAAO,EAAE,OAAO,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAC;IAAC,IAAI,CAAC,EAAE,MAAM,CAAA;CAAE,CAAC,CA8B9D"}
1
+ {"version":3,"file":"open-folder.d.ts","sourceRoot":"","sources":["../../../../../../src/presentation/web/app/actions/open-folder.ts"],"names":[],"mappings":"AAiBA,wBAAsB,UAAU,CAC9B,cAAc,EAAE,MAAM,GACrB,OAAO,CAAC;IAAE,OAAO,EAAE,OAAO,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAC;IAAC,IAAI,CAAC,EAAE,MAAM,CAAA;CAAE,CAAC,CA8B9D"}
@@ -1,6 +1,7 @@
1
1
  'use server';
2
2
  import { existsSync } from 'node:fs';
3
3
  import { platform } from 'node:os';
4
+ import { isAbsolute } from 'node:path';
4
5
  import { spawn } from 'node:child_process';
5
6
  // Use a record lookup instead of if/else to prevent the bundler from
6
7
  // tree-shaking platform branches at build time. Turbopack evaluates
@@ -9,9 +10,10 @@ import { spawn } from 'node:child_process';
9
10
  const FOLDER_COMMANDS = {
10
11
  darwin: { cmd: 'open', args: (p) => [p] },
11
12
  linux: { cmd: 'xdg-open', args: (p) => [p] },
13
+ win32: { cmd: 'explorer', args: (p) => [p] },
12
14
  };
13
15
  export async function openFolder(repositoryPath) {
14
- if (!repositoryPath?.startsWith('/')) {
16
+ if (!repositoryPath || !isAbsolute(repositoryPath)) {
15
17
  return { success: false, error: 'repositoryPath must be an absolute path' };
16
18
  }
17
19
  try {
@@ -22,7 +24,7 @@ export async function openFolder(repositoryPath) {
22
24
  if (!entry) {
23
25
  return {
24
26
  success: false,
25
- error: `Unsupported platform: ${platform()}. Folder open is supported on macOS and Linux only.`,
27
+ error: `Unsupported platform: ${platform()}`,
26
28
  };
27
29
  }
28
30
  const child = spawn(entry.cmd, entry.args(repositoryPath), {
@@ -1 +1 @@
1
- {"version":3,"file":"open-ide.d.ts","sourceRoot":"","sources":["../../../../../../src/presentation/web/app/actions/open-ide.ts"],"names":[],"mappings":"AAMA,UAAU,YAAY;IACpB,cAAc,EAAE,MAAM,CAAC;IACvB,MAAM,CAAC,EAAE,MAAM,CAAC;CACjB;AAED,wBAAsB,OAAO,CAC3B,KAAK,EAAE,YAAY,GAClB,OAAO,CAAC;IAAE,OAAO,EAAE,OAAO,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAC;IAAC,MAAM,CAAC,EAAE,MAAM,CAAC;IAAC,IAAI,CAAC,EAAE,MAAM,CAAA;CAAE,CAAC,CAuB/E"}
1
+ {"version":3,"file":"open-ide.d.ts","sourceRoot":"","sources":["../../../../../../src/presentation/web/app/actions/open-ide.ts"],"names":[],"mappings":"AAOA,UAAU,YAAY;IACpB,cAAc,EAAE,MAAM,CAAC;IACvB,MAAM,CAAC,EAAE,MAAM,CAAC;CACjB;AAED,wBAAsB,OAAO,CAC3B,KAAK,EAAE,YAAY,GAClB,OAAO,CAAC;IAAE,OAAO,EAAE,OAAO,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAC;IAAC,MAAM,CAAC,EAAE,MAAM,CAAC;IAAC,IAAI,CAAC,EAAE,MAAM,CAAA;CAAE,CAAC,CAuB/E"}
@@ -1,9 +1,10 @@
1
1
  'use server';
2
+ import { isAbsolute } from 'node:path';
2
3
  import { getSettings } from '../../../../../packages/core/src/infrastructure/services/settings.service.js';
3
4
  import { resolve } from '../../lib/server-container.js';
4
5
  export async function openIde(input) {
5
6
  const { repositoryPath, branch } = input;
6
- if (!repositoryPath?.startsWith('/')) {
7
+ if (!repositoryPath || !isAbsolute(repositoryPath)) {
7
8
  return { success: false, error: 'repositoryPath must be an absolute path' };
8
9
  }
9
10
  const settings = getSettings();
@@ -1 +1 @@
1
- {"version":3,"file":"open-shell.d.ts","sourceRoot":"","sources":["../../../../../../src/presentation/web/app/actions/open-shell.ts"],"names":[],"mappings":"AAiBA,UAAU,cAAc;IACtB,cAAc,EAAE,MAAM,CAAC;IACvB,MAAM,CAAC,EAAE,MAAM,CAAC;CACjB;AAED,wBAAsB,SAAS,CAC7B,KAAK,EAAE,cAAc,GACpB,OAAO,CAAC;IAAE,OAAO,EAAE,OAAO,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAC;IAAC,IAAI,CAAC,EAAE,MAAM,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAA;CAAE,CAAC,CAoC9E"}
1
+ {"version":3,"file":"open-shell.d.ts","sourceRoot":"","sources":["../../../../../../src/presentation/web/app/actions/open-shell.ts"],"names":[],"mappings":"AAmBA,UAAU,cAAc;IACtB,cAAc,EAAE,MAAM,CAAC;IACvB,MAAM,CAAC,EAAE,MAAM,CAAC;CACjB;AAED,wBAAsB,SAAS,CAC7B,KAAK,EAAE,cAAc,GACpB,OAAO,CAAC;IAAE,OAAO,EAAE,OAAO,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAC;IAAC,IAAI,CAAC,EAAE,MAAM,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAA;CAAE,CAAC,CAoC9E"}
@@ -1,6 +1,7 @@
1
1
  'use server';
2
2
  import { existsSync } from 'node:fs';
3
3
  import { platform } from 'node:os';
4
+ import { isAbsolute } from 'node:path';
4
5
  import { spawn } from 'node:child_process';
5
6
  import { getSettings } from '../../../../../packages/core/src/infrastructure/services/settings.service.js';
6
7
  import { computeWorktreePath } from '../../../../../packages/core/src/infrastructure/services/ide-launchers/compute-worktree-path.js';
@@ -11,10 +12,11 @@ import { computeWorktreePath } from '../../../../../packages/core/src/infrastruc
11
12
  const SHELL_COMMANDS = {
12
13
  darwin: { cmd: 'open', args: (p) => ['-a', 'Terminal', p] },
13
14
  linux: { cmd: 'x-terminal-emulator', args: (p) => [`--working-directory=${p}`] },
15
+ win32: { cmd: 'powershell', args: (p) => ['-NoExit', '-Command', `Set-Location "${p}"`] },
14
16
  };
15
17
  export async function openShell(input) {
16
18
  const { repositoryPath, branch } = input;
17
- if (!repositoryPath?.startsWith('/')) {
19
+ if (!repositoryPath || !isAbsolute(repositoryPath)) {
18
20
  return { success: false, error: 'repositoryPath must be an absolute path' };
19
21
  }
20
22
  try {
@@ -28,7 +30,7 @@ export async function openShell(input) {
28
30
  if (!entry) {
29
31
  return {
30
32
  success: false,
31
- error: `Unsupported platform: ${platform()}. Shell launch is supported on macOS and Linux only.`,
33
+ error: `Unsupported platform: ${platform()}`,
32
34
  };
33
35
  }
34
36
  const child = spawn(entry.cmd, entry.args(targetPath), {
@@ -1 +1 @@
1
- {"version":3,"file":"build-graph-nodes.d.ts","sourceRoot":"","sources":["../../../../../src/presentation/web/app/build-graph-nodes.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,OAAO,EAAE,UAAU,EAAE,QAAQ,EAAE,MAAM,sCAAsC,CAAC;AAQ1F,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,uCAAuC,CAAC;AAC5E,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,eAAe,CAAC;AAG1C,MAAM,WAAW,cAAc;IAC7B,OAAO,EAAE,OAAO,CAAC;IACjB,GAAG,EAAE,QAAQ,GAAG,IAAI,CAAC;CACtB;AAED;;;;;;;GAOG;AACH,wBAAgB,eAAe,CAC7B,YAAY,EAAE,UAAU,EAAE,EAC1B,gBAAgB,EAAE,cAAc,EAAE,GACjC;IAAE,KAAK,EAAE,cAAc,EAAE,CAAC;IAAC,KAAK,EAAE,IAAI,EAAE,CAAA;CAAE,CAuE5C"}
1
+ {"version":3,"file":"build-graph-nodes.d.ts","sourceRoot":"","sources":["../../../../../src/presentation/web/app/build-graph-nodes.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,OAAO,EAAE,UAAU,EAAE,QAAQ,EAAE,MAAM,sCAAsC,CAAC;AAQ1F,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,uCAAuC,CAAC;AAC5E,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,eAAe,CAAC;AAG1C,MAAM,WAAW,cAAc;IAC7B,OAAO,EAAE,OAAO,CAAC;IACjB,GAAG,EAAE,QAAQ,GAAG,IAAI,CAAC;CACtB;AAED;;;;;;;GAOG;AACH,wBAAgB,eAAe,CAC7B,YAAY,EAAE,UAAU,EAAE,EAC1B,gBAAgB,EAAE,cAAc,EAAE,GACjC;IAAE,KAAK,EAAE,cAAc,EAAE,CAAC;IAAC,KAAK,EAAE,IAAI,EAAE,CAAA;CAAE,CA2E5C"}
@@ -10,10 +10,12 @@ import { isProcessAlive } from '../../../../packages/core/src/infrastructure/ser
10
10
  * renders empty when features exist but their repository rows are missing.
11
11
  */
12
12
  export function buildGraphNodes(repositories, featuresWithRuns) {
13
- // Group features by repository path
13
+ // Normalize path separators so Windows backslash paths match forward-slash paths
14
+ const normalizePath = (p) => p.replace(/\\/g, '/');
15
+ // Group features by normalized repository path
14
16
  const featuresByRepo = {};
15
17
  featuresWithRuns.forEach((entry) => {
16
- const repoKey = entry.feature.repositoryPath;
18
+ const repoKey = normalizePath(entry.feature.repositoryPath);
17
19
  if (!featuresByRepo[repoKey]) {
18
20
  featuresByRepo[repoKey] = [];
19
21
  }
@@ -25,7 +27,8 @@ export function buildGraphNodes(repositories, featuresWithRuns) {
25
27
  const coveredPaths = new Set();
26
28
  // First, add nodes for all persisted repositories (including those without features)
27
29
  for (const repo of repositories) {
28
- coveredPaths.add(repo.path);
30
+ const normalizedRepoPath = normalizePath(repo.path);
31
+ coveredPaths.add(normalizedRepoPath);
29
32
  const repoNodeId = `repo-${repo.id}`;
30
33
  nodes.push({
31
34
  id: repoNodeId,
@@ -33,12 +36,12 @@ export function buildGraphNodes(repositories, featuresWithRuns) {
33
36
  position: { x: 0, y: 0 },
34
37
  data: {
35
38
  name: repo.name,
36
- repositoryPath: repo.path,
39
+ repositoryPath: normalizedRepoPath,
37
40
  id: repo.id,
38
41
  createdAt: repo.createdAt instanceof Date ? repo.createdAt.getTime() : Number(repo.createdAt),
39
42
  },
40
43
  });
41
- const repoFeatures = featuresByRepo[repo.path] ?? [];
44
+ const repoFeatures = featuresByRepo[normalizedRepoPath] ?? [];
42
45
  appendFeatureNodes(repoFeatures, repoNodeId, featuresWithRuns, nodes, edges, repo.name);
43
46
  }
44
47
  // Second pass: group orphaned features under virtual repository nodes
@@ -1 +1 @@
1
- {"version":3,"file":"feature-drawer-client.d.ts","sourceRoot":"","sources":["../../../../../../../src/presentation/web/components/common/control-center-drawer/feature-drawer-client.tsx"],"names":[],"mappings":"AAuCA,OAAO,KAAK,EAAE,UAAU,EAAE,aAAa,EAAE,MAAM,eAAe,CAAC;AAI/D,MAAM,WAAW,wBAAwB;IACvC,IAAI,EAAE,UAAU,CAAC;IACjB,8FAA8F;IAC9F,MAAM,CAAC,EAAE,aAAa,CAAC;CACxB;AAED,wBAAgB,mBAAmB,CAAC,EAAE,IAAI,EAAE,WAAW,EAAE,MAAM,EAAE,EAAE,wBAAwB,2CAgjB1F"}
1
+ {"version":3,"file":"feature-drawer-client.d.ts","sourceRoot":"","sources":["../../../../../../../src/presentation/web/components/common/control-center-drawer/feature-drawer-client.tsx"],"names":[],"mappings":"AAsCA,OAAO,KAAK,EAAE,UAAU,EAAE,aAAa,EAAE,MAAM,eAAe,CAAC;AAI/D,MAAM,WAAW,wBAAwB;IACvC,IAAI,EAAE,UAAU,CAAC;IACjB,8FAA8F;IAC9F,MAAM,CAAC,EAAE,aAAa,CAAC;CACxB;AAED,wBAAgB,mBAAmB,CAAC,EAAE,IAAI,EAAE,WAAW,EAAE,MAAM,EAAE,EAAE,wBAAwB,2CA2iB1F"}