oh-my-codex 0.15.2 → 0.16.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 (524) hide show
  1. package/Cargo.lock +10 -7
  2. package/Cargo.toml +1 -1
  3. package/README.md +3 -0
  4. package/crates/omx-explore/Cargo.toml +3 -0
  5. package/crates/omx-explore/src/main.rs +517 -16
  6. package/dist/agents/__tests__/native-config.test.js +33 -0
  7. package/dist/agents/__tests__/native-config.test.js.map +1 -1
  8. package/dist/autoresearch/goal.d.ts +90 -0
  9. package/dist/autoresearch/goal.d.ts.map +1 -0
  10. package/dist/autoresearch/goal.js +237 -0
  11. package/dist/autoresearch/goal.js.map +1 -0
  12. package/dist/autoresearch/skill-validation.d.ts +1 -0
  13. package/dist/autoresearch/skill-validation.d.ts.map +1 -1
  14. package/dist/autoresearch/skill-validation.js +10 -3
  15. package/dist/autoresearch/skill-validation.js.map +1 -1
  16. package/dist/catalog/__tests__/generator.test.js +9 -4
  17. package/dist/catalog/__tests__/generator.test.js.map +1 -1
  18. package/dist/catalog/__tests__/plugin-bundle-ssot.test.js +29 -2
  19. package/dist/catalog/__tests__/plugin-bundle-ssot.test.js.map +1 -1
  20. package/dist/catalog/__tests__/schema.test.js +14 -3
  21. package/dist/catalog/__tests__/schema.test.js.map +1 -1
  22. package/dist/catalog/schema.js +1 -1
  23. package/dist/catalog/schema.js.map +1 -1
  24. package/dist/cli/__tests__/autoresearch-goal.test.d.ts +2 -0
  25. package/dist/cli/__tests__/autoresearch-goal.test.d.ts.map +1 -0
  26. package/dist/cli/__tests__/autoresearch-goal.test.js +194 -0
  27. package/dist/cli/__tests__/autoresearch-goal.test.js.map +1 -0
  28. package/dist/cli/__tests__/cleanup.test.js +82 -1
  29. package/dist/cli/__tests__/cleanup.test.js.map +1 -1
  30. package/dist/cli/__tests__/codex-plugin-layout.test.js +7 -4
  31. package/dist/cli/__tests__/codex-plugin-layout.test.js.map +1 -1
  32. package/dist/cli/__tests__/doctor-context-window-warning.test.d.ts +2 -0
  33. package/dist/cli/__tests__/doctor-context-window-warning.test.d.ts.map +1 -0
  34. package/dist/cli/__tests__/doctor-context-window-warning.test.js +122 -0
  35. package/dist/cli/__tests__/doctor-context-window-warning.test.js.map +1 -0
  36. package/dist/cli/__tests__/doctor-warning-copy.test.js +25 -2
  37. package/dist/cli/__tests__/doctor-warning-copy.test.js.map +1 -1
  38. package/dist/cli/__tests__/exec.test.js +1 -0
  39. package/dist/cli/__tests__/exec.test.js.map +1 -1
  40. package/dist/cli/__tests__/explore.test.js +48 -18
  41. package/dist/cli/__tests__/explore.test.js.map +1 -1
  42. package/dist/cli/__tests__/index.test.js +222 -10
  43. package/dist/cli/__tests__/index.test.js.map +1 -1
  44. package/dist/cli/__tests__/launch-fallback.test.js +58 -0
  45. package/dist/cli/__tests__/launch-fallback.test.js.map +1 -1
  46. package/dist/cli/__tests__/mcp-serve.test.js +27 -1
  47. package/dist/cli/__tests__/mcp-serve.test.js.map +1 -1
  48. package/dist/cli/__tests__/native-assets.test.js +26 -1
  49. package/dist/cli/__tests__/native-assets.test.js.map +1 -1
  50. package/dist/cli/__tests__/package-bin-contract.test.js +2 -2
  51. package/dist/cli/__tests__/package-bin-contract.test.js.map +1 -1
  52. package/dist/cli/__tests__/performance-goal.test.d.ts +2 -0
  53. package/dist/cli/__tests__/performance-goal.test.d.ts.map +1 -0
  54. package/dist/cli/__tests__/performance-goal.test.js +144 -0
  55. package/dist/cli/__tests__/performance-goal.test.js.map +1 -0
  56. package/dist/cli/__tests__/question.test.js +8 -0
  57. package/dist/cli/__tests__/question.test.js.map +1 -1
  58. package/dist/cli/__tests__/ralph-goal-mode-contract.test.d.ts +2 -0
  59. package/dist/cli/__tests__/ralph-goal-mode-contract.test.d.ts.map +1 -0
  60. package/dist/cli/__tests__/ralph-goal-mode-contract.test.js +31 -0
  61. package/dist/cli/__tests__/ralph-goal-mode-contract.test.js.map +1 -0
  62. package/dist/cli/__tests__/ralph-prd-deep-interview.test.js +5 -4
  63. package/dist/cli/__tests__/ralph-prd-deep-interview.test.js.map +1 -1
  64. package/dist/cli/__tests__/ralph-prd-smoke.test.js +7 -0
  65. package/dist/cli/__tests__/ralph-prd-smoke.test.js.map +1 -1
  66. package/dist/cli/__tests__/ralph.test.js +59 -1
  67. package/dist/cli/__tests__/ralph.test.js.map +1 -1
  68. package/dist/cli/__tests__/setup-install-mode.test.js +57 -21
  69. package/dist/cli/__tests__/setup-install-mode.test.js.map +1 -1
  70. package/dist/cli/__tests__/setup-refresh.test.js +27 -8
  71. package/dist/cli/__tests__/setup-refresh.test.js.map +1 -1
  72. package/dist/cli/__tests__/setup-scope.test.js +20 -10
  73. package/dist/cli/__tests__/setup-scope.test.js.map +1 -1
  74. package/dist/cli/__tests__/setup-skill-validation.test.js +11 -11
  75. package/dist/cli/__tests__/setup-skill-validation.test.js.map +1 -1
  76. package/dist/cli/__tests__/setup-skills-overwrite.test.js +12 -12
  77. package/dist/cli/__tests__/setup-skills-overwrite.test.js.map +1 -1
  78. package/dist/cli/__tests__/team.test.js +242 -10
  79. package/dist/cli/__tests__/team.test.js.map +1 -1
  80. package/dist/cli/__tests__/ultragoal.test.d.ts +2 -0
  81. package/dist/cli/__tests__/ultragoal.test.d.ts.map +1 -0
  82. package/dist/cli/__tests__/ultragoal.test.js +106 -0
  83. package/dist/cli/__tests__/ultragoal.test.js.map +1 -0
  84. package/dist/cli/__tests__/uninstall.test.js +11 -0
  85. package/dist/cli/__tests__/uninstall.test.js.map +1 -1
  86. package/dist/cli/autoresearch-goal.d.ts +3 -0
  87. package/dist/cli/autoresearch-goal.d.ts.map +1 -0
  88. package/dist/cli/autoresearch-goal.js +175 -0
  89. package/dist/cli/autoresearch-goal.js.map +1 -0
  90. package/dist/cli/cleanup.d.ts +3 -1
  91. package/dist/cli/cleanup.d.ts.map +1 -1
  92. package/dist/cli/cleanup.js +42 -2
  93. package/dist/cli/cleanup.js.map +1 -1
  94. package/dist/cli/doctor.d.ts.map +1 -1
  95. package/dist/cli/doctor.js +95 -3
  96. package/dist/cli/doctor.js.map +1 -1
  97. package/dist/cli/explore.d.ts.map +1 -1
  98. package/dist/cli/explore.js +10 -2
  99. package/dist/cli/explore.js.map +1 -1
  100. package/dist/cli/index.d.ts +21 -2
  101. package/dist/cli/index.d.ts.map +1 -1
  102. package/dist/cli/index.js +268 -30
  103. package/dist/cli/index.js.map +1 -1
  104. package/dist/cli/mcp-serve.d.ts +1 -0
  105. package/dist/cli/mcp-serve.d.ts.map +1 -1
  106. package/dist/cli/mcp-serve.js +8 -0
  107. package/dist/cli/mcp-serve.js.map +1 -1
  108. package/dist/cli/native-assets.js +1 -1
  109. package/dist/cli/native-assets.js.map +1 -1
  110. package/dist/cli/performance-goal.d.ts +3 -0
  111. package/dist/cli/performance-goal.d.ts.map +1 -0
  112. package/dist/cli/performance-goal.js +186 -0
  113. package/dist/cli/performance-goal.js.map +1 -0
  114. package/dist/cli/ralph.d.ts +2 -0
  115. package/dist/cli/ralph.d.ts.map +1 -1
  116. package/dist/cli/ralph.js +25 -1
  117. package/dist/cli/ralph.js.map +1 -1
  118. package/dist/cli/setup.d.ts.map +1 -1
  119. package/dist/cli/setup.js +13 -6
  120. package/dist/cli/setup.js.map +1 -1
  121. package/dist/cli/team.d.ts +6 -0
  122. package/dist/cli/team.d.ts.map +1 -1
  123. package/dist/cli/team.js +113 -33
  124. package/dist/cli/team.js.map +1 -1
  125. package/dist/cli/tmux-hook.d.ts.map +1 -1
  126. package/dist/cli/tmux-hook.js +2 -1
  127. package/dist/cli/tmux-hook.js.map +1 -1
  128. package/dist/cli/ultragoal.d.ts +3 -0
  129. package/dist/cli/ultragoal.d.ts.map +1 -0
  130. package/dist/cli/ultragoal.js +191 -0
  131. package/dist/cli/ultragoal.js.map +1 -0
  132. package/dist/cli/uninstall.d.ts.map +1 -1
  133. package/dist/cli/uninstall.js +4 -2
  134. package/dist/cli/uninstall.js.map +1 -1
  135. package/dist/config/__tests__/generator-idempotent.test.js +39 -6
  136. package/dist/config/__tests__/generator-idempotent.test.js.map +1 -1
  137. package/dist/config/__tests__/generator-notify.test.js +5 -0
  138. package/dist/config/__tests__/generator-notify.test.js.map +1 -1
  139. package/dist/config/commit-lore-guard.d.ts +3 -0
  140. package/dist/config/commit-lore-guard.d.ts.map +1 -0
  141. package/dist/config/commit-lore-guard.js +9 -0
  142. package/dist/config/commit-lore-guard.js.map +1 -0
  143. package/dist/config/generator.d.ts +14 -4
  144. package/dist/config/generator.d.ts.map +1 -1
  145. package/dist/config/generator.js +166 -66
  146. package/dist/config/generator.js.map +1 -1
  147. package/dist/config/omx-first-party-mcp.d.ts +1 -0
  148. package/dist/config/omx-first-party-mcp.d.ts.map +1 -1
  149. package/dist/config/omx-first-party-mcp.js +4 -1
  150. package/dist/config/omx-first-party-mcp.js.map +1 -1
  151. package/dist/goal-workflows/__tests__/artifacts.test.d.ts +2 -0
  152. package/dist/goal-workflows/__tests__/artifacts.test.d.ts.map +1 -0
  153. package/dist/goal-workflows/__tests__/artifacts.test.js +96 -0
  154. package/dist/goal-workflows/__tests__/artifacts.test.js.map +1 -0
  155. package/dist/goal-workflows/__tests__/codex-goal-snapshot.test.d.ts +2 -0
  156. package/dist/goal-workflows/__tests__/codex-goal-snapshot.test.d.ts.map +1 -0
  157. package/dist/goal-workflows/__tests__/codex-goal-snapshot.test.js +54 -0
  158. package/dist/goal-workflows/__tests__/codex-goal-snapshot.test.js.map +1 -0
  159. package/dist/goal-workflows/artifacts.d.ts +62 -0
  160. package/dist/goal-workflows/artifacts.d.ts.map +1 -0
  161. package/dist/goal-workflows/artifacts.js +132 -0
  162. package/dist/goal-workflows/artifacts.js.map +1 -0
  163. package/dist/goal-workflows/codex-goal-snapshot.d.ts +28 -0
  164. package/dist/goal-workflows/codex-goal-snapshot.d.ts.map +1 -0
  165. package/dist/goal-workflows/codex-goal-snapshot.js +110 -0
  166. package/dist/goal-workflows/codex-goal-snapshot.js.map +1 -0
  167. package/dist/goal-workflows/handoff.d.ts +10 -0
  168. package/dist/goal-workflows/handoff.d.ts.map +1 -0
  169. package/dist/goal-workflows/handoff.js +31 -0
  170. package/dist/goal-workflows/handoff.js.map +1 -0
  171. package/dist/goal-workflows/validation.d.ts +13 -0
  172. package/dist/goal-workflows/validation.d.ts.map +1 -0
  173. package/dist/goal-workflows/validation.js +36 -0
  174. package/dist/goal-workflows/validation.js.map +1 -0
  175. package/dist/hooks/__tests__/agents-overlay.test.js +59 -0
  176. package/dist/hooks/__tests__/agents-overlay.test.js.map +1 -1
  177. package/dist/hooks/__tests__/anti-slop-workflow.test.js +109 -18
  178. package/dist/hooks/__tests__/anti-slop-workflow.test.js.map +1 -1
  179. package/dist/hooks/__tests__/keyword-detector.test.js +45 -32
  180. package/dist/hooks/__tests__/keyword-detector.test.js.map +1 -1
  181. package/dist/hooks/__tests__/notify-fallback-watcher.test.js +3 -3
  182. package/dist/hooks/__tests__/notify-fallback-watcher.test.js.map +1 -1
  183. package/dist/hooks/__tests__/notify-hook-team-dispatch.test.js +2 -1
  184. package/dist/hooks/__tests__/notify-hook-team-dispatch.test.js.map +1 -1
  185. package/dist/hooks/__tests__/notify-hook-team-leader-nudge.test.js +17 -24
  186. package/dist/hooks/__tests__/notify-hook-team-leader-nudge.test.js.map +1 -1
  187. package/dist/hooks/__tests__/prompt-guidance-wave-two.test.js +3 -3
  188. package/dist/hooks/__tests__/prompt-guidance-wave-two.test.js.map +1 -1
  189. package/dist/hooks/__tests__/task-size-detector.test.js +1 -1
  190. package/dist/hooks/__tests__/task-size-detector.test.js.map +1 -1
  191. package/dist/hooks/__tests__/visual-ralph-skill.test.js +3 -3
  192. package/dist/hooks/__tests__/visual-ralph-skill.test.js.map +1 -1
  193. package/dist/hooks/__tests__/visual-verdict-loop.test.js +7 -11
  194. package/dist/hooks/__tests__/visual-verdict-loop.test.js.map +1 -1
  195. package/dist/hooks/agents-overlay.d.ts.map +1 -1
  196. package/dist/hooks/agents-overlay.js +23 -2
  197. package/dist/hooks/agents-overlay.js.map +1 -1
  198. package/dist/hooks/keyword-detector.d.ts.map +1 -1
  199. package/dist/hooks/keyword-detector.js +12 -13
  200. package/dist/hooks/keyword-detector.js.map +1 -1
  201. package/dist/hooks/keyword-registry.d.ts.map +1 -1
  202. package/dist/hooks/keyword-registry.js +2 -10
  203. package/dist/hooks/keyword-registry.js.map +1 -1
  204. package/dist/hooks/prompt-guidance-contract.d.ts.map +1 -1
  205. package/dist/hooks/prompt-guidance-contract.js +0 -4
  206. package/dist/hooks/prompt-guidance-contract.js.map +1 -1
  207. package/dist/hooks/session.js +2 -2
  208. package/dist/hooks/session.js.map +1 -1
  209. package/dist/hooks/task-size-detector.d.ts.map +1 -1
  210. package/dist/hooks/task-size-detector.js +1 -0
  211. package/dist/hooks/task-size-detector.js.map +1 -1
  212. package/dist/hud/__tests__/index.test.js +30 -14
  213. package/dist/hud/__tests__/index.test.js.map +1 -1
  214. package/dist/hud/__tests__/reconcile.test.js +29 -7
  215. package/dist/hud/__tests__/reconcile.test.js.map +1 -1
  216. package/dist/hud/reconcile.d.ts +2 -1
  217. package/dist/hud/reconcile.d.ts.map +1 -1
  218. package/dist/hud/reconcile.js +12 -0
  219. package/dist/hud/reconcile.js.map +1 -1
  220. package/dist/mcp/__tests__/bootstrap.test.js +15 -2
  221. package/dist/mcp/__tests__/bootstrap.test.js.map +1 -1
  222. package/dist/mcp/__tests__/state-paths.test.js +54 -0
  223. package/dist/mcp/__tests__/state-paths.test.js.map +1 -1
  224. package/dist/mcp/__tests__/state-server.test.js +36 -0
  225. package/dist/mcp/__tests__/state-server.test.js.map +1 -1
  226. package/dist/mcp/bootstrap.d.ts +1 -1
  227. package/dist/mcp/bootstrap.d.ts.map +1 -1
  228. package/dist/mcp/bootstrap.js +9 -7
  229. package/dist/mcp/bootstrap.js.map +1 -1
  230. package/dist/mcp/state-paths.d.ts +17 -0
  231. package/dist/mcp/state-paths.d.ts.map +1 -1
  232. package/dist/mcp/state-paths.js +36 -2
  233. package/dist/mcp/state-paths.js.map +1 -1
  234. package/dist/modes/__tests__/base-session-scope.test.js +26 -0
  235. package/dist/modes/__tests__/base-session-scope.test.js.map +1 -1
  236. package/dist/modes/base.d.ts +1 -0
  237. package/dist/modes/base.d.ts.map +1 -1
  238. package/dist/modes/base.js +35 -5
  239. package/dist/modes/base.js.map +1 -1
  240. package/dist/notifications/__tests__/http-client.test.d.ts +2 -0
  241. package/dist/notifications/__tests__/http-client.test.d.ts.map +1 -0
  242. package/dist/notifications/__tests__/http-client.test.js +90 -0
  243. package/dist/notifications/__tests__/http-client.test.js.map +1 -0
  244. package/dist/notifications/__tests__/notifier.test.js +22 -60
  245. package/dist/notifications/__tests__/notifier.test.js.map +1 -1
  246. package/dist/notifications/dispatcher.d.ts.map +1 -1
  247. package/dist/notifications/dispatcher.js +35 -60
  248. package/dist/notifications/dispatcher.js.map +1 -1
  249. package/dist/notifications/http-client.d.ts +22 -0
  250. package/dist/notifications/http-client.d.ts.map +1 -0
  251. package/dist/notifications/http-client.js +298 -0
  252. package/dist/notifications/http-client.js.map +1 -0
  253. package/dist/notifications/notifier.d.ts +3 -2
  254. package/dist/notifications/notifier.d.ts.map +1 -1
  255. package/dist/notifications/notifier.js +17 -22
  256. package/dist/notifications/notifier.js.map +1 -1
  257. package/dist/openclaw/__tests__/dispatcher.test.js +63 -2
  258. package/dist/openclaw/__tests__/dispatcher.test.js.map +1 -1
  259. package/dist/openclaw/dispatcher.d.ts.map +1 -1
  260. package/dist/openclaw/dispatcher.js +3 -2
  261. package/dist/openclaw/dispatcher.js.map +1 -1
  262. package/dist/performance-goal/artifacts.d.ts +76 -0
  263. package/dist/performance-goal/artifacts.d.ts.map +1 -0
  264. package/dist/performance-goal/artifacts.js +221 -0
  265. package/dist/performance-goal/artifacts.js.map +1 -0
  266. package/dist/pipeline/__tests__/stages.test.js +423 -14
  267. package/dist/pipeline/__tests__/stages.test.js.map +1 -1
  268. package/dist/pipeline/stages/team-exec.d.ts +8 -4
  269. package/dist/pipeline/stages/team-exec.d.ts.map +1 -1
  270. package/dist/pipeline/stages/team-exec.js +181 -13
  271. package/dist/pipeline/stages/team-exec.js.map +1 -1
  272. package/dist/planning/__tests__/artifacts.test.js +261 -1
  273. package/dist/planning/__tests__/artifacts.test.js.map +1 -1
  274. package/dist/planning/artifact-names.d.ts +13 -0
  275. package/dist/planning/artifact-names.d.ts.map +1 -0
  276. package/dist/planning/artifact-names.js +108 -0
  277. package/dist/planning/artifact-names.js.map +1 -0
  278. package/dist/planning/artifacts.d.ts +23 -1
  279. package/dist/planning/artifacts.d.ts.map +1 -1
  280. package/dist/planning/artifacts.js +171 -59
  281. package/dist/planning/artifacts.js.map +1 -1
  282. package/dist/ralph/__tests__/persistence.test.js +21 -1
  283. package/dist/ralph/__tests__/persistence.test.js.map +1 -1
  284. package/dist/ralph/persistence.d.ts.map +1 -1
  285. package/dist/ralph/persistence.js +6 -4
  286. package/dist/ralph/persistence.js.map +1 -1
  287. package/dist/ralplan/__tests__/runtime.test.js +2 -0
  288. package/dist/ralplan/__tests__/runtime.test.js.map +1 -1
  289. package/dist/ralplan/runtime.d.ts.map +1 -1
  290. package/dist/ralplan/runtime.js +6 -0
  291. package/dist/ralplan/runtime.js.map +1 -1
  292. package/dist/scripts/__tests__/codex-native-hook.test.js +1749 -88
  293. package/dist/scripts/__tests__/codex-native-hook.test.js.map +1 -1
  294. package/dist/scripts/__tests__/hook-derived-watcher.test.js +33 -1
  295. package/dist/scripts/__tests__/hook-derived-watcher.test.js.map +1 -1
  296. package/dist/scripts/__tests__/run-test-files.test.js +36 -0
  297. package/dist/scripts/__tests__/run-test-files.test.js.map +1 -1
  298. package/dist/scripts/codex-native-hook.d.ts.map +1 -1
  299. package/dist/scripts/codex-native-hook.js +570 -45
  300. package/dist/scripts/codex-native-hook.js.map +1 -1
  301. package/dist/scripts/codex-native-pre-post.d.ts +7 -0
  302. package/dist/scripts/codex-native-pre-post.d.ts.map +1 -1
  303. package/dist/scripts/codex-native-pre-post.js +341 -15
  304. package/dist/scripts/codex-native-pre-post.js.map +1 -1
  305. package/dist/scripts/hook-derived-watcher.js +2 -1
  306. package/dist/scripts/hook-derived-watcher.js.map +1 -1
  307. package/dist/scripts/notify-fallback-watcher.js +2 -1
  308. package/dist/scripts/notify-fallback-watcher.js.map +1 -1
  309. package/dist/scripts/notify-hook/orchestration-intent.d.ts +1 -2
  310. package/dist/scripts/notify-hook/orchestration-intent.d.ts.map +1 -1
  311. package/dist/scripts/notify-hook/orchestration-intent.js +2 -3
  312. package/dist/scripts/notify-hook/orchestration-intent.js.map +1 -1
  313. package/dist/scripts/notify-hook/team-leader-nudge.d.ts +0 -2
  314. package/dist/scripts/notify-hook/team-leader-nudge.d.ts.map +1 -1
  315. package/dist/scripts/notify-hook/team-leader-nudge.js +8 -60
  316. package/dist/scripts/notify-hook/team-leader-nudge.js.map +1 -1
  317. package/dist/scripts/notify-hook/team-worker-posttooluse.js +1 -1
  318. package/dist/scripts/notify-hook/team-worker-posttooluse.js.map +1 -1
  319. package/dist/scripts/notify-hook/team-worker-stop.d.ts +15 -0
  320. package/dist/scripts/notify-hook/team-worker-stop.d.ts.map +1 -0
  321. package/dist/scripts/notify-hook/team-worker-stop.js +224 -0
  322. package/dist/scripts/notify-hook/team-worker-stop.js.map +1 -0
  323. package/dist/scripts/notify-hook/team-worker.d.ts.map +1 -1
  324. package/dist/scripts/notify-hook/team-worker.js +26 -18
  325. package/dist/scripts/notify-hook/team-worker.js.map +1 -1
  326. package/dist/scripts/notify-hook.js +1 -1
  327. package/dist/scripts/notify-hook.js.map +1 -1
  328. package/dist/scripts/run-test-files.js +17 -1
  329. package/dist/scripts/run-test-files.js.map +1 -1
  330. package/dist/scripts/sync-plugin-mirror.d.ts +1 -0
  331. package/dist/scripts/sync-plugin-mirror.d.ts.map +1 -1
  332. package/dist/scripts/sync-plugin-mirror.js +10 -4
  333. package/dist/scripts/sync-plugin-mirror.js.map +1 -1
  334. package/dist/state/__tests__/operations.test.js +26 -0
  335. package/dist/state/__tests__/operations.test.js.map +1 -1
  336. package/dist/state/__tests__/skill-active.test.js +76 -0
  337. package/dist/state/__tests__/skill-active.test.js.map +1 -1
  338. package/dist/state/operations.d.ts +3 -1
  339. package/dist/state/operations.d.ts.map +1 -1
  340. package/dist/state/operations.js +8 -4
  341. package/dist/state/operations.js.map +1 -1
  342. package/dist/state/skill-active.d.ts +1 -0
  343. package/dist/state/skill-active.d.ts.map +1 -1
  344. package/dist/state/skill-active.js +54 -13
  345. package/dist/state/skill-active.js.map +1 -1
  346. package/dist/team/__tests__/api-interop.test.js +279 -0
  347. package/dist/team/__tests__/api-interop.test.js.map +1 -1
  348. package/dist/team/__tests__/approved-execution.test.d.ts +2 -0
  349. package/dist/team/__tests__/approved-execution.test.d.ts.map +1 -0
  350. package/dist/team/__tests__/approved-execution.test.js +124 -0
  351. package/dist/team/__tests__/approved-execution.test.js.map +1 -0
  352. package/dist/team/__tests__/delivery-e2e-smoke.test.js +2 -4
  353. package/dist/team/__tests__/delivery-e2e-smoke.test.js.map +1 -1
  354. package/dist/team/__tests__/delivery-log.test.d.ts +2 -0
  355. package/dist/team/__tests__/delivery-log.test.d.ts.map +1 -0
  356. package/dist/team/__tests__/delivery-log.test.js +44 -0
  357. package/dist/team/__tests__/delivery-log.test.js.map +1 -0
  358. package/dist/team/__tests__/model-contract.test.js +40 -9
  359. package/dist/team/__tests__/model-contract.test.js.map +1 -1
  360. package/dist/team/__tests__/repo-aware-decomposition.test.js +41 -0
  361. package/dist/team/__tests__/repo-aware-decomposition.test.js.map +1 -1
  362. package/dist/team/__tests__/role-router.test.js +4 -4
  363. package/dist/team/__tests__/role-router.test.js.map +1 -1
  364. package/dist/team/__tests__/runtime-boxed-state.test.d.ts +2 -0
  365. package/dist/team/__tests__/runtime-boxed-state.test.d.ts.map +1 -0
  366. package/dist/team/__tests__/runtime-boxed-state.test.js +39 -0
  367. package/dist/team/__tests__/runtime-boxed-state.test.js.map +1 -0
  368. package/dist/team/__tests__/runtime-cli.test.js +24 -0
  369. package/dist/team/__tests__/runtime-cli.test.js.map +1 -1
  370. package/dist/team/__tests__/runtime.test.js +563 -72
  371. package/dist/team/__tests__/runtime.test.js.map +1 -1
  372. package/dist/team/__tests__/state-root.test.js +13 -0
  373. package/dist/team/__tests__/state-root.test.js.map +1 -1
  374. package/dist/team/__tests__/state.test.js +13 -0
  375. package/dist/team/__tests__/state.test.js.map +1 -1
  376. package/dist/team/__tests__/team-identity.test.d.ts +2 -0
  377. package/dist/team/__tests__/team-identity.test.d.ts.map +1 -0
  378. package/dist/team/__tests__/team-identity.test.js +166 -0
  379. package/dist/team/__tests__/team-identity.test.js.map +1 -0
  380. package/dist/team/__tests__/tmux-session.test.js +58 -1
  381. package/dist/team/__tests__/tmux-session.test.js.map +1 -1
  382. package/dist/team/__tests__/worker-bootstrap.test.js +62 -0
  383. package/dist/team/__tests__/worker-bootstrap.test.js.map +1 -1
  384. package/dist/team/api-interop.d.ts +1 -0
  385. package/dist/team/api-interop.d.ts.map +1 -1
  386. package/dist/team/api-interop.js +163 -132
  387. package/dist/team/api-interop.js.map +1 -1
  388. package/dist/team/approved-execution.d.ts +37 -0
  389. package/dist/team/approved-execution.d.ts.map +1 -0
  390. package/dist/team/approved-execution.js +136 -0
  391. package/dist/team/approved-execution.js.map +1 -0
  392. package/dist/team/delivery-log.d.ts +1 -1
  393. package/dist/team/delivery-log.d.ts.map +1 -1
  394. package/dist/team/delivery-log.js +2 -1
  395. package/dist/team/delivery-log.js.map +1 -1
  396. package/dist/team/followup-planner.js +2 -2
  397. package/dist/team/followup-planner.js.map +1 -1
  398. package/dist/team/goal-workflow.d.ts +20 -0
  399. package/dist/team/goal-workflow.d.ts.map +1 -0
  400. package/dist/team/goal-workflow.js +57 -0
  401. package/dist/team/goal-workflow.js.map +1 -0
  402. package/dist/team/orchestrator.js +2 -2
  403. package/dist/team/orchestrator.js.map +1 -1
  404. package/dist/team/repo-aware-decomposition.d.ts +3 -0
  405. package/dist/team/repo-aware-decomposition.d.ts.map +1 -1
  406. package/dist/team/repo-aware-decomposition.js +2 -0
  407. package/dist/team/repo-aware-decomposition.js.map +1 -1
  408. package/dist/team/role-router.js +5 -5
  409. package/dist/team/role-router.js.map +1 -1
  410. package/dist/team/runtime-cli.d.ts +32 -2
  411. package/dist/team/runtime-cli.d.ts.map +1 -1
  412. package/dist/team/runtime-cli.js +78 -26
  413. package/dist/team/runtime-cli.js.map +1 -1
  414. package/dist/team/runtime.d.ts +7 -1
  415. package/dist/team/runtime.d.ts.map +1 -1
  416. package/dist/team/runtime.js +383 -40
  417. package/dist/team/runtime.js.map +1 -1
  418. package/dist/team/scaling.d.ts.map +1 -1
  419. package/dist/team/scaling.js +2 -0
  420. package/dist/team/scaling.js.map +1 -1
  421. package/dist/team/state.d.ts +9 -0
  422. package/dist/team/state.d.ts.map +1 -1
  423. package/dist/team/state.js +21 -0
  424. package/dist/team/state.js.map +1 -1
  425. package/dist/team/team-identity.d.ts +26 -0
  426. package/dist/team/team-identity.d.ts.map +1 -0
  427. package/dist/team/team-identity.js +169 -0
  428. package/dist/team/team-identity.js.map +1 -0
  429. package/dist/team/tmux-session.d.ts +18 -0
  430. package/dist/team/tmux-session.d.ts.map +1 -1
  431. package/dist/team/tmux-session.js +65 -3
  432. package/dist/team/tmux-session.js.map +1 -1
  433. package/dist/team/worker-bootstrap.d.ts +4 -0
  434. package/dist/team/worker-bootstrap.d.ts.map +1 -1
  435. package/dist/team/worker-bootstrap.js +28 -2
  436. package/dist/team/worker-bootstrap.js.map +1 -1
  437. package/dist/ultragoal/__tests__/artifacts.test.d.ts +2 -0
  438. package/dist/ultragoal/__tests__/artifacts.test.d.ts.map +1 -0
  439. package/dist/ultragoal/__tests__/artifacts.test.js +93 -0
  440. package/dist/ultragoal/__tests__/artifacts.test.js.map +1 -0
  441. package/dist/ultragoal/artifacts.d.ts +89 -0
  442. package/dist/ultragoal/artifacts.d.ts.map +1 -0
  443. package/dist/ultragoal/artifacts.js +233 -0
  444. package/dist/ultragoal/artifacts.js.map +1 -0
  445. package/dist/utils/__tests__/agents-model-table.test.js +3 -1
  446. package/dist/utils/__tests__/agents-model-table.test.js.map +1 -1
  447. package/dist/utils/__tests__/paths.test.js +31 -1
  448. package/dist/utils/__tests__/paths.test.js.map +1 -1
  449. package/dist/utils/agents-model-table.d.ts.map +1 -1
  450. package/dist/utils/agents-model-table.js +12 -1
  451. package/dist/utils/agents-model-table.js.map +1 -1
  452. package/dist/utils/paths.d.ts +2 -0
  453. package/dist/utils/paths.d.ts.map +1 -1
  454. package/dist/utils/paths.js +23 -7
  455. package/dist/utils/paths.js.map +1 -1
  456. package/dist/verification/__tests__/ci-rust-gates.test.js +30 -19
  457. package/dist/verification/__tests__/ci-rust-gates.test.js.map +1 -1
  458. package/package.json +5 -5
  459. package/plugins/oh-my-codex/.codex-plugin/plugin.json +1 -1
  460. package/plugins/oh-my-codex/skills/ai-slop-cleaner/SKILL.md +30 -5
  461. package/plugins/oh-my-codex/skills/ask/SKILL.md +58 -0
  462. package/plugins/oh-my-codex/skills/autoresearch-goal/SKILL.md +36 -0
  463. package/plugins/oh-my-codex/skills/omx-setup/SKILL.md +2 -2
  464. package/plugins/oh-my-codex/skills/performance-goal/SKILL.md +65 -0
  465. package/plugins/oh-my-codex/skills/plan/SKILL.md +1 -1
  466. package/plugins/oh-my-codex/skills/ralph/SKILL.md +22 -3
  467. package/plugins/oh-my-codex/skills/team/SKILL.md +6 -2
  468. package/plugins/oh-my-codex/skills/ultragoal/SKILL.md +49 -0
  469. package/plugins/oh-my-codex/skills/visual-ralph/SKILL.md +9 -9
  470. package/prompts/api-reviewer.md +1 -1
  471. package/prompts/code-reviewer.md +2 -0
  472. package/prompts/performance-reviewer.md +1 -1
  473. package/prompts/quality-reviewer.md +1 -1
  474. package/prompts/quality-strategist.md +2 -2
  475. package/prompts/style-reviewer.md +1 -1
  476. package/prompts/test-engineer.md +1 -1
  477. package/skills/ai-slop-cleaner/SKILL.md +30 -5
  478. package/skills/ask/SKILL.md +58 -0
  479. package/skills/ask-claude/SKILL.md +3 -54
  480. package/skills/ask-gemini/SKILL.md +3 -54
  481. package/skills/autoresearch-goal/SKILL.md +36 -0
  482. package/skills/build-fix/SKILL.md +4 -139
  483. package/skills/deepsearch/SKILL.md +4 -32
  484. package/skills/ecomode/SKILL.md +4 -108
  485. package/skills/help/SKILL.md +4 -196
  486. package/skills/note/SKILL.md +4 -56
  487. package/skills/omx-setup/SKILL.md +2 -2
  488. package/skills/performance-goal/SKILL.md +65 -0
  489. package/skills/plan/SKILL.md +1 -1
  490. package/skills/ralph/SKILL.md +22 -3
  491. package/skills/ralph-init/SKILL.md +4 -40
  492. package/skills/review/SKILL.md +4 -32
  493. package/skills/security-review/SKILL.md +4 -294
  494. package/skills/swarm/SKILL.md +4 -19
  495. package/skills/tdd/SKILL.md +4 -100
  496. package/skills/team/SKILL.md +6 -2
  497. package/skills/trace/SKILL.md +4 -27
  498. package/skills/ultragoal/SKILL.md +49 -0
  499. package/skills/visual-ralph/SKILL.md +9 -9
  500. package/skills/visual-verdict/SKILL.md +4 -70
  501. package/skills/web-clone/SKILL.md +4 -18
  502. package/src/scripts/__tests__/codex-native-hook.test.ts +2923 -1030
  503. package/src/scripts/__tests__/hook-derived-watcher.test.ts +45 -1
  504. package/src/scripts/__tests__/run-test-files.test.ts +46 -0
  505. package/src/scripts/codex-native-hook.ts +696 -46
  506. package/src/scripts/codex-native-pre-post.ts +369 -16
  507. package/src/scripts/hook-derived-watcher.ts +2 -1
  508. package/src/scripts/notify-fallback-watcher.ts +2 -1
  509. package/src/scripts/notify-hook/orchestration-intent.ts +1 -3
  510. package/src/scripts/notify-hook/team-leader-nudge.ts +7 -63
  511. package/src/scripts/notify-hook/team-worker-posttooluse.ts +1 -1
  512. package/src/scripts/notify-hook/team-worker-stop.ts +246 -0
  513. package/src/scripts/notify-hook/team-worker.ts +23 -14
  514. package/src/scripts/notify-hook.ts +1 -1
  515. package/src/scripts/run-test-files.ts +20 -1
  516. package/src/scripts/sync-plugin-mirror.ts +13 -4
  517. package/templates/catalog-manifest.json +45 -27
  518. package/plugins/oh-my-codex/skills/ask-claude/SKILL.md +0 -61
  519. package/plugins/oh-my-codex/skills/ask-gemini/SKILL.md +0 -61
  520. package/plugins/oh-my-codex/skills/help/SKILL.md +0 -202
  521. package/plugins/oh-my-codex/skills/note/SKILL.md +0 -62
  522. package/plugins/oh-my-codex/skills/security-review/SKILL.md +0 -300
  523. package/plugins/oh-my-codex/skills/trace/SKILL.md +0 -33
  524. package/plugins/oh-my-codex/skills/visual-verdict/SKILL.md +0 -76
