aiwcli 0.15.5 → 0.17.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (435) hide show
  1. package/README.md +108 -1124
  2. package/bin/run.js +0 -4
  3. package/dist/capabilities/branch/adapters.d.ts +2 -0
  4. package/dist/capabilities/branch/adapters.js +21 -0
  5. package/dist/capabilities/branch/contracts.d.ts +57 -0
  6. package/dist/capabilities/branch/contracts.js +1 -0
  7. package/dist/capabilities/branch/control-plane.d.ts +2 -0
  8. package/dist/capabilities/branch/control-plane.js +343 -0
  9. package/dist/capabilities/branch/runtime-core.d.ts +5 -0
  10. package/dist/capabilities/branch/runtime-core.js +36 -0
  11. package/dist/capabilities/installation/control-plane/clean-command.d.ts +41 -0
  12. package/dist/capabilities/installation/control-plane/clean-command.js +196 -0
  13. package/dist/capabilities/installation/control-plane/clear-command.d.ts +162 -0
  14. package/dist/capabilities/installation/control-plane/clear-command.js +1249 -0
  15. package/dist/capabilities/installation/control-plane/init-command.d.ts +81 -0
  16. package/dist/capabilities/installation/control-plane/init-command.js +449 -0
  17. package/dist/capabilities/launch/contracts.d.ts +86 -0
  18. package/dist/capabilities/launch/contracts.js +1 -0
  19. package/dist/capabilities/launch/control-plane/execute-launch.d.ts +2 -0
  20. package/dist/capabilities/launch/control-plane/execute-launch.js +261 -0
  21. package/dist/capabilities/launch/runtime-core/launch-decisions.d.ts +82 -0
  22. package/dist/capabilities/launch/runtime-core/launch-decisions.js +202 -0
  23. package/dist/capabilities/launch/runtime-core/launch-options.d.ts +14 -0
  24. package/dist/capabilities/launch/runtime-core/launch-options.js +69 -0
  25. package/dist/cli/base-command.d.ts +18 -0
  26. package/dist/cli/base-command.js +55 -0
  27. package/dist/commands/branch.d.ts +1 -21
  28. package/dist/commands/branch.js +25 -417
  29. package/dist/commands/clean.d.ts +1 -41
  30. package/dist/commands/clean.js +1 -196
  31. package/dist/commands/clear.d.ts +1 -161
  32. package/dist/commands/clear.js +1 -1121
  33. package/dist/commands/init/index.d.ts +1 -98
  34. package/dist/commands/init/index.js +4 -478
  35. package/dist/commands/launch.d.ts +32 -12
  36. package/dist/commands/launch.js +107 -166
  37. package/dist/lib/claude-settings-types.d.ts +31 -19
  38. package/dist/lib/config.js +1 -2
  39. package/dist/lib/context/context-formatter.d.ts +74 -0
  40. package/dist/lib/context/context-formatter.js +493 -0
  41. package/dist/lib/context/context-selector.d.ts +42 -0
  42. package/dist/lib/context/context-selector.js +451 -0
  43. package/dist/lib/context/context-store.d.ts +100 -0
  44. package/dist/lib/context/context-store.js +644 -0
  45. package/dist/lib/context/plan-manager.d.ts +54 -0
  46. package/dist/lib/context/plan-manager.js +282 -0
  47. package/dist/lib/context/task-tracker.d.ts +44 -0
  48. package/dist/lib/context/task-tracker.js +146 -0
  49. package/dist/lib/core-ide-base.d.ts +4 -0
  50. package/dist/lib/core-ide-base.js +77 -0
  51. package/dist/lib/core-installer.d.ts +5 -0
  52. package/dist/lib/core-installer.js +33 -0
  53. package/dist/lib/debug.d.ts +0 -10
  54. package/dist/lib/debug.js +0 -10
  55. package/dist/lib/env-sanitizer.d.ts +25 -0
  56. package/dist/lib/env-sanitizer.js +46 -0
  57. package/dist/lib/errors.d.ts +0 -13
  58. package/dist/lib/errors.js +0 -15
  59. package/dist/lib/git-exclude-manager.d.ts +2 -2
  60. package/dist/lib/git-exclude-manager.js +3 -3
  61. package/dist/lib/hooks/context-monitor-logic.d.ts +6 -0
  62. package/dist/lib/hooks/context-monitor-logic.js +25 -0
  63. package/dist/lib/hooks/hook-utils.d.ts +143 -0
  64. package/dist/lib/hooks/hook-utils.js +620 -0
  65. package/dist/lib/hooks/prompt-binding-logic.d.ts +7 -0
  66. package/dist/lib/hooks/prompt-binding-logic.js +50 -0
  67. package/dist/lib/hooks/session-end-logic.d.ts +5 -0
  68. package/dist/lib/hooks/session-end-logic.js +51 -0
  69. package/dist/lib/hooks-merger.js +25 -19
  70. package/dist/lib/ide-path-resolver.d.ts +19 -7
  71. package/dist/lib/ide-path-resolver.js +25 -9
  72. package/dist/lib/install-state.d.ts +34 -0
  73. package/dist/lib/install-state.js +154 -0
  74. package/dist/lib/json-io.d.ts +12 -0
  75. package/dist/lib/json-io.js +30 -0
  76. package/dist/lib/lsp-patch.d.ts +12 -0
  77. package/dist/lib/lsp-patch.js +156 -0
  78. package/dist/lib/multiplexer.d.ts +65 -0
  79. package/dist/lib/multiplexer.js +38 -0
  80. package/dist/lib/multiplexers/psmux.d.ts +55 -0
  81. package/dist/lib/multiplexers/psmux.js +324 -0
  82. package/dist/lib/multiplexers/tmux.d.ts +36 -0
  83. package/dist/lib/multiplexers/tmux.js +221 -0
  84. package/dist/lib/multiplexers/wezterm.d.ts +38 -0
  85. package/dist/lib/multiplexers/wezterm.js +225 -0
  86. package/dist/lib/mux-utils.d.ts +6 -0
  87. package/dist/lib/mux-utils.js +36 -0
  88. package/dist/lib/paths.d.ts +2 -2
  89. package/dist/lib/paths.js +2 -2
  90. package/dist/lib/platform-commands.d.ts +27 -0
  91. package/dist/lib/platform-commands.js +49 -0
  92. package/dist/lib/prompt-file-manager.d.ts +23 -0
  93. package/dist/lib/prompt-file-manager.js +41 -0
  94. package/dist/lib/runtime/agent-launcher.d.ts +67 -0
  95. package/dist/lib/runtime/agent-launcher.js +262 -0
  96. package/dist/lib/runtime/aiw-cli.d.ts +39 -0
  97. package/dist/lib/runtime/aiw-cli.js +76 -0
  98. package/dist/lib/runtime/atomic-write.d.ts +19 -0
  99. package/dist/lib/runtime/atomic-write.js +121 -0
  100. package/dist/lib/runtime/cli-args.d.ts +58 -0
  101. package/dist/lib/runtime/cli-args.js +200 -0
  102. package/dist/lib/runtime/constants.d.ts +56 -0
  103. package/dist/lib/runtime/constants.js +230 -0
  104. package/dist/lib/runtime/executable-policy.d.ts +16 -0
  105. package/dist/lib/runtime/executable-policy.js +57 -0
  106. package/dist/lib/runtime/git-state.d.ts +9 -0
  107. package/dist/lib/runtime/git-state.js +59 -0
  108. package/dist/lib/runtime/inference.d.ts +37 -0
  109. package/dist/lib/runtime/inference.js +251 -0
  110. package/dist/lib/runtime/lint-dispatch.d.ts +40 -0
  111. package/dist/lib/runtime/lint-dispatch.js +285 -0
  112. package/dist/lib/runtime/logger.d.ts +66 -0
  113. package/dist/lib/runtime/logger.js +201 -0
  114. package/dist/lib/runtime/models.d.ts +20 -0
  115. package/dist/lib/runtime/models.js +20 -0
  116. package/dist/lib/runtime/platform-adapter.d.ts +7 -0
  117. package/dist/lib/runtime/platform-adapter.js +21 -0
  118. package/dist/lib/runtime/preflight.d.ts +24 -0
  119. package/dist/lib/runtime/preflight.js +65 -0
  120. package/dist/lib/runtime/sentinel-ipc.d.ts +14 -0
  121. package/dist/lib/runtime/sentinel-ipc.js +67 -0
  122. package/dist/lib/runtime/state-io.d.ts +31 -0
  123. package/dist/lib/runtime/state-io.js +179 -0
  124. package/dist/lib/runtime/stop-words.d.ts +20 -0
  125. package/dist/lib/runtime/stop-words.js +150 -0
  126. package/dist/lib/runtime/subprocess-utils.d.ts +29 -0
  127. package/dist/lib/runtime/subprocess-utils.js +96 -0
  128. package/dist/lib/runtime/tmux-preflight.d.ts +13 -0
  129. package/dist/lib/runtime/tmux-preflight.js +78 -0
  130. package/dist/lib/runtime/utils.d.ts +62 -0
  131. package/dist/lib/runtime/utils.js +192 -0
  132. package/dist/lib/schemas.d.ts +250 -0
  133. package/dist/lib/schemas.js +216 -0
  134. package/dist/lib/sentinel-manager.d.ts +32 -0
  135. package/dist/lib/sentinel-manager.js +62 -0
  136. package/dist/lib/sentinel-wrapper.d.ts +10 -0
  137. package/dist/lib/sentinel-wrapper.js +29 -0
  138. package/dist/lib/settings-hierarchy.js +3 -20
  139. package/dist/lib/shell-adapters/bash-adapter.d.ts +18 -0
  140. package/dist/lib/shell-adapters/bash-adapter.js +69 -0
  141. package/dist/lib/shell-adapters/index.d.ts +5 -0
  142. package/dist/lib/shell-adapters/index.js +7 -0
  143. package/dist/lib/shell-adapters/powershell-adapter.d.ts +18 -0
  144. package/dist/lib/shell-adapters/powershell-adapter.js +62 -0
  145. package/dist/lib/shell-adapters/shell-adapter.d.ts +45 -0
  146. package/dist/lib/shell-adapters/shell-adapter.js +5 -0
  147. package/dist/lib/shell-quoting.d.ts +5 -0
  148. package/dist/lib/shell-quoting.js +17 -0
  149. package/dist/lib/spawn-errors.d.ts +9 -0
  150. package/dist/lib/spawn-errors.js +29 -0
  151. package/dist/lib/spawn.js +5 -11
  152. package/dist/lib/spinner.d.ts +0 -5
  153. package/dist/lib/spinner.js +0 -16
  154. package/dist/lib/template-installer.d.ts +14 -5
  155. package/dist/lib/template-installer.js +40 -38
  156. package/dist/lib/template-resolver.d.ts +6 -7
  157. package/dist/lib/template-resolver.js +26 -21
  158. package/dist/lib/template-settings-reconstructor.d.ts +7 -2
  159. package/dist/lib/template-settings-reconstructor.js +76 -45
  160. package/dist/lib/terminal-strategy.d.ts +12 -0
  161. package/dist/lib/terminal-strategy.js +55 -0
  162. package/dist/lib/terminal.d.ts +34 -4
  163. package/dist/lib/terminal.js +192 -119
  164. package/dist/lib/tmux-pane-placement.d.ts +17 -0
  165. package/dist/lib/tmux-pane-placement.js +58 -0
  166. package/dist/lib/tmux-primitives.d.ts +3 -0
  167. package/dist/lib/tmux-primitives.js +11 -0
  168. package/dist/lib/tmux-session.d.ts +32 -0
  169. package/dist/lib/tmux-session.js +87 -0
  170. package/dist/lib/tty-detection.js +1 -1
  171. package/dist/lib/types.d.ts +168 -0
  172. package/dist/lib/types.js +6 -0
  173. package/dist/lib/version.d.ts +1 -1
  174. package/dist/lib/version.js +1 -1
  175. package/dist/lib/windsurf-hooks-hierarchy.js +6 -23
  176. package/dist/platform/launch.d.ts +11 -0
  177. package/dist/platform/launch.js +11 -0
  178. package/dist/templates/CLAUDE.md +30 -40
  179. package/dist/templates/cc-native/.claude/settings.json +26 -36
  180. package/dist/templates/cc-native/CC-NATIVE-README.md +1 -1
  181. package/dist/templates/cc-native/TEMPLATE-SCHEMA.md +20 -12
  182. package/dist/templates/cc-native/_cc-native/cc-native.config.json +2 -6
  183. package/dist/templates/cc-native/_cc-native/hooks/CLAUDE.md +39 -59
  184. package/dist/templates/cc-native/_cc-native/hooks/cc-native-plan-review.ts +9 -11
  185. package/dist/templates/cc-native/_cc-native/hooks/enhance_plan_post_subagent.ts +2 -2
  186. package/dist/templates/cc-native/_cc-native/hooks/enhance_plan_post_write.ts +4 -5
  187. package/dist/templates/cc-native/_cc-native/hooks/mark_questions_asked.ts +4 -4
  188. package/dist/templates/cc-native/_cc-native/hooks/plan_questions_early.ts +2 -27
  189. package/dist/templates/cc-native/_cc-native/hooks/validate_task_prompt.ts +7 -7
  190. package/dist/templates/cc-native/_cc-native/lib-ts/.mocharc.json +9 -0
  191. package/dist/templates/cc-native/_cc-native/lib-ts/__tests__/aggregate-agents.test.ts +118 -0
  192. package/dist/templates/cc-native/_cc-native/lib-ts/__tests__/artifacts.test.ts +234 -0
  193. package/dist/templates/cc-native/_cc-native/lib-ts/__tests__/cc-native-state.test.ts +170 -0
  194. package/dist/templates/cc-native/_cc-native/lib-ts/__tests__/cli-output-parser.test.ts +73 -0
  195. package/dist/templates/cc-native/_cc-native/lib-ts/__tests__/config.test.ts +64 -0
  196. package/dist/templates/cc-native/_cc-native/lib-ts/__tests__/constants.test.ts +40 -0
  197. package/dist/templates/cc-native/_cc-native/lib-ts/__tests__/debug.test.ts +42 -0
  198. package/dist/templates/cc-native/_cc-native/lib-ts/__tests__/exports.test.ts +58 -0
  199. package/dist/templates/cc-native/_cc-native/lib-ts/__tests__/helpers.ts +107 -0
  200. package/dist/templates/cc-native/_cc-native/lib-ts/__tests__/hooks/add-plan-context.hook.test.ts +97 -0
  201. package/dist/templates/cc-native/_cc-native/lib-ts/__tests__/hooks/plan-questions.hook.test.ts +81 -0
  202. package/dist/templates/cc-native/_cc-native/lib-ts/__tests__/hooks/plan-review.hook.test.ts +71 -0
  203. package/dist/templates/cc-native/_cc-native/lib-ts/__tests__/json-parser.test.ts +99 -0
  204. package/dist/templates/cc-native/_cc-native/lib-ts/__tests__/orchestrator-agent.test.ts +288 -0
  205. package/dist/templates/cc-native/_cc-native/lib-ts/__tests__/orchestrator.test.ts +48 -0
  206. package/dist/templates/cc-native/_cc-native/lib-ts/__tests__/reviewers.test.ts +32 -0
  207. package/dist/templates/cc-native/_cc-native/lib-ts/__tests__/state.test.ts +124 -0
  208. package/dist/templates/cc-native/_cc-native/lib-ts/__tests__/verdict.test.ts +93 -0
  209. package/dist/templates/cc-native/_cc-native/lib-ts/agent-selection.ts +163 -0
  210. package/dist/templates/cc-native/_cc-native/lib-ts/aggregate-agents.ts +6 -14
  211. package/dist/templates/cc-native/_cc-native/{artifacts/lib → lib-ts/artifacts}/format.ts +597 -599
  212. package/dist/templates/cc-native/_cc-native/{artifacts/lib → lib-ts/artifacts}/index.ts +26 -26
  213. package/dist/templates/cc-native/_cc-native/{artifacts/lib → lib-ts/artifacts}/tracker.ts +106 -107
  214. package/dist/templates/cc-native/_cc-native/{artifacts/lib → lib-ts/artifacts}/write.ts +118 -119
  215. package/dist/templates/cc-native/_cc-native/lib-ts/artifacts.ts +21 -0
  216. package/dist/templates/cc-native/_cc-native/lib-ts/cc-native-state.ts +17 -16
  217. package/dist/templates/cc-native/_cc-native/lib-ts/cli-output-parser.ts +132 -10
  218. package/dist/templates/cc-native/_cc-native/lib-ts/config.ts +1 -1
  219. package/dist/templates/cc-native/_cc-native/lib-ts/constants.ts +6 -6
  220. package/dist/templates/cc-native/_cc-native/lib-ts/corroboration.ts +119 -0
  221. package/dist/templates/cc-native/_cc-native/lib-ts/debug.ts +2 -3
  222. package/dist/templates/cc-native/_cc-native/{plan-review/lib → lib-ts}/graduation.ts +132 -132
  223. package/dist/templates/cc-native/_cc-native/lib-ts/index.ts +88 -86
  224. package/dist/templates/cc-native/_cc-native/lib-ts/json-parser.ts +5 -6
  225. package/dist/templates/cc-native/_cc-native/{plan-review/lib → lib-ts}/orchestrator.ts +70 -70
  226. package/dist/templates/cc-native/_cc-native/{plan-review/lib → lib-ts}/output-builder.ts +130 -121
  227. package/dist/templates/cc-native/_cc-native/lib-ts/package-lock.json +1679 -0
  228. package/dist/templates/cc-native/_cc-native/lib-ts/package.json +24 -0
  229. package/dist/templates/cc-native/_cc-native/lib-ts/plan-discovery.ts +5 -5
  230. package/dist/templates/cc-native/_cc-native/lib-ts/plan-enhancement.ts +1 -6
  231. package/dist/templates/cc-native/_cc-native/{plan-review/lib → lib-ts}/plan-questions.ts +101 -101
  232. package/dist/templates/cc-native/_cc-native/{plan-review/lib → lib-ts}/review-pipeline.ts +511 -543
  233. package/dist/templates/cc-native/_cc-native/lib-ts/reviewers/__tests__/agent-providers.test.ts +262 -0
  234. package/dist/templates/cc-native/_cc-native/{plan-review/lib → lib-ts}/reviewers/agent.ts +71 -85
  235. package/dist/templates/{_shared/lib-ts/agent-exec → cc-native/_cc-native/lib-ts/reviewers/base}/base-agent.ts +138 -150
  236. package/dist/templates/cc-native/_cc-native/{plan-review/lib → lib-ts}/reviewers/index.ts +12 -12
  237. package/dist/templates/cc-native/_cc-native/{plan-review/lib → lib-ts}/reviewers/providers/claude-agent.ts +66 -57
  238. package/dist/templates/cc-native/_cc-native/{plan-review/lib → lib-ts}/reviewers/providers/codex-agent.ts +185 -200
  239. package/dist/templates/cc-native/_cc-native/{plan-review/lib → lib-ts}/reviewers/providers/gemini-agent.ts +39 -40
  240. package/dist/templates/cc-native/_cc-native/{plan-review/lib → lib-ts}/reviewers/providers/orchestrator-claude-agent.ts +196 -225
  241. package/dist/templates/cc-native/_cc-native/{plan-review/lib → lib-ts}/reviewers/schemas.ts +201 -201
  242. package/dist/templates/cc-native/_cc-native/{plan-review/lib → lib-ts}/reviewers/types.ts +21 -23
  243. package/dist/templates/cc-native/_cc-native/lib-ts/rlm/__tests__/hyde.test.ts +365 -0
  244. package/dist/templates/cc-native/_cc-native/lib-ts/rlm/__tests__/ollama-client.test.ts +223 -0
  245. package/dist/templates/cc-native/_cc-native/lib-ts/rlm/embedding-indexer.ts +12 -16
  246. package/dist/templates/cc-native/_cc-native/lib-ts/rlm/hyde.ts +3 -2
  247. package/dist/templates/cc-native/_cc-native/lib-ts/rlm/index.ts +31 -31
  248. package/dist/templates/cc-native/_cc-native/lib-ts/rlm/logger.ts +7 -8
  249. package/dist/templates/cc-native/_cc-native/lib-ts/rlm/ollama-client.ts +7 -9
  250. package/dist/templates/cc-native/_cc-native/lib-ts/rlm/retrieval-pipeline.ts +16 -19
  251. package/dist/templates/cc-native/_cc-native/lib-ts/rlm/transcript-indexer.ts +37 -41
  252. package/dist/templates/cc-native/_cc-native/lib-ts/rlm/transcript-loader.ts +33 -43
  253. package/dist/templates/cc-native/_cc-native/lib-ts/rlm/transcript-searcher.ts +20 -20
  254. package/dist/templates/cc-native/_cc-native/lib-ts/rlm/types.ts +9 -10
  255. package/dist/templates/cc-native/_cc-native/lib-ts/rlm/vector-store.ts +3 -4
  256. package/dist/templates/cc-native/_cc-native/lib-ts/settings.ts +50 -126
  257. package/dist/templates/cc-native/_cc-native/lib-ts/state.ts +20 -22
  258. package/dist/templates/cc-native/_cc-native/lib-ts/tsconfig.json +2 -2
  259. package/dist/templates/cc-native/_cc-native/lib-ts/types.ts +14 -89
  260. package/dist/templates/cc-native/_cc-native/{plan-review/lib → lib-ts}/verdict.ts +72 -72
  261. package/dist/templates/cc-native/_cc-native/plan-review/CLAUDE.md +38 -1
  262. package/dist/templates/cc-native/_cc-native/plan-review/lib/__tests__/agent-selection.test.ts +345 -0
  263. package/dist/templates/cc-native/_cc-native/plan-review/lib/__tests__/preflight.test.ts +344 -0
  264. package/dist/templates/cc-native/_cc-native/plan-review/lib/agent-selection.ts +38 -16
  265. package/dist/templates/cc-native/_cc-native/plan-review/lib/preflight.ts +56 -26
  266. package/dist/templates/cc-native/_cc-native/scripts/council_debate.ts +242 -0
  267. package/dist/templates/cc-native/_cc-native/scripts/council_debate_simple.ts +294 -0
  268. package/dist/templates/cc-native/_cc-native/{plan-review/workflows → workflows}/specdev.md +9 -9
  269. package/dist/templates/core/.claude/skills/codex/SKILL.md +25 -0
  270. package/dist/templates/core/.claude/skills/devin/SKILL.md +25 -0
  271. package/dist/templates/core/.claude/skills/handoff/SKILL.md +11 -0
  272. package/dist/templates/core/.claude/skills/handoff-resume/SKILL.md +11 -0
  273. package/dist/templates/core/.claude/skills/meta-plan/SKILL.md +13 -0
  274. package/dist/templates/core/.codex/skills/codex/SKILL.md +13 -0
  275. package/dist/templates/core/.codex/skills/devin/SKILL.md +19 -0
  276. package/dist/templates/core/.codex/skills/handoff/SKILL.md +11 -0
  277. package/dist/templates/core/.codex/skills/handoff-resume/SKILL.md +11 -0
  278. package/dist/templates/core/.codex/skills/meta-plan/SKILL.md +13 -0
  279. package/dist/templates/core/.devin/AGENTS.md +5 -0
  280. package/dist/templates/core/.devin/config.json +12 -0
  281. package/dist/templates/core/.devin/skills/codex/SKILL.md +19 -0
  282. package/dist/templates/core/.devin/skills/devin/SKILL.md +13 -0
  283. package/dist/templates/core/.devin/skills/handoff/SKILL.md +11 -0
  284. package/dist/templates/core/.devin/skills/handoff-resume/SKILL.md +11 -0
  285. package/dist/templates/core/.devin/skills/meta-plan/SKILL.md +13 -0
  286. package/dist/templates/core/.windsurf/workflows/handoff-resume.md +9 -0
  287. package/dist/templates/{_shared → core}/.windsurf/workflows/handoff.md +1 -1
  288. package/dist/templates/{_shared → core}/.windsurf/workflows/meta-plan.md +1 -1
  289. package/dist/templates/core/hooks-ts/_utils/git-state.ts +2 -0
  290. package/dist/templates/{_shared → core}/hooks-ts/archive_plan.ts +15 -44
  291. package/dist/templates/core/hooks-ts/codex_explorer.ts +160 -0
  292. package/dist/templates/{_shared → core}/hooks-ts/context_monitor.ts +23 -55
  293. package/dist/templates/{_shared → core}/hooks-ts/file-suggestion.ts +5 -22
  294. package/dist/templates/{_shared → core}/hooks-ts/lint_after_edit.ts +7 -9
  295. package/dist/templates/core/hooks-ts/pre_compact.ts +36 -0
  296. package/dist/templates/{_shared → core}/hooks-ts/session_end.ts +38 -78
  297. package/dist/templates/{_shared → core}/hooks-ts/session_start.ts +5 -5
  298. package/dist/templates/core/hooks-ts/task_create_capture.ts +32 -0
  299. package/dist/templates/{_shared → core}/hooks-ts/task_update_capture.ts +9 -24
  300. package/dist/templates/core/hooks-ts/user_prompt_submit.ts +46 -0
  301. package/dist/templates/{_shared → core}/lib-ts/CLAUDE.md +27 -16
  302. package/dist/templates/{_shared → core}/lib-ts/context/CLAUDE.md +9 -6
  303. package/dist/templates/{_shared → core}/lib-ts/context/context-formatter.ts +16 -21
  304. package/dist/templates/{_shared → core}/lib-ts/context/context-selector.ts +8 -6
  305. package/dist/templates/{_shared → core}/lib-ts/context/context-store.ts +59 -20
  306. package/dist/templates/{_shared → core}/lib-ts/context/plan-manager.ts +19 -15
  307. package/dist/templates/{_shared → core}/lib-ts/context/task-tracker.ts +3 -3
  308. package/dist/templates/core/lib-ts/hooks/context-monitor-logic.ts +32 -0
  309. package/dist/templates/{_shared/lib-ts/base → core/lib-ts/hooks}/hook-utils.ts +179 -41
  310. package/dist/templates/core/lib-ts/hooks/prompt-binding-logic.ts +80 -0
  311. package/dist/templates/core/lib-ts/hooks/session-end-logic.ts +82 -0
  312. package/dist/templates/core/lib-ts/package.json +19 -0
  313. package/dist/templates/core/lib-ts/runtime/agent-launcher.ts +369 -0
  314. package/dist/templates/core/lib-ts/runtime/aiw-cli.ts +108 -0
  315. package/dist/templates/{_shared/lib-ts/base → core/lib-ts/runtime}/atomic-write.ts +12 -7
  316. package/dist/templates/{_shared/lib-ts/base → core/lib-ts/runtime}/cli-args.ts +24 -8
  317. package/dist/templates/{_shared/lib-ts/base → core/lib-ts/runtime}/constants.ts +326 -324
  318. package/dist/templates/core/lib-ts/runtime/executable-policy.ts +89 -0
  319. package/dist/templates/{_shared/lib-ts/base → core/lib-ts/runtime}/git-state.ts +6 -4
  320. package/dist/templates/{_shared/lib-ts/base → core/lib-ts/runtime}/inference.ts +60 -23
  321. package/dist/templates/{_shared/lib-ts/base → core/lib-ts/runtime}/lint-dispatch.ts +25 -23
  322. package/dist/templates/{_shared/lib-ts/base → core/lib-ts/runtime}/logger.ts +32 -29
  323. package/dist/templates/{_shared/lib-ts/base → core/lib-ts/runtime}/models.ts +9 -2
  324. package/dist/templates/core/lib-ts/runtime/platform-adapter.ts +33 -0
  325. package/dist/templates/{_shared/lib-ts/base → core/lib-ts/runtime}/preflight.ts +4 -3
  326. package/dist/templates/core/lib-ts/runtime/sentinel-ipc.ts +91 -0
  327. package/dist/templates/{_shared/lib-ts/base → core/lib-ts/runtime}/state-io.ts +20 -11
  328. package/dist/templates/core/lib-ts/runtime/stop-words.ts +185 -0
  329. package/dist/templates/core/lib-ts/runtime/subprocess-utils.ts +147 -0
  330. package/dist/templates/core/lib-ts/runtime/tmux-preflight.ts +93 -0
  331. package/dist/templates/{_shared/lib-ts/base → core/lib-ts/runtime}/utils.ts +34 -4
  332. package/dist/templates/core/lib-ts/schemas.ts +233 -0
  333. package/dist/templates/{_shared → core}/lib-ts/templates/formatters.ts +7 -5
  334. package/dist/templates/{_shared → core}/lib-ts/templates/plan-context.ts +2 -1
  335. package/dist/templates/{_shared → core}/lib-ts/tsconfig.json +3 -1
  336. package/dist/templates/{_shared → core}/lib-ts/types.ts +78 -77
  337. package/dist/templates/core/scripts/resolve-run.ts +93 -0
  338. package/dist/templates/{_shared → core}/scripts/resolve_context.ts +3 -3
  339. package/dist/templates/{_shared → core}/scripts/status_line.ts +26 -21
  340. package/dist/templates/core/skills/codex/CLAUDE.md +83 -0
  341. package/dist/templates/{_shared → core}/skills/codex/SKILL.md +27 -18
  342. package/dist/templates/{_shared → core}/skills/codex/lib/codex-watcher.ts +79 -113
  343. package/dist/templates/{_shared → core}/skills/codex/scripts/launch-codex.ts +134 -148
  344. package/dist/templates/{_shared → core}/skills/codex/scripts/watch-codex.ts +6 -4
  345. package/dist/templates/core/skills/devin/CLAUDE.md +122 -0
  346. package/dist/templates/core/skills/devin/SKILL.md +73 -0
  347. package/dist/templates/core/skills/devin/lib/devin-watcher.ts +300 -0
  348. package/dist/templates/core/skills/devin/scripts/launch-devin.ts +258 -0
  349. package/dist/templates/{_shared → core}/skills/handoff-system/CLAUDE.md +436 -433
  350. package/dist/templates/{_shared → core}/skills/handoff-system/lib/document-generator.ts +9 -7
  351. package/dist/templates/{_shared → core}/skills/handoff-system/lib/handoff-reader.ts +6 -4
  352. package/dist/templates/{_shared → core}/skills/handoff-system/scripts/resume_handoff.ts +10 -8
  353. package/dist/templates/{_shared → core}/skills/handoff-system/scripts/save_handoff.ts +12 -10
  354. package/dist/templates/{_shared → core}/skills/handoff-system/workflows/handoff-resume.md +2 -2
  355. package/dist/templates/{_shared → core}/skills/handoff-system/workflows/handoff.md +6 -5
  356. package/dist/templates/{_shared → core}/skills/meta-plan/CLAUDE.md +2 -1
  357. package/dist/templates/{_shared → core}/skills/meta-plan/workflows/meta-plan.md +8 -7
  358. package/oclif.manifest.json +89 -13
  359. package/package.json +13 -12
  360. package/dist/lib/base-command.d.ts +0 -114
  361. package/dist/lib/base-command.js +0 -153
  362. package/dist/lib/env-compat.d.ts +0 -18
  363. package/dist/lib/env-compat.js +0 -23
  364. package/dist/lib/stdin.d.ts +0 -48
  365. package/dist/lib/stdin.js +0 -60
  366. package/dist/templates/_shared/.claude/settings.json +0 -120
  367. package/dist/templates/_shared/.claude/skills/codex/SKILL.md +0 -35
  368. package/dist/templates/_shared/.claude/skills/handoff/SKILL.md +0 -13
  369. package/dist/templates/_shared/.claude/skills/handoff-resume/SKILL.md +0 -13
  370. package/dist/templates/_shared/.claude/skills/meta-plan/SKILL.md +0 -43
  371. package/dist/templates/_shared/.codex/workflows/codex.md +0 -11
  372. package/dist/templates/_shared/.codex/workflows/handoff.md +0 -226
  373. package/dist/templates/_shared/.codex/workflows/meta-plan.md +0 -347
  374. package/dist/templates/_shared/hooks-ts/_utils/git-state.ts +0 -2
  375. package/dist/templates/_shared/hooks-ts/pre_compact.ts +0 -49
  376. package/dist/templates/_shared/hooks-ts/task_create_capture.ts +0 -48
  377. package/dist/templates/_shared/hooks-ts/user_prompt_submit.ts +0 -93
  378. package/dist/templates/_shared/lib-ts/agent-exec/backends/headless.ts +0 -33
  379. package/dist/templates/_shared/lib-ts/agent-exec/backends/index.ts +0 -6
  380. package/dist/templates/_shared/lib-ts/agent-exec/backends/tmux.ts +0 -119
  381. package/dist/templates/_shared/lib-ts/agent-exec/execution-backend.ts +0 -50
  382. package/dist/templates/_shared/lib-ts/agent-exec/index.ts +0 -6
  383. package/dist/templates/_shared/lib-ts/agent-exec/structured-output.ts +0 -166
  384. package/dist/templates/_shared/lib-ts/base/launchers/tmux-launcher.ts +0 -173
  385. package/dist/templates/_shared/lib-ts/base/launchers/window-launcher.ts +0 -93
  386. package/dist/templates/_shared/lib-ts/base/launchers/wt-launcher.ts +0 -64
  387. package/dist/templates/_shared/lib-ts/base/pane-launcher.ts +0 -55
  388. package/dist/templates/_shared/lib-ts/base/sentinel-ipc.ts +0 -87
  389. package/dist/templates/_shared/lib-ts/base/stop-words.ts +0 -184
  390. package/dist/templates/_shared/lib-ts/base/subprocess-utils.ts +0 -249
  391. package/dist/templates/_shared/lib-ts/base/tmux-driver.ts +0 -341
  392. package/dist/templates/_shared/lib-ts/base/tmux-pane-placement.ts +0 -78
  393. package/dist/templates/_shared/lib-ts/package.json +0 -20
  394. package/dist/templates/_shared/scripts/resolve-run.ts +0 -62
  395. package/dist/templates/_shared/skills/codex/CLAUDE.md +0 -70
  396. package/dist/templates/cc-native/_cc-native/CLAUDE.md +0 -73
  397. package/dist/templates/cc-native/_cc-native/artifacts/CLAUDE.md +0 -64
  398. package/dist/templates/cc-native/_cc-native/lib-ts/CLAUDE.md +0 -70
  399. package/dist/templates/cc-native/_cc-native/plan-review/CODING-STANDARDS-CHECKLIST.md +0 -75
  400. package/dist/templates/cc-native/_cc-native/plan-review/agents/CLAUDE.md +0 -143
  401. package/dist/templates/cc-native/_cc-native/plan-review/agents/PLAN-ORCHESTRATOR.md +0 -213
  402. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-questions/PLAN-QUESTIONER.md +0 -70
  403. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/ARCH-EVOLUTION.md +0 -62
  404. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/ARCH-PATTERNS.md +0 -61
  405. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/ARCH-STRUCTURE.md +0 -62
  406. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/ASSUMPTION-TRACER.md +0 -56
  407. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/CLARITY-AUDITOR.md +0 -53
  408. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/COMPLETENESS-FEASIBILITY.md +0 -66
  409. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/COMPLETENESS-GAPS.md +0 -70
  410. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/COMPLETENESS-ORDERING.md +0 -62
  411. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/CONSTRAINT-VALIDATOR.md +0 -72
  412. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/DESIGN-ADR-VALIDATOR.md +0 -61
  413. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/DESIGN-SCALE-MATCHER.md +0 -64
  414. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/DEVILS-ADVOCATE.md +0 -56
  415. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/DOCUMENTATION-PHILOSOPHY.md +0 -86
  416. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/HANDOFF-READINESS.md +0 -59
  417. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/HIDDEN-COMPLEXITY.md +0 -58
  418. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/INCREMENTAL-DELIVERY.md +0 -66
  419. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/RISK-DEPENDENCY.md +0 -62
  420. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/RISK-FMEA.md +0 -66
  421. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/RISK-PREMORTEM.md +0 -71
  422. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/RISK-REVERSIBILITY.md +0 -74
  423. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/SCOPE-BOUNDARY.md +0 -77
  424. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/SIMPLICITY-GUARDIAN.md +0 -62
  425. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/SKEPTIC.md +0 -68
  426. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/TESTDRIVEN-BEHAVIOR-AUDITOR.md +0 -61
  427. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/TESTDRIVEN-CHARACTERIZATION.md +0 -71
  428. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/TESTDRIVEN-FIRST-VALIDATOR.md +0 -61
  429. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/TESTDRIVEN-PYRAMID-ANALYZER.md +0 -61
  430. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/TRADEOFF-COSTS.md +0 -67
  431. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/TRADEOFF-STAKEHOLDERS.md +0 -65
  432. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/VERIFY-COVERAGE.md +0 -74
  433. package/dist/templates/cc-native/_cc-native/plan-review/agents/plan-review/VERIFY-STRENGTH.md +0 -69
  434. package/dist/templates/cc-native/_cc-native/plan-review/lib/corroboration.ts +0 -172
  435. package/dist/templates/cc-native/_cc-native/plan-review/lib/reviewers/base/base-agent.ts +0 -7