package/dist/cli/index.js CHANGED
@@ -5,7 +5,8 @@
5
5
  import { execFileSync, spawn } from "child_process";
6
6
  import { basename, dirname, join } from "path";
7
7
  import { existsSync, mkdirSync, readFileSync, rmSync, statSync, writeFileSync } from "fs";
8
- import { constants as osConstants } from "os";
8
+ import { copyFile, cp, lstat, mkdir, readdir, rm, symlink } from "fs/promises";
9
+ import { constants as osConstants, homedir } from "os";
9
10
  import { setup, SETUP_SCOPES } from "./setup.js";
10
11
  import { uninstall } from "./uninstall.js";
11
12
  import { version } from "./version.js";
@@ -15,6 +16,8 @@ import { hudCommand } from "../hud/index.js";
15
16
  import { sidecarCommand } from "../sidecar/index.js";
16
17
  import { teamCommand } from "./team.js";
17
18
  import { ralphCommand } from "./ralph.js";
19
+ import { ultragoalCommand } from "./ultragoal.js";
20
+ import { performanceGoalCommand } from "./performance-goal.js";
18
21
  import { askCommand } from "./ask.js";
19
22
  import { questionCommand } from "./question.js";
20
23
  import { stateCommand } from "./state.js";
@@ -25,6 +28,7 @@ import { agentsInitCommand } from "./agents-init.js";
25
28
  import { agentsCommand } from "./agents.js";
26
29
  import { sessionCommand } from "./session-search.js";
27
30
  import { autoresearchCommand } from "./autoresearch.js";
31
+ import { autoresearchGoalCommand } from "./autoresearch-goal.js";
28
32
  import { mcpParityCommand } from "./mcp-parity.js";
29
33
  import { mcpServeCommand } from "./mcp-serve.js";
30
34
  import { adaptCommand } from "./adapt.js";
@@ -41,9 +45,10 @@ import { generateOverlay, removeSessionModelInstructionsFile, resolveSessionOrch
41
45
  import { readSessionState, writeSessionStart, writeSessionEnd, resetSessionMetrics, } from "../hooks/session.js";
42
46
  import { buildClientAttachedReconcileHookName, buildReconcileHudResizeArgs, buildRegisterClientAttachedReconcileArgs, buildRegisterResizeHookArgs, buildResizeHookName, buildResizeHookTarget, buildScheduleDelayedHudResizeArgs, buildUnregisterClientAttachedReconcileArgs, buildUnregisterResizeHookArgs, enableMouseScrolling, isMsysOrGitBash, isNativeWindows, isTmuxAvailable, mitigateCopyModeUnderlineArtifacts, } from "../team/tmux-session.js";
43
47
  import { getPackageRoot } from "../utils/package.js";
44
- import { codexConfigPath, rememberOmxLaunchContext, resolveOmxEntryPath } from "../utils/paths.js";
48
+ import { codexConfigPath, omxRoot, rememberOmxLaunchContext, resolveOmxEntryPath } from "../utils/paths.js";
45
49
  import { cleanCodexModelAvailabilityNuxIfNeeded, repairConfigIfNeeded } from "../config/generator.js";
46
50
  import { HUD_TMUX_HEIGHT_LINES } from "../hud/constants.js";
51
+ import { OMX_TMUX_HUD_OWNER_ENV } from "../hud/reconcile.js";
47
52
  import { createHudWatchPane as createSharedHudWatchPane, killTmuxPane as killSharedTmuxPane, listCurrentWindowHudPaneIds, parsePaneIdFromTmuxOutput, } from "../hud/tmux.js";
48
53
  export { parseTmuxPaneSnapshot, isHudWatchPane, findHudWatchPaneIds } from "../hud/tmux.js";
49
54
  rememberOmxLaunchContext();
@@ -96,6 +101,11 @@ Usage:
96
101
  Alias for agents-init (lightweight AGENTS bootstrap only)
97
102
  omx team Spawn parallel worker panes in tmux and bootstrap inbox/task state
98
103
  omx ralph Launch Codex with ralph persistence mode active
104
+ omx ultragoal Create, resume, and checkpoint durable multi-goal plans over Codex goal mode
105
+ omx performance-goal
106
+ Create, hand off, and gate evaluator-backed performance goals
107
+ omx autoresearch-goal
108
+ Create, hand off, and gate professor-critic research goals
99
109
  omx autoresearch [DEPRECATED] Use $autoresearch; direct CLI launch removed
100
110
  omx version Show version information
101
111
  omx tmux-hook Manage tmux prompt injection workaround (init|status|validate|test)
@@ -213,6 +223,7 @@ const NESTED_HELP_COMMANDS = new Set([
213
223
  "cleanup",
214
224
  "adapt",
215
225
  "autoresearch",
226
+ "autoresearch-goal",
216
227
  "agents",
217
228
  "agents-init",
218
229
  "deepinit",
@@ -225,6 +236,8 @@ const NESTED_HELP_COMMANDS = new Set([
225
236
  "wiki",
226
237
  "mcp-serve",
227
238
  "ralph",
239
+ "ultragoal",
240
+ "performance-goal",
228
241
  "resume",
229
242
  "session",
230
243
  "sparkshell",
@@ -393,6 +406,65 @@ export function resolveCodexLaunchPolicy(env = process.env, _platform = process.
393
406
  function resolveTmuxExecutableForLaunch() {
394
407
  return resolveTmuxBinaryForPlatform() || "tmux";
395
408
  }
409
+ export function runtimeCodexHomePath(cwd, sessionId) {
410
+ return join(omxRoot(cwd), "runtime", "codex-home", sessionId);
411
+ }
412
+ async function linkOrCopyCodexHomeEntry(source, destination) {
413
+ const stat = await lstat(source);
414
+ try {
415
+ await symlink(source, destination, stat.isDirectory() && process.platform === "win32" ? "junction" : undefined);
416
+ }
417
+ catch {
418
+ if (stat.isDirectory()) {
419
+ await cp(source, destination, { recursive: true, force: true, verbatimSymlinks: true });
420
+ return;
421
+ }
422
+ await copyFile(source, destination);
423
+ }
424
+ }
425
+ /**
426
+ * Project-scope setup keeps durable Codex config under <repo>/.codex, but the
427
+ * Codex TUI also stores model-availability NUX counters in CODEX_HOME/config.toml.
428
+ * Launch against a session mirror so those runtime writes never dirty the
429
+ * durable project config while preserving the project config as the launch input.
430
+ */
431
+ export async function prepareRuntimeCodexHomeForProjectLaunch(cwd, sessionId, projectCodexHome) {
432
+ const runtimeCodexHome = runtimeCodexHomePath(cwd, sessionId);
433
+ await rm(runtimeCodexHome, { recursive: true, force: true });
434
+ await mkdir(runtimeCodexHome, { recursive: true });
435
+ if (!existsSync(projectCodexHome))
436
+ return runtimeCodexHome;
437
+ for (const entry of await readdir(projectCodexHome, { withFileTypes: true })) {
438
+ const source = join(projectCodexHome, entry.name);
439
+ const destination = join(runtimeCodexHome, entry.name);
440
+ if (entry.name === "config.toml") {
441
+ await copyFile(source, destination);
442
+ continue;
443
+ }
444
+ await linkOrCopyCodexHomeEntry(source, destination);
445
+ }
446
+ return runtimeCodexHome;
447
+ }
448
+ export async function prepareCodexHomeForLaunch(cwd, sessionId, env = process.env) {
449
+ const projectLocalCodexHomeForCleanup = resolveProjectLocalCodexHomeForLaunch(cwd, env);
450
+ if (projectLocalCodexHomeForCleanup) {
451
+ const runtimeCodexHome = await prepareRuntimeCodexHomeForProjectLaunch(cwd, sessionId, projectLocalCodexHomeForCleanup);
452
+ return {
453
+ codexHomeOverride: runtimeCodexHome,
454
+ projectLocalCodexHomeForCleanup,
455
+ runtimeCodexHomeForCleanup: runtimeCodexHome,
456
+ };
457
+ }
458
+ return {
459
+ codexHomeOverride: resolveCodexHomeForLaunch(cwd, env),
460
+ projectLocalCodexHomeForCleanup,
461
+ };
462
+ }
463
+ async function cleanupRuntimeCodexHome(runtimeCodexHomeForCleanup) {
464
+ if (!runtimeCodexHomeForCleanup)
465
+ return;
466
+ await rm(runtimeCodexHomeForCleanup, { recursive: true, force: true });
467
+ }
396
468
  function execTmuxFileSync(args, options) {
397
469
  return execFileSync(resolveTmuxExecutableForLaunch(), args, {
398
470
  ...(options ?? {}),
@@ -423,6 +495,11 @@ function tmuxFailureMessage(error) {
423
495
  const detail = (stderr || stdout || err.message || String(error)).trim();
424
496
  return detail.replace(/\s+/g, " ");
425
497
  }
498
+ function isUnsupportedTmuxExtendedKeysFailure(error) {
499
+ const message = tmuxFailureMessage(error).toLowerCase();
500
+ return (message.includes("extended-keys") &&
501
+ /(?:invalid|unknown|unsupported) (?:option|flag|argument)|no such option|unknown option/.test(message));
502
+ }
426
503
  function isBenignMissingTmuxServerMessage(message) {
427
504
  return (/no server running/i.test(message) ||
428
505
  /error connecting to .*\(No such file or directory\)/i.test(message));
@@ -447,6 +524,42 @@ function warnDetachedTmuxFallback(reason) {
447
524
  const suffix = reason ? ` (${reason})` : "";
448
525
  console.warn(`[omx] warning: tmux is installed but its server/socket is unusable${suffix}. Falling back to direct Codex launch.`);
449
526
  }
527
+ const QUICK_ATTACH_NOOP_THRESHOLD_MS = 2_000;
528
+ function isWslWindowsTerminalEnvironment(env) {
529
+ return Boolean(env.WT_SESSION?.trim() &&
530
+ (env.WSL_INTEROP?.trim() ||
531
+ env.WSL_DISTRO_NAME?.trim() ||
532
+ env.WSLENV?.trim()));
533
+ }
534
+ function readDetachedSessionAttachedClientCount(sessionName) {
535
+ try {
536
+ const output = execTmuxFileSync(["display-message", "-p", "-t", sessionName, "#{session_attached}"], {
537
+ stdio: ["ignore", "pipe", "pipe"],
538
+ encoding: "utf-8",
539
+ }).trim();
540
+ const parsed = Number.parseInt(output, 10);
541
+ return Number.isFinite(parsed) ? parsed : null;
542
+ }
543
+ catch (err) {
544
+ logCliOperationFailure(err);
545
+ return null;
546
+ }
547
+ }
548
+ function assertDetachedAttachDidNotNoop(sessionName, elapsedMs, env) {
549
+ if (!isWslWindowsTerminalEnvironment(env))
550
+ return;
551
+ if (elapsedMs >= QUICK_ATTACH_NOOP_THRESHOLD_MS)
552
+ return;
553
+ const attachedClients = readDetachedSessionAttachedClientCount(sessionName);
554
+ if (attachedClients === null || attachedClients > 0)
555
+ return;
556
+ throw new Error([
557
+ "tmux attach-session returned immediately without attaching a client",
558
+ `(session=${sessionName}).`,
559
+ "This can happen on WSL2 under Windows Terminal.",
560
+ "Falling back to direct Codex launch.",
561
+ ].join(" "));
562
+ }
450
563
  function resolveTmuxAwareLaunchPolicy(explicitLaunchPolicy, nativeWindows) {
451
564
  const launchPolicy = resolveCodexLaunchPolicy(process.env, process.platform, undefined, nativeWindows, undefined, undefined, explicitLaunchPolicy);
452
565
  if (launchPolicy !== "detached-tmux") {
@@ -541,6 +654,51 @@ export function buildHudPaneCleanupTargets(existingPaneIds, createdPaneId, leade
541
654
  }
542
655
  return [...targets];
543
656
  }
657
+ export function resolveOmxRootForLaunch(cwd, env = process.env) {
658
+ const raw = env.OMX_ROOT || env.OMX_STATE_ROOT;
659
+ if (typeof raw !== "string" || raw.trim() === "")
660
+ return undefined;
661
+ return raw.startsWith("/") ? raw : join(cwd, raw);
662
+ }
663
+ export function shouldAutoIsolateMadmaxLaunch(command, launchArgs, env = process.env) {
664
+ if (command !== "launch" && command !== "exec")
665
+ return false;
666
+ if (env.OMX_NO_BOX === "1" || env.OMXBOX_ACTIVE === "1")
667
+ return false;
668
+ if (env.OMX_ROOT || env.OMX_STATE_ROOT)
669
+ return false;
670
+ return launchArgs.some((arg) => arg === MADMAX_FLAG || arg === MADMAX_SPARK_FLAG);
671
+ }
672
+ function sanitizeRunIdSegment(value) {
673
+ return value.replace(/[^a-zA-Z0-9._-]/g, "-").replace(/-+/g, "-").replace(/^-|-$/g, "");
674
+ }
675
+ export function createMadmaxIsolatedRoot(sourceCwd, argv, env = process.env) {
676
+ const runsRoot = env.OMX_RUNS_DIR || join(homedir(), ".omx-runs");
677
+ mkdirSync(runsRoot, { recursive: true });
678
+ const stamp = new Date().toISOString().replace(/[-:TZ.]/g, "").slice(0, 14);
679
+ const suffix = Math.random().toString(16).slice(2, 6);
680
+ const runDir = join(runsRoot, sanitizeRunIdSegment(`run-${stamp}-${suffix}`));
681
+ mkdirSync(runDir, { recursive: false });
682
+ const metadata = {
683
+ launcher: "omx --madmax",
684
+ created_at: new Date().toISOString(),
685
+ cwd: runDir,
686
+ source_cwd: sourceCwd,
687
+ argv,
688
+ };
689
+ writeFileSync(join(runDir, ".omxbox-run.json"), `${JSON.stringify(metadata, null, 2)}\n`);
690
+ writeFileSync(join(runsRoot, "registry.jsonl"), `${JSON.stringify(metadata)}\n`, { flag: "a" });
691
+ return runDir;
692
+ }
693
+ function activateMadmaxIsolationIfNeeded(command, launchArgs, cwd, env = process.env) {
694
+ if (!shouldAutoIsolateMadmaxLaunch(command, launchArgs, env))
695
+ return;
696
+ const runDir = createMadmaxIsolatedRoot(cwd, launchArgs, env);
697
+ env.OMX_ROOT = runDir;
698
+ env.OMXBOX_ACTIVE = "1";
699
+ env.OMX_SOURCE_CWD = cwd;
700
+ process.stderr.write(`[omx] madmax isolated state: ${runDir} (source: ${cwd})\n`);
701
+ }
544
702
  export async function main(args) {
545
703
  const knownCommands = new Set([
546
704
  "launch",
@@ -557,10 +715,13 @@ export async function main(args) {
557
715
  "ask",
558
716
  "question",
559
717
  "autoresearch",
718
+ "autoresearch-goal",
560
719
  "explore",
561
720
  "sparkshell",
562
721
  "team",
563
722
  "ralph",
723
+ "ultragoal",
724
+ "performance-goal",
564
725
  "session",
565
726
  "resume",
566
727
  "version",
@@ -590,6 +751,7 @@ export async function main(args) {
590
751
  console.log(HELP);
591
752
  return;
592
753
  }
754
+ activateMadmaxIsolationIfNeeded(command, launchArgs, process.cwd(), process.env);
593
755
  try {
594
756
  switch (command) {
595
757
  case "launch":
@@ -652,6 +814,9 @@ export async function main(args) {
652
814
  case "autoresearch":
653
815
  await autoresearchCommand(args.slice(1));
654
816
  break;
817
+ case "autoresearch-goal":
818
+ await autoresearchGoalCommand(args.slice(1));
819
+ break;
655
820
  case "explore":
656
821
  await exploreCommand(args.slice(1));
657
822
  break;
@@ -675,6 +840,12 @@ export async function main(args) {
675
840
  case "ralph":
676
841
  await ralphCommand(args.slice(1));
677
842
  break;
843
+ case "ultragoal":
844
+ await ultragoalCommand(args.slice(1));
845
+ break;
846
+ case "performance-goal":
847
+ await performanceGoalCommand(args.slice(1));
848
+ break;
678
849
  case "version":
679
850
  version();
680
851
  break;
@@ -832,11 +1003,10 @@ export async function launchWithHud(args) {
832
1003
  const parsedWorktree = parseWorktreeMode(args);
833
1004
  const notifyTempResult = resolveNotifyTempContract(parsedWorktree.remainingArgs, process.env);
834
1005
  const explicitLaunchPolicy = resolveEffectiveLeaderLaunchPolicyOverride(notifyTempResult.passthroughArgs, process.env);
835
- const codexHomeOverride = resolveCodexHomeForLaunch(launchCwd, process.env);
836
- const projectLocalCodexHomeForCleanup = resolveProjectLocalCodexHomeForLaunch(launchCwd, process.env);
1006
+ const persistentCodexHomeForLaunch = resolveCodexHomeForLaunch(launchCwd, process.env);
837
1007
  const { launchPolicy, effectiveExplicitLaunchPolicy } = resolveTmuxAwareLaunchPolicy(explicitLaunchPolicy, isNativeWindows());
838
1008
  const enableNotifyFallbackAuthority = launchPolicy === "direct";
839
- const workerSparkModel = resolveWorkerSparkModel(notifyTempResult.passthroughArgs, codexHomeOverride);
1009
+ const workerSparkModel = resolveWorkerSparkModel(notifyTempResult.passthroughArgs, persistentCodexHomeForLaunch);
840
1010
  const normalizedArgs = normalizeCodexLaunchArgs(notifyTempResult.passthroughArgs);
841
1011
  let cwd = launchCwd;
842
1012
  let worktreeDirty = false;
@@ -891,6 +1061,9 @@ export async function launchWithHud(args) {
891
1061
  catch {
892
1062
  // Non-fatal: repair failure must not block launch
893
1063
  }
1064
+ const preparedCodexHome = await prepareCodexHomeForLaunch(launchCwd, sessionId, process.env);
1065
+ const codexHomeOverride = preparedCodexHome.codexHomeOverride;
1066
+ const projectLocalCodexHomeForCleanup = preparedCodexHome.projectLocalCodexHomeForCleanup;
894
1067
  // ── Phase 1: preLaunch ──────────────────────────────────────────────────
895
1068
  try {
896
1069
  await preLaunch(cwd, sessionId, notifyTempResult.contract, codexHomeOverride, enableNotifyFallbackAuthority, worktreeDirty);
@@ -900,23 +1073,26 @@ export async function launchWithHud(args) {
900
1073
  console.error(`[omx] preLaunch warning: ${err instanceof Error ? err.message : err}`);
901
1074
  }
902
1075
  // ── Phase 2: run ────────────────────────────────────────────────────────
1076
+ let postLaunchHandledExternally = false;
903
1077
  try {
904
1078
  const notifyTempContractRaw = notifyTempResult.contract.active
905
1079
  ? serializeNotifyTempContract(notifyTempResult.contract)
906
1080
  : null;
907
- runCodex(cwd, normalizedArgs, sessionId, workerSparkModel, codexHomeOverride, notifyTempContractRaw, effectiveExplicitLaunchPolicy);
1081
+ const launchResult = runCodex(cwd, normalizedArgs, sessionId, workerSparkModel, codexHomeOverride, notifyTempContractRaw, effectiveExplicitLaunchPolicy, projectLocalCodexHomeForCleanup, preparedCodexHome.runtimeCodexHomeForCleanup);
1082
+ postLaunchHandledExternally = launchResult.postLaunchHandledExternally;
908
1083
  }
909
1084
  finally {
910
1085
  // ── Phase 3: postLaunch ─────────────────────────────────────────────
911
- await postLaunch(cwd, sessionId, codexHomeOverride, enableNotifyFallbackAuthority, projectLocalCodexHomeForCleanup);
1086
+ if (!postLaunchHandledExternally) {
1087
+ await postLaunch(cwd, sessionId, codexHomeOverride, enableNotifyFallbackAuthority, projectLocalCodexHomeForCleanup);
1088
+ await cleanupRuntimeCodexHome(preparedCodexHome.runtimeCodexHomeForCleanup).catch(logCliOperationFailure);
1089
+ }
912
1090
  }
913
1091
  }
914
1092
  export async function execWithOverlay(args) {
915
1093
  const launchCwd = process.cwd();
916
1094
  const parsedWorktree = parseWorktreeMode(args);
917
1095
  const notifyTempResult = resolveNotifyTempContract(parsedWorktree.remainingArgs, process.env);
918
- const codexHomeOverride = resolveCodexHomeForLaunch(launchCwd, process.env);
919
- const projectLocalCodexHomeForCleanup = resolveProjectLocalCodexHomeForLaunch(launchCwd, process.env);
920
1096
  const normalizedArgs = normalizeCodexLaunchArgs(notifyTempResult.passthroughArgs);
921
1097
  let cwd = launchCwd;
922
1098
  let worktreeDirty = false;
@@ -965,6 +1141,9 @@ export async function execWithOverlay(args) {
965
1141
  catch {
966
1142
  // Non-fatal
967
1143
  }
1144
+ const preparedCodexHome = await prepareCodexHomeForLaunch(launchCwd, sessionId, process.env);
1145
+ const codexHomeOverride = preparedCodexHome.codexHomeOverride;
1146
+ const projectLocalCodexHomeForCleanup = preparedCodexHome.projectLocalCodexHomeForCleanup;
968
1147
  try {
969
1148
  await preLaunch(cwd, sessionId, notifyTempResult.contract, codexHomeOverride, true, worktreeDirty);
970
1149
  }
@@ -976,9 +1155,12 @@ export async function execWithOverlay(args) {
976
1155
  ? serializeNotifyTempContract(notifyTempResult.contract)
977
1156
  : null;
978
1157
  const codexArgs = injectModelInstructionsBypassArgs(cwd, ["exec", ...normalizedArgs], process.env, sessionModelInstructionsPath(cwd, sessionId));
979
- const codexEnvBase = codexHomeOverride
980
- ? { ...process.env, CODEX_HOME: codexHomeOverride }
981
- : process.env;
1158
+ const omxRootOverride = resolveOmxRootForLaunch(cwd, process.env);
1159
+ const codexEnvBase = {
1160
+ ...process.env,
1161
+ ...(codexHomeOverride ? { CODEX_HOME: codexHomeOverride } : {}),
1162
+ ...(omxRootOverride ? { OMX_ROOT: omxRootOverride } : {}),
1163
+ };
982
1164
  const codexEnv = notifyTempContractRaw
983
1165
  ? {
984
1166
  ...codexEnvBase,
@@ -989,6 +1171,7 @@ export async function execWithOverlay(args) {
989
1171
  }
990
1172
  finally {
991
1173
  await postLaunch(cwd, sessionId, codexHomeOverride, true, projectLocalCodexHomeForCleanup);
1174
+ await cleanupRuntimeCodexHome(preparedCodexHome.runtimeCodexHomeForCleanup).catch(logCliOperationFailure);
992
1175
  }
993
1176
  }
994
1177
  export function normalizeCodexLaunchArgs(args) {
@@ -1338,7 +1521,7 @@ function blockMs(ms) {
1338
1521
  Atomics.wait(view, 0, 0, delay);
1339
1522
  }
1340
1523
  function tmuxExtendedKeysLeaseRoot(cwd) {
1341
- return join(cwd, ".omx", "state", TMUX_EXTENDED_KEYS_LEASE_DIR);
1524
+ return join(omxRoot(cwd), "state", TMUX_EXTENDED_KEYS_LEASE_DIR);
1342
1525
  }
1343
1526
  function resolveTmuxSocketPath(execFileSyncImpl = (file, tmuxArgs) => execFileSync(file, tmuxArgs, {
1344
1527
  encoding: "utf-8",
@@ -1509,7 +1692,10 @@ function withTmuxExtendedKeysLeaseLock(cwd, socketPath, run) {
1509
1692
  }
1510
1693
  throw new Error(`timed out waiting for tmux extended-keys lease lock: ${lockPath}`);
1511
1694
  }
1512
- function buildDetachedSessionLeaderCommand(cwd, sessionName, codexCmd) {
1695
+ function buildDetachedSessionLeaderCommand(cwd, sessionName, codexCmd, sessionId, codexHomeOverride, projectLocalCodexHomeForCleanup, runtimeCodexHomeForCleanup) {
1696
+ const detachedPostLaunchHelper = sessionId
1697
+ ? `${buildDetachedSessionPostLaunchHelperCommand(cwd, sessionId, codexHomeOverride, projectLocalCodexHomeForCleanup, runtimeCodexHomeForCleanup)} >/dev/null 2>&1 || true;`
1698
+ : "";
1513
1699
  const wrapped = [
1514
1700
  buildTmuxExtendedKeysAcquireShellSnippet(cwd),
1515
1701
  'exec 3<&0;',
@@ -1523,6 +1709,7 @@ function buildDetachedSessionLeaderCommand(cwd, sessionName, codexCmd) {
1523
1709
  "fi;",
1524
1710
  'exec 3<&- 2>/dev/null || true;',
1525
1711
  buildTmuxExtendedKeysReleaseShellSnippet(cwd),
1712
+ detachedPostLaunchHelper,
1526
1713
  'if [ "$status" -lt 128 ]; then',
1527
1714
  `tmux kill-session -t "${escapeShellDoubleQuotedValue(sessionName)}" >/dev/null 2>&1 || true;`,
1528
1715
  "fi;",
@@ -1535,6 +1722,27 @@ function buildDetachedSessionLeaderCommand(cwd, sessionName, codexCmd) {
1535
1722
  ].join(" ");
1536
1723
  return `/bin/sh -c ${quoteShellArg(wrapped)}`;
1537
1724
  }
1725
+ function buildDetachedSessionPostLaunchHelperCommand(cwd, sessionId, codexHomeOverride, projectLocalCodexHomeForCleanup, runtimeCodexHomeForCleanup) {
1726
+ const cwdLiteral = JSON.stringify(cwd);
1727
+ const sessionIdLiteral = JSON.stringify(sessionId);
1728
+ const codexHomeLiteral = typeof codexHomeOverride === "string" && codexHomeOverride.length > 0
1729
+ ? JSON.stringify(codexHomeOverride)
1730
+ : "undefined";
1731
+ const projectLocalCleanupLiteral = typeof projectLocalCodexHomeForCleanup === "string" &&
1732
+ projectLocalCodexHomeForCleanup.length > 0
1733
+ ? JSON.stringify(projectLocalCodexHomeForCleanup)
1734
+ : "undefined";
1735
+ const runtimeCodexHomeCleanupLiteral = typeof runtimeCodexHomeForCleanup === "string" &&
1736
+ runtimeCodexHomeForCleanup.length > 0
1737
+ ? JSON.stringify(runtimeCodexHomeForCleanup)
1738
+ : "undefined";
1739
+ const moduleUrlLiteral = JSON.stringify(import.meta.url);
1740
+ const script = [
1741
+ `const mod = await import(${moduleUrlLiteral});`,
1742
+ `await mod.runDetachedSessionPostLaunch(${cwdLiteral}, ${sessionIdLiteral}, ${codexHomeLiteral}, ${projectLocalCleanupLiteral}, ${runtimeCodexHomeCleanupLiteral});`,
1743
+ ].join(" ");
1744
+ return `${quoteShellArg(process.execPath)} --input-type=module -e ${quoteShellArg(script)}`;
1745
+ }
1538
1746
  function execTmuxSync(args, execFileSyncImpl = (file, tmuxArgs) => execFileSync(file, tmuxArgs, {
1539
1747
  encoding: "utf-8",
1540
1748
  ...(process.platform === "win32" ? { windowsHide: true } : {}),
@@ -1573,7 +1781,9 @@ export function acquireTmuxExtendedKeysLease(cwd, execFileSyncImpl = (file, tmux
1573
1781
  return `${socketPath}\t${leaseId}`;
1574
1782
  }
1575
1783
  catch (err) {
1576
- logCliOperationFailure(err);
1784
+ if (!isUnsupportedTmuxExtendedKeysFailure(err)) {
1785
+ logCliOperationFailure(err);
1786
+ }
1577
1787
  return null;
1578
1788
  }
1579
1789
  }
@@ -1612,7 +1822,9 @@ export function releaseTmuxExtendedKeysLease(cwd, leaseHandle, execFileSyncImpl
1612
1822
  });
1613
1823
  }
1614
1824
  catch (err) {
1615
- logCliOperationFailure(err);
1825
+ if (!isUnsupportedTmuxExtendedKeysFailure(err)) {
1826
+ logCliOperationFailure(err);
1827
+ }
1616
1828
  }
1617
1829
  }
1618
1830
  function buildTmuxExtendedKeysHelperCommand(cwd, operation) {
@@ -1642,10 +1854,10 @@ export function withTmuxExtendedKeys(cwd, run, execFileSyncImpl = (file, tmuxArg
1642
1854
  releaseTmuxExtendedKeysLease(cwd, leaseHandle, execFileSyncImpl);
1643
1855
  }
1644
1856
  }
1645
- export function buildDetachedSessionBootstrapSteps(sessionName, cwd, codexCmd, hudCmd, workerLaunchArgs, codexHomeOverride, notifyTempContractRaw, nativeWindows = false, sessionId) {
1857
+ export function buildDetachedSessionBootstrapSteps(sessionName, cwd, codexCmd, hudCmd, workerLaunchArgs, codexHomeOverride, notifyTempContractRaw, nativeWindows = false, sessionId, projectLocalCodexHomeForCleanup, runtimeCodexHomeForCleanup, omxRootOverride, env = process.env) {
1646
1858
  const detachedLeaderCmd = nativeWindows
1647
1859
  ? "powershell.exe"
1648
- : buildDetachedSessionLeaderCommand(cwd, sessionName, codexCmd);
1860
+ : buildDetachedSessionLeaderCommand(cwd, sessionName, codexCmd, sessionId, codexHomeOverride, projectLocalCodexHomeForCleanup, runtimeCodexHomeForCleanup);
1649
1861
  const newSessionArgs = [
1650
1862
  "new-session",
1651
1863
  "-d",
@@ -1660,7 +1872,12 @@ export function buildDetachedSessionBootstrapSteps(sessionName, cwd, codexCmd, h
1660
1872
  ? ["-e", `${TEAM_WORKER_LAUNCH_ARGS_ENV}=${workerLaunchArgs}`]
1661
1873
  : []),
1662
1874
  ...(sessionId ? ["-e", `OMX_SESSION_ID=${sessionId}`] : []),
1875
+ ...(sessionId ? ["-e", `${OMX_TMUX_HUD_OWNER_ENV}=1`] : []),
1663
1876
  ...(codexHomeOverride ? ["-e", `CODEX_HOME=${codexHomeOverride}`] : []),
1877
+ ...(omxRootOverride ? ["-e", `OMX_ROOT=${omxRootOverride}`] : []),
1878
+ ...(env.OMX_STATE_ROOT ? ["-e", `OMX_STATE_ROOT=${env.OMX_STATE_ROOT}`] : []),
1879
+ ...(env.OMXBOX_ACTIVE ? ["-e", `OMXBOX_ACTIVE=${env.OMXBOX_ACTIVE}`] : []),
1880
+ ...(env.OMX_SOURCE_CWD ? ["-e", `OMX_SOURCE_CWD=${env.OMX_SOURCE_CWD}`] : []),
1664
1881
  ...(notifyTempContractRaw
1665
1882
  ? ["-e", `${OMX_NOTIFY_TEMP_CONTRACT_ENV}=${notifyTempContractRaw}`]
1666
1883
  : []),
@@ -1787,6 +2004,7 @@ export function buildNotifyFallbackWatcherEnv(env = process.env, options = {}) {
1787
2004
  return {
1788
2005
  ...nextEnv,
1789
2006
  ...(options.codexHomeOverride ? { CODEX_HOME: options.codexHomeOverride } : {}),
2007
+ ...(options.omxRootOverride ? { OMX_ROOT: options.omxRootOverride } : {}),
1790
2008
  ...(options.sessionId ? { OMX_SESSION_ID: options.sessionId } : {}),
1791
2009
  OMX_HUD_AUTHORITY: options.enableAuthority ? "1" : "0",
1792
2010
  };
@@ -2094,7 +2312,7 @@ ${launchAppendix}${dirtyWorktreeGuidance}`
2094
2312
  * runCodex: Launch Codex CLI (blocks until exit).
2095
2313
  * All 3 paths (new tmux, existing tmux, no tmux) block via execSync/execFileSync.
2096
2314
  */
2097
- function runCodex(cwd, args, sessionId, workerDefaultModel, codexHomeOverride, notifyTempContractRaw, explicitLaunchPolicy) {
2315
+ function runCodex(cwd, args, sessionId, workerDefaultModel, codexHomeOverride, notifyTempContractRaw, explicitLaunchPolicy, projectLocalCodexHomeForCleanup, runtimeCodexHomeForCleanup) {
2098
2316
  const launchArgs = injectModelInstructionsBypassArgs(cwd, args, process.env, sessionModelInstructionsPath(cwd, sessionId));
2099
2317
  const nativeWindows = isNativeWindows();
2100
2318
  const omxBin = resolveOmxEntryPath();
@@ -2103,13 +2321,20 @@ function runCodex(cwd, args, sessionId, workerDefaultModel, codexHomeOverride, n
2103
2321
  }
2104
2322
  const hudCmd = nativeWindows
2105
2323
  ? buildWindowsPromptCommand("node", [omxBin, "hud", "--watch"])
2106
- : buildTmuxPaneCommand("env", [`OMX_SESSION_ID=${sessionId}`, "node", omxBin, "hud", "--watch"]);
2324
+ : buildTmuxPaneCommand("env", [`OMX_SESSION_ID=${sessionId}`, `${OMX_TMUX_HUD_OWNER_ENV}=1`, "node", omxBin, "hud", "--watch"]);
2107
2325
  const inheritLeaderFlags = process.env[TEAM_INHERIT_LEADER_FLAGS_ENV] !== "0";
2108
2326
  const workerLaunchArgs = resolveTeamWorkerLaunchArgsEnv(process.env[TEAM_WORKER_LAUNCH_ARGS_ENV], launchArgs, inheritLeaderFlags, workerDefaultModel);
2109
- const codexBaseEnv = codexHomeOverride
2110
- ? { ...process.env, CODEX_HOME: codexHomeOverride }
2111
- : process.env;
2112
- const codexEnvWithSession = { ...codexBaseEnv, OMX_SESSION_ID: sessionId };
2327
+ const omxRootOverride = resolveOmxRootForLaunch(cwd, process.env);
2328
+ const codexBaseEnv = {
2329
+ ...process.env,
2330
+ ...(codexHomeOverride ? { CODEX_HOME: codexHomeOverride } : {}),
2331
+ ...(omxRootOverride ? { OMX_ROOT: omxRootOverride } : {}),
2332
+ };
2333
+ const codexEnvWithSession = {
2334
+ ...codexBaseEnv,
2335
+ OMX_SESSION_ID: sessionId,
2336
+ [OMX_TMUX_HUD_OWNER_ENV]: "1",
2337
+ };
2113
2338
  const codexEnv = workerLaunchArgs
2114
2339
  ? { ...codexEnvWithSession, [TEAM_WORKER_LAUNCH_ARGS_ENV]: workerLaunchArgs }
2115
2340
  : codexEnvWithSession;
@@ -2119,7 +2344,7 @@ function runCodex(cwd, args, sessionId, workerDefaultModel, codexHomeOverride, n
2119
2344
  const { launchPolicy } = resolveTmuxAwareLaunchPolicy(explicitLaunchPolicy, nativeWindows);
2120
2345
  if (isCodexVersionRequest(launchArgs)) {
2121
2346
  runCodexBlocking(cwd, launchArgs, codexEnvWithNotify);
2122
- return;
2347
+ return { postLaunchHandledExternally: false };
2123
2348
  }
2124
2349
  if (launchPolicy === "inside-tmux") {
2125
2350
  // Already in tmux: launch codex in current pane, HUD in bottom split
@@ -2176,11 +2401,13 @@ function runCodex(cwd, args, sessionId, workerDefaultModel, codexHomeOverride, n
2176
2401
  killTmuxPane(paneId);
2177
2402
  }
2178
2403
  }
2404
+ return { postLaunchHandledExternally: false };
2179
2405
  }
2180
2406
  else if (launchPolicy === "direct") {
2181
2407
  // Detached HUD sessions require tmux. Skip the bootstrap entirely when the
2182
2408
  // binary is unavailable so direct launches do not emit noisy ENOENT logs.
2183
2409
  runCodexBlocking(cwd, launchArgs, codexEnvWithNotify);
2410
+ return { postLaunchHandledExternally: false };
2184
2411
  }
2185
2412
  else {
2186
2413
  // Not in tmux: create a new tmux session with codex + HUD pane
@@ -2198,7 +2425,7 @@ function runCodex(cwd, args, sessionId, workerDefaultModel, codexHomeOverride, n
2198
2425
  let registeredHookName = null;
2199
2426
  let registeredClientAttachedHookName = null;
2200
2427
  try {
2201
- const bootstrapSteps = buildDetachedSessionBootstrapSteps(sessionName, cwd, codexCmd, hudCmd, workerLaunchArgs, codexHomeOverride, notifyTempContractRaw, nativeWindows, sessionId);
2428
+ const bootstrapSteps = buildDetachedSessionBootstrapSteps(sessionName, cwd, codexCmd, hudCmd, workerLaunchArgs, codexHomeOverride, notifyTempContractRaw, nativeWindows, sessionId, projectLocalCodexHomeForCleanup, runtimeCodexHomeForCleanup, omxRootOverride, process.env);
2202
2429
  for (const step of bootstrapSteps) {
2203
2430
  const output = execTmuxFileSync(step.args, {
2204
2431
  stdio: "pipe",
@@ -2238,7 +2465,11 @@ function runCodex(cwd, args, sessionId, workerDefaultModel, codexHomeOverride, n
2238
2465
  }
2239
2466
  const stdio = finalizeStep.name === "attach-session" ? "inherit" : "ignore";
2240
2467
  try {
2468
+ const startedAtMs = Date.now();
2241
2469
  execTmuxFileSync(finalizeStep.args, { stdio });
2470
+ if (finalizeStep.name === "attach-session") {
2471
+ assertDetachedAttachDidNotNoop(sessionName, Date.now() - startedAtMs, process.env);
2472
+ }
2242
2473
  }
2243
2474
  catch (err) {
2244
2475
  logCliOperationFailure(err);
@@ -2259,6 +2490,7 @@ function runCodex(cwd, args, sessionId, workerDefaultModel, codexHomeOverride, n
2259
2490
  }
2260
2491
  }
2261
2492
  }
2493
+ return { postLaunchHandledExternally: !nativeWindows };
2262
2494
  }
2263
2495
  catch (err) {
2264
2496
  logCliOperationFailure(err);
@@ -2276,6 +2508,7 @@ function runCodex(cwd, args, sessionId, workerDefaultModel, codexHomeOverride, n
2276
2508
  }
2277
2509
  // tmux not available or failed, just run codex directly
2278
2510
  runCodexBlocking(cwd, launchArgs, codexEnvWithNotify);
2511
+ return { postLaunchHandledExternally: false };
2279
2512
  }
2280
2513
  }
2281
2514
  }
@@ -2517,6 +2750,10 @@ async function postLaunch(cwd, sessionId, codexHomeOverride, enableNotifyFallbac
2517
2750
  // Non-fatal
2518
2751
  }
2519
2752
  }
2753
+ export async function runDetachedSessionPostLaunch(cwd, sessionId, codexHomeOverride, projectLocalCodexHomeForCleanup, runtimeCodexHomeForCleanup) {
2754
+ await postLaunch(cwd, sessionId, codexHomeOverride, false, projectLocalCodexHomeForCleanup);
2755
+ await cleanupRuntimeCodexHome(runtimeCodexHomeForCleanup).catch(logCliOperationFailure);
2756
+ }
2520
2757
  async function emitNativeHookEvent(cwd, event, opts = {}) {
2521
2758
  const payload = buildHookEvent(event, {
2522
2759
  source: "native",
@@ -2532,10 +2769,10 @@ async function emitNativeHookEvent(cwd, event, opts = {}) {
2532
2769
  });
2533
2770
  }
2534
2771
  function notifyFallbackPidPath(cwd) {
2535
- return join(cwd, ".omx", "state", "notify-fallback.pid");
2772
+ return join(omxRoot(cwd), "state", "notify-fallback.pid");
2536
2773
  }
2537
2774
  function hookDerivedWatcherPidPath(cwd) {
2538
- return join(cwd, ".omx", "state", "hook-derived-watcher.pid");
2775
+ return join(omxRoot(cwd), "state", "hook-derived-watcher.pid");
2539
2776
  }
2540
2777
  export function shouldDetachBackgroundHelper(env = process.env, platform = process.platform) {
2541
2778
  // The long-running watcher/helper itself must stay detached so it can
@@ -2703,7 +2940,7 @@ async function startNotifyFallbackWatcher(cwd, options = {}) {
2703
2940
  const notifyScript = resolveNotifyHookScript(pkgRoot);
2704
2941
  if (!existsSync(watcherScript) || !existsSync(notifyScript))
2705
2942
  return;
2706
- await mkdir(join(cwd, ".omx", "state"), { recursive: true }).catch((error) => {
2943
+ await mkdir(join(omxRoot(cwd), "state"), { recursive: true }).catch((error) => {
2707
2944
  console.warn("[omx] warning: failed to create notify fallback watcher state directory", {
2708
2945
  cwd,
2709
2946
  error: error instanceof Error ? error.message : String(error),
@@ -2711,6 +2948,7 @@ async function startNotifyFallbackWatcher(cwd, options = {}) {
2711
2948
  });
2712
2949
  const watcherEnv = buildNotifyFallbackWatcherEnv(process.env, {
2713
2950
  codexHomeOverride: options.codexHomeOverride,
2951
+ omxRootOverride: resolveOmxRootForLaunch(cwd, process.env),
2714
2952
  enableAuthority: options.enableAuthority === true,
2715
2953
  sessionId: options.sessionId,
2716
2954
  });
@@ -2776,7 +3014,7 @@ async function startHookDerivedWatcher(cwd) {
2776
3014
  });
2777
3015
  }
2778
3016
  }
2779
- await mkdir(join(cwd, ".omx", "state"), { recursive: true }).catch((error) => {
3017
+ await mkdir(join(omxRoot(cwd), "state"), { recursive: true }).catch((error) => {
2780
3018
  console.warn("[omx] warning: failed to create hook-derived watcher state directory", {
2781
3019
  cwd,
2782
3020
  error: error instanceof Error ? error.message : String(error),