@@ -0,0 +1,261 @@
1
+ import path from 'node:path';
2
+ import { checkVersionCompatibility, detectMultiplexer, ensureLspPatch, findExecutable, findToolPath, getClaudeCodeVersion, launchTerminal, ProcessSpawnError, quoteForSh, spawnProcess, } from '../../../platform/launch.js';
3
+ import { EXIT_CODES } from '../../../types/index.js';
4
+ import { clearProcessNestingVars, isCalledFromRepl } from '../../../lib/env-sanitizer.js';
5
+ import { PromptFileManager } from '../../../lib/prompt-file-manager.js';
6
+ import { SentinelManager } from '../../../lib/sentinel-manager.js';
7
+ import { formatPathWarning } from '../../../lib/spawn-errors.js';
8
+ import { buildSpawnedWindowArgs, parseExtraEnv, resolvePromptText, } from '../runtime-core/launch-options.js';
9
+ import { buildInlineArgs, buildSessionRequest, buildSplitRequest, formatSessionLaunchMessage, formatSplitSuccessMessage, formatVersionCheckMessages, QUICK_EXIT_THRESHOLD_MS, resolveInlineFallbackMessage, resolveSessionFallbackWarning, resolveToolConfig, resolveToolModeDebugMessage, shouldRetry, toJsonLaunchResult, } from '../runtime-core/launch-decisions.js';
10
+ async function runPreflightWarmup(command, host) {
11
+ try {
12
+ const result = await spawnProcess(command, ['--version'], { stdio: 'pipe' });
13
+ host.debug(`${command} preflight: exit=${result}`);
14
+ }
15
+ catch {
16
+ host.debug(`${command} preflight failed (non-fatal)`);
17
+ }
18
+ }
19
+ async function spawnInlineWithRetry(command, args, retryOnQuickExit, host) {
20
+ if (retryOnQuickExit) {
21
+ await runPreflightWarmup(command, host);
22
+ }
23
+ const start = Date.now();
24
+ let exitCode = await spawnProcess(command, args);
25
+ if (retryOnQuickExit && shouldRetry(Date.now() - start)) {
26
+ host.debug(`${command} exited in <${QUICK_EXIT_THRESHOLD_MS}ms — retrying (first-run init behavior)`);
27
+ exitCode = await spawnProcess(command, args);
28
+ }
29
+ return exitCode;
30
+ }
31
+ export async function executeLaunch(request, dependencies) {
32
+ const { cwd, flags, interactiveTty, platform, readPromptFile } = request;
33
+ const { host, now, pid, tempDir, writePromptFile } = dependencies;
34
+ // 1. Capture REPL context BEFORE clearing env vars (injectable for testing)
35
+ const calledFromRepl = (dependencies.isCalledFromRepl ?? isCalledFromRepl)();
36
+ (dependencies.clearNestingVars ?? clearProcessNestingVars)();
37
+ // Pure decision: resolve tool config
38
+ const toolConfig = resolveToolConfig(flags, platform);
39
+ const { cliCommand, cliArgs, launchFlag, toolMode } = toolConfig;
40
+ const disableMux = flags['no-tmux'];
41
+ const wantJson = flags.json;
42
+ const wantWait = flags.wait;
43
+ if (toolConfig.needsLspPatch) {
44
+ await ensureLspPatch({
45
+ debugLog: (message) => host.debug(message),
46
+ warn(message) {
47
+ host.warn(message);
48
+ },
49
+ });
50
+ }
51
+ let extraEnv = {};
52
+ try {
53
+ extraEnv = parseExtraEnv(flags.env);
54
+ }
55
+ catch (error) {
56
+ host.error(error instanceof Error ? error.message : '--env must be a valid JSON object string', {
57
+ exit: EXIT_CODES.INVALID_USAGE,
58
+ });
59
+ }
60
+ const promptPath = flags['prompt-path']?.trim() || undefined;
61
+ const promptText = resolvePromptText(flags.prompt, flags['prompt-file'], readPromptFile);
62
+ // 2. Handle --new (terminal window)
63
+ if (flags.new) {
64
+ host.debug(`Launching new terminal in: ${cwd}`);
65
+ let promptFilePath;
66
+ if (!promptPath && promptText) {
67
+ promptFilePath = path.join(tempDir, `aiwcli-prompt-${now()}-${pid}.txt`);
68
+ writePromptFile(promptFilePath, promptText);
69
+ }
70
+ const launchArgs = buildSpawnedWindowArgs({
71
+ useCodex: flags.codex,
72
+ useDevin: flags.devin,
73
+ disableTmux: disableMux,
74
+ ...(promptPath ? { promptPath } : {}),
75
+ ...(promptFilePath ? { promptFilePath } : {}),
76
+ ...(flags.env ? { rawEnvJson: flags.env } : {}),
77
+ ...(flags['tmux-session'] ? { tmuxSessionFlag: flags['tmux-session'] } : {}),
78
+ });
79
+ const launchCmd = launchArgs.map((arg) => quoteForSh(arg)).join(' ');
80
+ const result = await launchTerminal({
81
+ cwd,
82
+ command: launchCmd,
83
+ windowsShellPreference: platform === 'win32' ? 'mintty' : 'default',
84
+ debugLog: (message) => host.debug(message),
85
+ });
86
+ if (!result.success) {
87
+ host.error(`Failed to launch new terminal: ${result.error}`, { exit: EXIT_CODES.GENERAL_ERROR });
88
+ }
89
+ host.log(`New terminal launched with aiw launch${launchFlag ? ` ${launchFlag}` : ''}`);
90
+ return;
91
+ }
92
+ const toolDebugMsg = resolveToolModeDebugMessage(toolMode);
93
+ if (toolDebugMsg)
94
+ host.debug(toolDebugMsg);
95
+ // 3. Detect multiplexer + version check
96
+ const [versionCheck, mux] = await Promise.all([
97
+ toolConfig.skipVersionCheck
98
+ ? null
99
+ : getClaudeCodeVersion().then((v) => checkVersionCompatibility(v)),
100
+ disableMux ? null : detectMultiplexer(platform),
101
+ ]);
102
+ if (versionCheck) {
103
+ const msgs = formatVersionCheckMessages(versionCheck);
104
+ for (const line of msgs.debugLines)
105
+ host.debug(line);
106
+ if (msgs.warning)
107
+ host.warn(msgs.warning);
108
+ }
109
+ // 4. Resolve strategy — backend decides
110
+ const resolved = mux?.resolveStrategy({ calledFromRepl, platform, disableMux })
111
+ ?? { strategy: 'inline', reason: 'No multiplexer available' };
112
+ if (!mux || resolved.strategy === 'inline' || resolved.strategy === 'unavailable') {
113
+ // Pure decision: resolve fallback message
114
+ host.logInfo(resolveInlineFallbackMessage({
115
+ disableMux,
116
+ hasMux: Boolean(mux),
117
+ interactiveTty,
118
+ platform,
119
+ resolvedReason: resolved.reason,
120
+ }));
121
+ try {
122
+ // Pure decision: build inline args
123
+ const inlineArgs = buildInlineArgs(cliArgs, toolMode, promptText, promptPath);
124
+ const exitCode = await spawnInlineWithRetry(cliCommand, inlineArgs, toolConfig.retryOnQuickExit, host);
125
+ host.exit(exitCode);
126
+ }
127
+ catch (error) {
128
+ if (error instanceof ProcessSpawnError) {
129
+ host.error(error.message, { exit: EXIT_CODES.ENVIRONMENT_ERROR });
130
+ }
131
+ host.error('Unexpected launch failure.', { exit: EXIT_CODES.GENERAL_ERROR });
132
+ }
133
+ return;
134
+ }
135
+ // Lifecycle managers
136
+ const sentinelMgr = new SentinelManager();
137
+ const promptMgr = new PromptFileManager({ tempDir, now, pid });
138
+ // When --json is used without --wait, sentinel ownership transfers to the
139
+ // JSON caller (e.g. skill scripts). The CLI must NOT clean up the sentinel
140
+ // directory because the caller polls for sentinel.txt to detect pane close.
141
+ let sentinelOwnershipTransferred = false;
142
+ let exitCode = 0;
143
+ try {
144
+ const strategy = resolved.strategy;
145
+ if (strategy === 'split') {
146
+ // 5a. Split pane
147
+ host.logInfo(`Inside ${mux.backend} session — splitting new pane`);
148
+ const sentinelPath = sentinelMgr.create(cliCommand);
149
+ let effectivePromptPath = promptPath;
150
+ if (!effectivePromptPath && promptText) {
151
+ effectivePromptPath = promptMgr.materialize(promptText);
152
+ }
153
+ // Pure decision: build split request (fixes cliArgs mutation bug)
154
+ const splitParams = buildSplitRequest({
155
+ cliArgs,
156
+ toolMode,
157
+ effectivePromptPath,
158
+ extraEnv,
159
+ cwd,
160
+ split: flags.split ?? 'auto',
161
+ sentinelPath,
162
+ retryOnQuickExit: toolConfig.retryOnQuickExit,
163
+ });
164
+ const splitResult = await mux.split({
165
+ toolName: cliCommand,
166
+ args: splitParams.toolArgs,
167
+ env: splitParams.env,
168
+ cwd: splitParams.cwd,
169
+ mode: splitParams.mode,
170
+ split: splitParams.split,
171
+ promptPath: splitParams.splitPromptPath,
172
+ sentinelPath: splitParams.sentinelPath,
173
+ holdPane: splitParams.holdPane,
174
+ retryOnQuickExit: splitParams.retryOnQuickExit,
175
+ });
176
+ if (wantJson) {
177
+ const jsonExitCode = wantWait && splitResult.launched && splitResult.sentinelPath
178
+ ? await sentinelMgr.waitForExit(splitResult.sentinelPath)
179
+ : splitResult.exitCode ?? null;
180
+ // When returning sentinel path to caller without waiting, transfer
181
+ // ownership so the finally block does not delete the directory.
182
+ if (!wantWait && splitResult.launched && splitResult.sentinelPath) {
183
+ sentinelOwnershipTransferred = true;
184
+ }
185
+ host.log(JSON.stringify(toJsonLaunchResult(splitResult, jsonExitCode)));
186
+ host.exit(jsonExitCode ?? 0);
187
+ }
188
+ if (splitResult.launched) {
189
+ host.logInfo(formatSplitSuccessMessage(mux.backend, splitResult.handle));
190
+ if (wantWait && splitResult.sentinelPath) {
191
+ const waitedExitCode = await sentinelMgr.waitForExit(splitResult.sentinelPath);
192
+ host.exit(waitedExitCode ?? 1);
193
+ }
194
+ return;
195
+ }
196
+ host.logWarning(`Pane split failed (${splitResult.reason}), launching directly`);
197
+ // Pure decision: build inline args for fallback
198
+ const fallbackArgs = buildInlineArgs(cliArgs, toolMode, promptText, promptPath);
199
+ exitCode = await spawnInlineWithRetry(cliCommand, fallbackArgs, toolConfig.retryOnQuickExit, host);
200
+ }
201
+ else {
202
+ // 5b. Create session
203
+ const resolvedPath = findToolPath(cliCommand) ?? findExecutable(cliCommand);
204
+ if (resolvedPath) {
205
+ // Pure decision: build session request
206
+ const sessionParams = buildSessionRequest({
207
+ cliArgs,
208
+ toolMode,
209
+ promptPath,
210
+ promptText,
211
+ tmuxSessionFlag: flags['tmux-session'],
212
+ cwd,
213
+ now: now(),
214
+ pid,
215
+ });
216
+ host.logInfo(formatSessionLaunchMessage(mux.backend, sessionParams.sessionName, sessionParams.reattach));
217
+ const result = await mux.createSession({
218
+ sessionName: sessionParams.sessionName,
219
+ reattach: sessionParams.reattach,
220
+ toolPath: resolvedPath,
221
+ toolArgs: sessionParams.toolArgs,
222
+ cwd,
223
+ promptText: sessionParams.promptText,
224
+ });
225
+ if (result.launched) {
226
+ exitCode = result.exitCode ?? 0;
227
+ if (wantJson) {
228
+ host.log(JSON.stringify(toJsonLaunchResult(result, exitCode)));
229
+ host.exit(exitCode);
230
+ }
231
+ }
232
+ else {
233
+ // Pure decision: resolve fallback warning
234
+ if (result.reason) {
235
+ host.logWarning(resolveSessionFallbackWarning(mux.backend, result.reason));
236
+ }
237
+ const fallbackArgs = buildInlineArgs(cliArgs, toolMode, promptText, promptPath);
238
+ exitCode = await spawnInlineWithRetry(cliCommand, fallbackArgs, toolConfig.retryOnQuickExit, host);
239
+ }
240
+ }
241
+ else {
242
+ host.logWarning(formatPathWarning(cliCommand));
243
+ const fallbackArgs = buildInlineArgs(cliArgs, toolMode, promptText, promptPath);
244
+ exitCode = await spawnInlineWithRetry(cliCommand, fallbackArgs, toolConfig.retryOnQuickExit, host);
245
+ }
246
+ }
247
+ }
248
+ catch (error) {
249
+ if (error instanceof ProcessSpawnError) {
250
+ host.error(error.message, { exit: EXIT_CODES.ENVIRONMENT_ERROR });
251
+ }
252
+ host.error('Unexpected launch failure.', { exit: EXIT_CODES.GENERAL_ERROR });
253
+ }
254
+ finally {
255
+ if (!sentinelOwnershipTransferred) {
256
+ sentinelMgr.cleanupAll();
257
+ }
258
+ promptMgr.cleanup();
259
+ }
260
+ host.exit(exitCode);
261
+ }
@@ -0,0 +1,82 @@
1
+ /**
2
+ * Pure decision functions extracted from execute-launch.ts.
3
+ * No side effects — all functions are deterministic string/config transforms.
4
+ */
5
+ import type { LaunchResult } from '../../../platform/launch.js';
6
+ import type { InlineFallbackContext, JsonLaunchResult, LaunchFlags, SessionRequestParams, SplitRequestParams, ToolConfig, ToolMode } from '../contracts.js';
7
+ export declare const QUICK_EXIT_THRESHOLD_MS = 10000;
8
+ /**
9
+ * Return the debug message for tool mode, or undefined if none (claude has no special message).
10
+ */
11
+ export declare function resolveToolModeDebugMessage(toolMode: ToolMode): string | undefined;
12
+ /**
13
+ * Format version check results into debug lines and an optional warning.
14
+ */
15
+ export declare function formatVersionCheckMessages(versionCheck: {
16
+ compatible: boolean;
17
+ version?: null | string;
18
+ warning?: string;
19
+ }): {
20
+ debugLines: string[];
21
+ warning?: string | undefined;
22
+ };
23
+ /**
24
+ * Format the success message after a split pane launch.
25
+ */
26
+ export declare function formatSplitSuccessMessage(backend: string, handle?: string): string;
27
+ /**
28
+ * Format the info message when launching in a session.
29
+ */
30
+ export declare function formatSessionLaunchMessage(backend: string, sessionName: string, reattach: boolean): string;
31
+ /**
32
+ * Determine which CLI tool to launch and its configuration.
33
+ */
34
+ export declare function resolveToolConfig(flags: Pick<LaunchFlags, 'codex' | 'devin'>, platform: NodeJS.Platform): ToolConfig;
35
+ /**
36
+ * Decide the informational message to log when falling back to inline mode.
37
+ */
38
+ export declare function resolveInlineFallbackMessage(ctx: InlineFallbackContext): string;
39
+ /**
40
+ * Build the args array for an inline process spawn.
41
+ * Always returns a new array — never mutates input.
42
+ */
43
+ export declare function buildInlineArgs(cliArgs: readonly string[], toolMode: ToolMode, promptText: string | undefined, promptPath: string | undefined): string[];
44
+ /**
45
+ * Build split pane parameters.
46
+ * Returns a new toolArgs array — fixes the cliArgs mutation bug.
47
+ */
48
+ export declare function buildSplitRequest(params: {
49
+ cliArgs: readonly string[];
50
+ cwd: string;
51
+ effectivePromptPath: string | undefined;
52
+ extraEnv: Record<string, string>;
53
+ retryOnQuickExit: boolean;
54
+ sentinelPath: string;
55
+ split: 'auto' | 'horizontal' | 'vertical';
56
+ toolMode: ToolMode;
57
+ }): SplitRequestParams;
58
+ /**
59
+ * Build session creation parameters.
60
+ */
61
+ export declare function buildSessionRequest(params: {
62
+ cliArgs: readonly string[];
63
+ cwd: string;
64
+ now: number;
65
+ pid: number;
66
+ promptPath: string | undefined;
67
+ promptText: string | undefined;
68
+ tmuxSessionFlag: string | undefined;
69
+ toolMode: ToolMode;
70
+ }): SessionRequestParams;
71
+ /**
72
+ * Decide warning message when session creation fails and we fall back inline.
73
+ */
74
+ export declare function resolveSessionFallbackWarning(backend: string, reason: string | undefined): string;
75
+ /**
76
+ * Pure timing decision for retry logic.
77
+ */
78
+ export declare function shouldRetry(elapsedMs: number, threshold?: number): boolean;
79
+ /**
80
+ * Convert a LaunchResult to JSON-serializable form.
81
+ */
82
+ export declare function toJsonLaunchResult(result: LaunchResult, exitCode: null | number): JsonLaunchResult;
@@ -0,0 +1,202 @@
1
+ /**
2
+ * Pure decision functions extracted from execute-launch.ts.
3
+ * No side effects — all functions are deterministic string/config transforms.
4
+ */
5
+ import path from 'node:path';
6
+ import { buildUniqueSessionName, sanitizeSessionName } from './launch-options.js';
7
+ export const QUICK_EXIT_THRESHOLD_MS = 10_000;
8
+ /**
9
+ * Return the debug message for tool mode, or undefined if none (claude has no special message).
10
+ */
11
+ export function resolveToolModeDebugMessage(toolMode) {
12
+ if (toolMode === 'codex')
13
+ return 'Launching Codex with --yolo flag';
14
+ if (toolMode === 'devin')
15
+ return 'Launching Devin with --permission-mode dangerous';
16
+ return undefined;
17
+ }
18
+ /**
19
+ * Format version check results into debug lines and an optional warning.
20
+ */
21
+ export function formatVersionCheckMessages(versionCheck) {
22
+ return {
23
+ debugLines: [
24
+ `Claude Code version: ${versionCheck.version ?? 'unknown'}`,
25
+ `Compatibility status: ${versionCheck.compatible ? 'compatible' : 'incompatible'}`,
26
+ ],
27
+ ...(versionCheck.warning ? { warning: versionCheck.warning } : {}),
28
+ };
29
+ }
30
+ /**
31
+ * Format the success message after a split pane launch.
32
+ */
33
+ export function formatSplitSuccessMessage(backend, handle) {
34
+ if (handle) {
35
+ return `Launched in ${backend} pane: ${handle}`;
36
+ }
37
+ return `Launched in ${backend}`;
38
+ }
39
+ /**
40
+ * Format the info message when launching in a session.
41
+ */
42
+ export function formatSessionLaunchMessage(backend, sessionName, reattach) {
43
+ if (reattach) {
44
+ return `Launching in ${backend} session: ${sessionName} (reuse/attach)`;
45
+ }
46
+ return `Launching in new ${backend} session: ${sessionName}`;
47
+ }
48
+ function buildCodexArgs(platform) {
49
+ if (platform !== 'win32')
50
+ return ['--yolo'];
51
+ return ['-c', 'shell_type="bash"', '--yolo'];
52
+ }
53
+ function buildDevinArgs() {
54
+ return ['--permission-mode', 'dangerous'];
55
+ }
56
+ /**
57
+ * Determine which CLI tool to launch and its configuration.
58
+ */
59
+ export function resolveToolConfig(flags, platform) {
60
+ if (flags.devin) {
61
+ return {
62
+ cliCommand: 'devin',
63
+ cliArgs: buildDevinArgs(),
64
+ launchFlag: '--devin',
65
+ toolMode: 'devin',
66
+ retryOnQuickExit: true,
67
+ needsLspPatch: false,
68
+ skipVersionCheck: true,
69
+ };
70
+ }
71
+ if (flags.codex) {
72
+ return {
73
+ cliCommand: 'codex',
74
+ cliArgs: buildCodexArgs(platform),
75
+ launchFlag: '--codex',
76
+ toolMode: 'codex',
77
+ retryOnQuickExit: false,
78
+ needsLspPatch: false,
79
+ skipVersionCheck: true,
80
+ };
81
+ }
82
+ return {
83
+ cliCommand: 'claude',
84
+ cliArgs: ['--dangerously-skip-permissions'],
85
+ launchFlag: '',
86
+ toolMode: 'claude',
87
+ retryOnQuickExit: false,
88
+ needsLspPatch: platform === 'win32',
89
+ skipVersionCheck: false,
90
+ };
91
+ }
92
+ /**
93
+ * Decide the informational message to log when falling back to inline mode.
94
+ */
95
+ export function resolveInlineFallbackMessage(ctx) {
96
+ if (!ctx.hasMux) {
97
+ if (ctx.disableMux) {
98
+ return 'Multiplexer disabled via --no-tmux — launching inline';
99
+ }
100
+ if (!ctx.interactiveTty) {
101
+ return 'Non-interactive terminal — launching inline';
102
+ }
103
+ if (ctx.platform === 'win32') {
104
+ return 'No multiplexer found — launching inline. Run inside WezTerm or install psmux for session management.';
105
+ }
106
+ return 'No multiplexer found — launching inline. Install tmux for session management.';
107
+ }
108
+ return ctx.resolvedReason ?? 'Launching inline';
109
+ }
110
+ /**
111
+ * Build the args array for an inline process spawn.
112
+ * Always returns a new array — never mutates input.
113
+ */
114
+ export function buildInlineArgs(cliArgs, toolMode, promptText, promptPath) {
115
+ if (toolMode === 'devin' && promptPath) {
116
+ return [...cliArgs, '--prompt-file', promptPath];
117
+ }
118
+ if (promptText) {
119
+ return [...cliArgs, promptText];
120
+ }
121
+ return [...cliArgs];
122
+ }
123
+ /**
124
+ * Build split pane parameters.
125
+ * Returns a new toolArgs array — fixes the cliArgs mutation bug.
126
+ */
127
+ export function buildSplitRequest(params) {
128
+ let toolArgs;
129
+ let splitPromptPath;
130
+ if (params.toolMode === 'devin' && params.effectivePromptPath) {
131
+ toolArgs = [...params.cliArgs, '--prompt-file', params.effectivePromptPath];
132
+ splitPromptPath = undefined;
133
+ }
134
+ else {
135
+ toolArgs = [...params.cliArgs];
136
+ splitPromptPath = params.effectivePromptPath;
137
+ }
138
+ return {
139
+ toolArgs,
140
+ splitPromptPath,
141
+ env: params.extraEnv,
142
+ cwd: params.cwd,
143
+ mode: 'repl',
144
+ split: params.split,
145
+ sentinelPath: params.sentinelPath,
146
+ holdPane: false,
147
+ retryOnQuickExit: params.retryOnQuickExit,
148
+ };
149
+ }
150
+ /**
151
+ * Build session creation parameters.
152
+ */
153
+ export function buildSessionRequest(params) {
154
+ const sessionFromFlag = params.tmuxSessionFlag?.trim();
155
+ const reattach = Boolean(sessionFromFlag && sessionFromFlag.length > 0);
156
+ const sessionName = reattach
157
+ ? sanitizeSessionName(sessionFromFlag)
158
+ : buildUniqueSessionName(`aiw-${path.basename(params.cwd)}`, params.now, params.pid);
159
+ const toolArgs = params.toolMode === 'devin' && params.promptPath
160
+ ? [...params.cliArgs, '--prompt-file', params.promptPath]
161
+ : [...params.cliArgs];
162
+ const promptText = params.toolMode === 'devin' ? undefined : params.promptText;
163
+ return { sessionName, reattach, toolArgs, promptText };
164
+ }
165
+ /**
166
+ * Decide warning message when session creation fails and we fall back inline.
167
+ */
168
+ export function resolveSessionFallbackWarning(backend, reason) {
169
+ if (!reason)
170
+ return 'Session creation failed — launching inline';
171
+ if (reason.includes('not found') || reason.includes('unavailable')) {
172
+ const hint = backend === 'psmux' ? ' Install with: winget install psmux' : '';
173
+ return `${backend} unavailable — launching inline.${hint}`;
174
+ }
175
+ if (reason.includes('too old')) {
176
+ const hint = backend === 'psmux' ? ' Update with: winget upgrade psmux' : '';
177
+ return `${reason} — launching inline.${hint}`;
178
+ }
179
+ if (backend === 'psmux' && reason.includes('attach failed')) {
180
+ return `${reason} — launching inline. Recovery: run "psmux kill-server" and relaunch if this persists.`;
181
+ }
182
+ return `${reason} — launching inline`;
183
+ }
184
+ /**
185
+ * Pure timing decision for retry logic.
186
+ */
187
+ export function shouldRetry(elapsedMs, threshold = QUICK_EXIT_THRESHOLD_MS) {
188
+ return elapsedMs < threshold;
189
+ }
190
+ /**
191
+ * Convert a LaunchResult to JSON-serializable form.
192
+ */
193
+ export function toJsonLaunchResult(result, exitCode) {
194
+ return {
195
+ launched: result.launched,
196
+ backend: result.backend,
197
+ handle: result.handle ?? null,
198
+ sentinelPath: result.sentinelPath ?? null,
199
+ exitCode,
200
+ reason: result.reason ?? null,
201
+ };
202
+ }
@@ -0,0 +1,14 @@
1
+ export interface BuildSpawnedWindowArgsParams {
2
+ disableTmux: boolean;
3
+ promptFilePath?: string | undefined;
4
+ promptPath?: string | undefined;
5
+ rawEnvJson?: string | undefined;
6
+ tmuxSessionFlag?: string | undefined;
7
+ useCodex: boolean;
8
+ useDevin?: boolean;
9
+ }
10
+ export declare function parseExtraEnv(raw: string | undefined): Record<string, string>;
11
+ export declare function resolvePromptText(promptFlag: string | undefined, promptFileFlag: string | undefined, readFile: (filePath: string) => string | undefined): string | undefined;
12
+ export declare function buildSpawnedWindowArgs(params: BuildSpawnedWindowArgsParams): string[];
13
+ export declare function sanitizeSessionName(input: string): string;
14
+ export declare function buildUniqueSessionName(base: string, now?: number, pid?: number): string;
@@ -0,0 +1,69 @@
1
+ export function parseExtraEnv(raw) {
2
+ if (!raw)
3
+ return {};
4
+ let parsed;
5
+ try {
6
+ parsed = JSON.parse(raw);
7
+ }
8
+ catch {
9
+ throw new Error('--env must be a valid JSON object string');
10
+ }
11
+ if (!parsed || typeof parsed !== 'object' || Array.isArray(parsed)) {
12
+ throw new Error('--env must be a valid JSON object string');
13
+ }
14
+ return parsed;
15
+ }
16
+ export function resolvePromptText(promptFlag, promptFileFlag, readFile) {
17
+ const promptText = promptFlag?.trim();
18
+ if (promptText)
19
+ return promptText;
20
+ const promptFilePath = promptFileFlag?.trim();
21
+ if (!promptFilePath)
22
+ return undefined;
23
+ try {
24
+ const fromFile = readFile(promptFilePath)?.trim();
25
+ return fromFile || undefined;
26
+ }
27
+ catch {
28
+ return undefined;
29
+ }
30
+ }
31
+ export function buildSpawnedWindowArgs(params) {
32
+ const { useCodex, useDevin, disableTmux, promptFilePath, promptPath, rawEnvJson, tmuxSessionFlag } = params;
33
+ const parts = ['aiw', 'launch', '--spawned-window'];
34
+ if (useDevin)
35
+ parts.push('--devin');
36
+ else if (useCodex)
37
+ parts.push('--codex');
38
+ if (disableTmux)
39
+ parts.push('--no-tmux');
40
+ const tmuxSession = tmuxSessionFlag?.trim();
41
+ if (tmuxSession) {
42
+ parts.push('--tmux-session', tmuxSession);
43
+ }
44
+ const envJson = rawEnvJson?.trim();
45
+ if (envJson) {
46
+ parts.push('--env', envJson);
47
+ }
48
+ if (promptPath) {
49
+ parts.push('--prompt-path', promptPath);
50
+ }
51
+ else if (promptFilePath) {
52
+ parts.push('--prompt-file', promptFilePath);
53
+ }
54
+ return parts;
55
+ }
56
+ export function sanitizeSessionName(input) {
57
+ const trimmed = input.trim().toLowerCase();
58
+ const safe = trimmed
59
+ .replaceAll(/[^a-z0-9_-]/g, '-')
60
+ .replaceAll(/-+/g, '-')
61
+ .replaceAll(/^[-_]+|[-_]+$/g, '');
62
+ return safe || 'aiw';
63
+ }
64
+ export function buildUniqueSessionName(base, now = Date.now(), pid = process.pid) {
65
+ const safeBase = sanitizeSessionName(base);
66
+ const timestamp = now.toString(36);
67
+ const pidPart = pid.toString(36);
68
+ return sanitizeSessionName(`${safeBase}-${timestamp}-${pidPart}`);
69
+ }
@@ -0,0 +1,18 @@
1
+ import { Command } from '@oclif/core';
2
+ import { type Ora } from 'ora';
3
+ export default abstract class BaseCommand extends Command {
4
+ static baseFlags: {
5
+ debug: import("@oclif/core/interfaces").BooleanFlag<boolean>;
6
+ help: import("@oclif/core/interfaces").BooleanFlag<void>;
7
+ quiet: import("@oclif/core/interfaces").BooleanFlag<boolean>;
8
+ };
9
+ init(): Promise<void>;
10
+ protected isQuiet(): boolean;
11
+ protected logDebug(message: string): void;
12
+ protected logError(message: string): void;
13
+ protected logInfo(message: string): void;
14
+ protected logSuccess(message: string): void;
15
+ protected logWarning(message: string): void;
16
+ abstract run(): Promise<void>;
17
+ protected spinner(text: string): Ora;
18
+ }