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
@@ -2,6 +2,7 @@ import {
2
2
  buildDocumentRefreshAdvisoryOutput,
3
3
  evaluateStagedDocumentRefresh,
4
4
  } from "../document-refresh/enforcer.js";
5
+ import { isLoreCommitGuardEnabled } from "../config/commit-lore-guard.js";
5
6
  import { resolveCodexExecutionSurface } from "./codex-execution-surface.js";
6
7
 
7
8
  type CodexHookPayload = Record<string, unknown>;
@@ -284,8 +285,91 @@ function tokenizeShellCommand(commandText: string): string[] | null {
284
285
  return tokens.length > 0 ? tokens : null;
285
286
  }
286
287
 
288
+ interface ShellToken {
289
+ value: string;
290
+ startsCommand: boolean;
291
+ }
292
+
293
+ function tokenizeShellCommandWithBoundaries(commandText: string): ShellToken[] | null {
294
+ const trimmed = commandText.trim();
295
+ if (!trimmed) return null;
296
+
297
+ const tokens: ShellToken[] = [];
298
+ let current = "";
299
+ let quote: "'" | "\"" | null = null;
300
+ let escaping = false;
301
+ let nextTokenStartsCommand = false;
302
+
303
+ const pushCurrent = () => {
304
+ if (!current) return;
305
+ tokens.push({ value: current, startsCommand: tokens.length === 0 || nextTokenStartsCommand });
306
+ current = "";
307
+ nextTokenStartsCommand = false;
308
+ };
309
+
310
+ for (let index = 0; index < trimmed.length; index += 1) {
311
+ const char = trimmed[index] ?? "";
312
+
313
+ if (escaping) {
314
+ current += char;
315
+ escaping = false;
316
+ continue;
317
+ }
318
+
319
+ if (quote === "'") {
320
+ if (char === "'") {
321
+ quote = null;
322
+ } else {
323
+ current += char;
324
+ }
325
+ continue;
326
+ }
327
+
328
+ if (quote === "\"") {
329
+ if (char === "\"") quote = null;
330
+ else if (char === "\\") {
331
+ if (isDoubleQuotedShellEscapeTarget(trimmed[index + 1])) escaping = true;
332
+ else current += char;
333
+ }
334
+ else current += char;
335
+ continue;
336
+ }
337
+
338
+ if (char === "\n" || char === ";" || char === "&" || char === "|") {
339
+ pushCurrent();
340
+ nextTokenStartsCommand = true;
341
+ if ((char === "&" || char === "|") && trimmed[index + 1] === char) index += 1;
342
+ continue;
343
+ }
344
+
345
+ if (/\s/.test(char)) {
346
+ pushCurrent();
347
+ continue;
348
+ }
349
+
350
+ if (char === "'" || char === "\"") {
351
+ quote = char;
352
+ continue;
353
+ }
354
+
355
+ if (char === "\\") {
356
+ escaping = true;
357
+ continue;
358
+ }
359
+
360
+ current += char;
361
+ }
362
+
363
+ if (escaping || quote) return null;
364
+ pushCurrent();
365
+ return tokens.length > 0 ? tokens : null;
366
+ }
367
+
287
368
  interface GitCommitCommandParseResult {
288
369
  isGitCommit: boolean;
370
+ inlineEnvironment: NodeJS.ProcessEnv;
371
+ environmentStartsClean: boolean;
372
+ unsetEnvironmentNames: string[];
289
373
  inlineMessage: string | null;
290
374
  repositorySelection: GitRepositorySelection;
291
375
  requiresExternalMessageSource: boolean;
@@ -322,38 +406,159 @@ function envOptionConsumesNextValue(token: string): boolean {
322
406
  || token === "--split-string";
323
407
  }
324
408
 
325
- function findGitCommandTokenIndex(tokens: string[]): number {
326
- let index = 0;
409
+ function tokenStartsCommand(tokens: ShellToken[], index: number): boolean {
410
+ return index <= 0 || (tokens[index]?.startsCommand ?? false);
411
+ }
412
+
413
+ function nextCommandStart(tokens: ShellToken[], startIndex: number): number {
414
+ let index = startIndex + 1;
415
+ while (index < tokens.length && !tokenStartsCommand(tokens, index)) {
416
+ index += 1;
417
+ }
418
+ return index;
419
+ }
420
+
421
+ function findGitCommandTokenIndex(tokens: ShellToken[]): number {
422
+ for (let commandStart = 0; commandStart < tokens.length; commandStart = nextCommandStart(tokens, commandStart)) {
423
+ let index = commandStart;
424
+ const commandEnd = nextCommandStart(tokens, commandStart);
425
+
426
+ while (index < commandEnd && isInlineShellEnvAssignment(tokens[index]?.value ?? "")) {
427
+ index += 1;
428
+ }
429
+
430
+ while (index < commandEnd && isEnvExecutableToken(tokens[index]?.value ?? "")) {
431
+ index += 1;
432
+ while (index < commandEnd) {
433
+ const token = tokens[index]?.value ?? "";
434
+ if (token === "--") {
435
+ index += 1;
436
+ break;
437
+ }
438
+ if (isInlineShellEnvAssignment(token)) {
439
+ index += 1;
440
+ continue;
441
+ }
442
+ if (token === "-i" || token === "--ignore-environment" || token.startsWith("--unset=")) {
443
+ index += 1;
444
+ continue;
445
+ }
446
+ if (token.startsWith("-")) {
447
+ index += envOptionConsumesNextValue(token) ? 2 : 1;
448
+ continue;
449
+ }
450
+ break;
451
+ }
452
+ while (index < commandEnd && isInlineShellEnvAssignment(tokens[index]?.value ?? "")) {
453
+ index += 1;
454
+ }
455
+ }
456
+
457
+ if (index < commandEnd && isGitExecutableToken(tokens[index]?.value ?? "")) return index;
458
+ if (commandEnd <= commandStart) break;
459
+ commandStart = commandEnd - 1;
460
+ }
461
+
462
+ return -1;
463
+ }
464
+
465
+ function tokenValues(tokens: ShellToken[]): string[] {
466
+ return tokens.map((token) => token.value);
467
+ }
468
+
469
+ function findCommandStart(tokens: ShellToken[], tokenIndex: number): number {
470
+ let index = tokenIndex;
471
+ while (index > 0 && !tokenStartsCommand(tokens, index)) {
472
+ index -= 1;
473
+ }
474
+ return index;
475
+ }
476
+
477
+
478
+ interface InlineEnvironmentRead {
479
+ inlineEnvironment: NodeJS.ProcessEnv;
480
+ environmentStartsClean: boolean;
481
+ unsetEnvironmentNames: string[];
482
+ }
483
+
484
+ function readUnsetEnvNameFromOption(token: string, nextToken: string | undefined): {
485
+ name: string | null;
486
+ consumedNext: boolean;
487
+ } {
488
+ if (token === "-u" || token === "--unset") {
489
+ return { name: nextToken ?? null, consumedNext: true };
490
+ }
491
+ if (token.startsWith("--unset=")) {
492
+ return { name: token.slice("--unset=".length), consumedNext: false };
493
+ }
494
+ return { name: null, consumedNext: false };
495
+ }
327
496
 
328
- while (index < tokens.length && isInlineShellEnvAssignment(tokens[index] ?? "")) {
497
+ function readInlineEnvironmentAssignments(tokens: ShellToken[], gitTokenIndex: number): InlineEnvironmentRead {
498
+ const inlineEnvironment: NodeJS.ProcessEnv = {};
499
+ const unsetEnvironmentNames = new Set<string>();
500
+ let environmentStartsClean = false;
501
+ const commandStart = findCommandStart(tokens, gitTokenIndex);
502
+ const recordAssignment = (token: string) => {
503
+ const separatorIndex = token.indexOf("=");
504
+ const name = token.slice(0, separatorIndex);
505
+ inlineEnvironment[name] = token.slice(separatorIndex + 1);
506
+ unsetEnvironmentNames.delete(name);
507
+ };
508
+ const recordUnset = (name: string | null) => {
509
+ if (!name) return;
510
+ delete inlineEnvironment[name];
511
+ unsetEnvironmentNames.add(name);
512
+ };
513
+
514
+ let index = commandStart;
515
+ while (index < gitTokenIndex && isInlineShellEnvAssignment(tokens[index]?.value ?? "")) {
516
+ recordAssignment(tokens[index]?.value ?? "");
329
517
  index += 1;
330
518
  }
331
519
 
332
- while (index < tokens.length && isEnvExecutableToken(tokens[index] ?? "")) {
520
+ while (index < gitTokenIndex && isEnvExecutableToken(tokens[index]?.value ?? "")) {
333
521
  index += 1;
334
- while (index < tokens.length) {
335
- const token = tokens[index] ?? "";
522
+ while (index < gitTokenIndex) {
523
+ const token = tokens[index]?.value ?? "";
336
524
  if (token === "--") {
337
525
  index += 1;
338
526
  break;
339
527
  }
340
- if (isInlineShellEnvAssignment(token) || token.startsWith("-")) {
341
- if (envOptionConsumesNextValue(token)) {
342
- index += 1;
343
- }
528
+ if (isInlineShellEnvAssignment(token)) {
529
+ recordAssignment(token);
530
+ index += 1;
531
+ continue;
532
+ }
533
+ if (token === "-i" || token === "--ignore-environment") {
534
+ environmentStartsClean = true;
535
+ unsetEnvironmentNames.clear();
344
536
  index += 1;
345
537
  continue;
346
538
  }
539
+ const unset = readUnsetEnvNameFromOption(token, tokens[index + 1]?.value);
540
+ if (unset.name !== null || unset.consumedNext) {
541
+ recordUnset(unset.name);
542
+ index += unset.consumedNext ? 2 : 1;
543
+ continue;
544
+ }
545
+ if (token.startsWith("-")) {
546
+ index += envOptionConsumesNextValue(token) ? 2 : 1;
547
+ continue;
548
+ }
347
549
  break;
348
550
  }
349
- while (index < tokens.length && isInlineShellEnvAssignment(tokens[index] ?? "")) {
551
+ while (index < gitTokenIndex && isInlineShellEnvAssignment(tokens[index]?.value ?? "")) {
552
+ recordAssignment(tokens[index]?.value ?? "");
350
553
  index += 1;
351
554
  }
352
555
  }
353
556
 
354
- return index < tokens.length && isGitExecutableToken(tokens[index] ?? "")
355
- ? index
356
- : -1;
557
+ return {
558
+ inlineEnvironment,
559
+ environmentStartsClean,
560
+ unsetEnvironmentNames: [...unsetEnvironmentNames],
561
+ };
357
562
  }
358
563
 
359
564
  function gitOptionConsumesNextValue(token: string): boolean {
@@ -420,20 +625,27 @@ function readGitRepositorySelection(tokens: string[], gitTokenIndex: number, sub
420
625
  }
421
626
 
422
627
  export function parseGitCommitCommand(commandText: string): GitCommitCommandParseResult {
423
- const tokens = tokenizeShellCommand(commandText);
628
+ const shellTokens = tokenizeShellCommandWithBoundaries(commandText);
629
+ const tokens = shellTokens ? tokenValues(shellTokens) : null;
424
630
  if (!tokens) {
425
631
  return {
426
632
  isGitCommit: false,
633
+ inlineEnvironment: {},
634
+ environmentStartsClean: false,
635
+ unsetEnvironmentNames: [],
427
636
  inlineMessage: null,
428
637
  repositorySelection: "current-cwd",
429
638
  requiresExternalMessageSource: false,
430
639
  };
431
640
  }
432
641
 
433
- const gitTokenIndex = findGitCommandTokenIndex(tokens);
642
+ const gitTokenIndex = findGitCommandTokenIndex(shellTokens ?? []);
434
643
  if (gitTokenIndex < 0 || !isGitExecutableToken(tokens[gitTokenIndex] ?? "")) {
435
644
  return {
436
645
  isGitCommit: false,
646
+ inlineEnvironment: {},
647
+ environmentStartsClean: false,
648
+ unsetEnvironmentNames: [],
437
649
  inlineMessage: null,
438
650
  repositorySelection: "current-cwd",
439
651
  requiresExternalMessageSource: false,
@@ -444,6 +656,9 @@ export function parseGitCommitCommand(commandText: string): GitCommitCommandPars
444
656
  if (subcommandIndex < 0 || tokens[subcommandIndex]?.toLowerCase() !== "commit") {
445
657
  return {
446
658
  isGitCommit: false,
659
+ inlineEnvironment: {},
660
+ environmentStartsClean: false,
661
+ unsetEnvironmentNames: [],
447
662
  inlineMessage: null,
448
663
  repositorySelection: "current-cwd",
449
664
  requiresExternalMessageSource: false,
@@ -451,6 +666,7 @@ export function parseGitCommitCommand(commandText: string): GitCommitCommandPars
451
666
  }
452
667
 
453
668
  const repositorySelection = readGitRepositorySelection(tokens, gitTokenIndex, subcommandIndex);
669
+ const { inlineEnvironment, environmentStartsClean, unsetEnvironmentNames } = readInlineEnvironmentAssignments(shellTokens ?? [], gitTokenIndex);
454
670
  const messageParts: string[] = [];
455
671
  let requiresExternalMessageSource = false;
456
672
  const args = tokens.slice(subcommandIndex + 1);
@@ -492,12 +708,26 @@ export function parseGitCommitCommand(commandText: string): GitCommitCommandPars
492
708
 
493
709
  return {
494
710
  isGitCommit: true,
711
+ inlineEnvironment,
712
+ environmentStartsClean,
713
+ unsetEnvironmentNames,
495
714
  inlineMessage: messageParts.length > 0 ? messageParts.join("\n\n").trim() : null,
496
715
  repositorySelection,
497
716
  requiresExternalMessageSource,
498
717
  };
499
718
  }
500
719
 
720
+ function buildEffectiveLoreCommitGuardEnv(parsed: GitCommitCommandParseResult): NodeJS.ProcessEnv {
721
+ const effectiveEnvironment: NodeJS.ProcessEnv = parsed.environmentStartsClean ? {} : { ...process.env };
722
+ for (const name of parsed.unsetEnvironmentNames) {
723
+ delete effectiveEnvironment[name];
724
+ }
725
+ for (const [name, value] of Object.entries(parsed.inlineEnvironment)) {
726
+ if (typeof value === "string") effectiveEnvironment[name] = value;
727
+ }
728
+ return effectiveEnvironment;
729
+ }
730
+
501
731
  function isLoreTrailerLine(line: string): boolean {
502
732
  return line === OMX_COAUTHOR_TRAILER
503
733
  || LORE_TRAILER_PREFIXES.some((prefix) => line.startsWith(prefix));
@@ -578,6 +808,8 @@ function buildGitCommitEnforcementOutput(commandText: string): Record<string, un
578
808
  const parsed = parseGitCommitCommand(commandText);
579
809
  if (!parsed.isGitCommit) return null;
580
810
 
811
+ if (!isLoreCommitGuardEnabled(buildEffectiveLoreCommitGuardEnv(parsed))) return null;
812
+
581
813
  const errors = parsed.requiresExternalMessageSource
582
814
  ? [
583
815
  "Use inline `git commit -m ...` paragraphs for Lore-format commits in this path; file/editor/reuse/fixup message sources are not inspectable safely from pre-tool-use enforcement.",
@@ -616,6 +848,125 @@ function buildDocumentRefreshPreToolUseOutput(
616
848
  return buildDocumentRefreshAdvisoryOutput(warning, "PreToolUse");
617
849
  }
618
850
 
851
+
852
+ export const SLOPPY_FALLBACK_PHRASE_PATTERNS = [
853
+ /\bquick hack\b/i,
854
+ /\bhacky\b/i,
855
+ /\bworkaround for now\b/i,
856
+ /\btemporary workaround\b/i,
857
+ /\btemporary fallback\b/i,
858
+ /\bjust bypass\b/i,
859
+ /\bjust skip\b/i,
860
+ /\bskip (?:the )?(?:failing )?(?:test|validation|checks?)\b/i,
861
+ /\bfallback if (?:it|this|that) fails\b/i,
862
+ /\bfor now,? just\b/i,
863
+ /\bbypass (?:the )?(?:failing )?(?:test|validation|checks?)\b/i,
864
+ ] as const;
865
+
866
+ export const SLOPPY_FALLBACK_IMPLEMENTATION_CONTEXT_PATTERNS = [
867
+ /\badd\b/i,
868
+ /\bimplement\b/i,
869
+ /\bpatch\b/i,
870
+ /\bwrite\b/i,
871
+ /\bchange\b/i,
872
+ /\bfix\b/i,
873
+ /\bbypass\b/i,
874
+ /\bfallback\b/i,
875
+ /\bworkaround\b/i,
876
+ /\bskip\b/i,
877
+ /\bdisable\b/i,
878
+ ] as const;
879
+
880
+ export const SLOPPY_FALLBACK_GROUNDING_PATTERNS = [
881
+ /\btested\b/i,
882
+ /\btests? pass(?:ed)?\b/i,
883
+ /\bnpm (?:run )?test\b/i,
884
+ /\bnode --test\b/i,
885
+ /\bunit tests?\b/i,
886
+ /\bintegration tests?\b/i,
887
+ /\bregression tests?\b/i,
888
+ /\bcoverage\b/i,
889
+ /\bspec(?:ification)?\b/i,
890
+ /\bADR\b/,
891
+ /\barchitecture\b/i,
892
+ /\barchitect\b/i,
893
+ /\bdesign\b/i,
894
+ /\bbecause\b/i,
895
+ /\bcompatib(?:le|ility)\b/i,
896
+ /\bbackward-compatible\b/i,
897
+ /\bfail-safe\b/i,
898
+ /\bfailsafe\b/i,
899
+ /\benvironment issue\b/i,
900
+ /\benv(?:ironment)? problem\b/i,
901
+ /\buser approved\b/i,
902
+ /\bapproved by (?:the )?user\b/i,
903
+ /(?:^|\s)#\d+\b/,
904
+ /\bPR\s*#?\d+\b/i,
905
+ ] as const;
906
+
907
+ const READ_ONLY_COMMAND_TOKENS = new Set([
908
+ "cat",
909
+ "find",
910
+ "grep",
911
+ "head",
912
+ "less",
913
+ "ls",
914
+ "rg",
915
+ "sed",
916
+ "tail",
917
+ ]);
918
+
919
+ function commandStartsWithReadOnlyInspection(command: string): boolean {
920
+ if (commandHasWriteLikeIntent(command)) return false;
921
+ const tokens = tokenizeShellCommand(command);
922
+ if (!tokens || tokens.length === 0) return false;
923
+ let commandToken = tokens[0] ?? "";
924
+ if (commandToken === "env") {
925
+ const nextCommand = tokens.find((token, index) => index > 0 && !token.startsWith("-") && !isInlineShellEnvAssignment(token));
926
+ commandToken = nextCommand ?? commandToken;
927
+ }
928
+ const basename = commandToken.replace(/\\/g, "/").split("/").pop()?.toLowerCase() ?? commandToken.toLowerCase();
929
+ if (!READ_ONLY_COMMAND_TOKENS.has(basename)) return false;
930
+ if (basename === "sed" && tokens.some((token) => token === "-i" || token.startsWith("-i"))) return false;
931
+ if (basename === "cat" && /(?:^|[;&|]\s*)cat\b[\s\S]{0,200}>\s*[^\s&|;]+/.test(command)) return false;
932
+ return !/\|\s*(?:sh|bash|zsh|python3?|node|perl|ruby|apply_patch)\b/i.test(command);
933
+ }
934
+
935
+ function commandHasWriteLikeIntent(command: string): boolean {
936
+ return /\bapply_patch\b/.test(command)
937
+ || /(?:^|[;&|]\s*)(?:cat|printf|echo)\b[\s\S]{0,200}>\s*[^\s&|;]+/.test(command)
938
+ || /\btee\s+(?:-a\s+)?[^\s&|;]+/.test(command)
939
+ || /\bsed\s+(?:[^\n;&|]*\s)?-i(?:\b|['"])/.test(command)
940
+ || /\b(?:python3?|node|perl|ruby)\b[\s\S]{0,240}\b(?:writeFileSync|writeFile|write_text|open\([^)]*["']w|File\.write|Path\()/.test(command)
941
+ || /<<['"]?[A-Za-z0-9_ -]+['"]?[\s\S]*(?:^|\n)(?:\+\+\+\s|---\s|import\s|export\s|function\s|const\s|class\s|interface\s)/m.test(command);
942
+ }
943
+
944
+ export function hasAnyPattern(text: string, patterns: readonly RegExp[]): boolean {
945
+ return patterns.some((pattern) => pattern.test(text));
946
+ }
947
+
948
+ function detectSloppyFallbackFraming(command: string): boolean {
949
+ const trimmed = command.trim();
950
+ if (!trimmed) return false;
951
+ if (commandStartsWithReadOnlyInspection(trimmed)) return false;
952
+ if (!commandHasWriteLikeIntent(trimmed)) return false;
953
+ if (!hasAnyPattern(trimmed, SLOPPY_FALLBACK_PHRASE_PATTERNS)) return false;
954
+ if (!hasAnyPattern(trimmed, SLOPPY_FALLBACK_IMPLEMENTATION_CONTEXT_PATTERNS)) return false;
955
+ if (hasAnyPattern(trimmed, SLOPPY_FALLBACK_GROUNDING_PATTERNS)) return false;
956
+ return true;
957
+ }
958
+
959
+ function buildSloppyFallbackPreToolUseOutput(commandText: string): Record<string, unknown> | null {
960
+ if (!detectSloppyFallbackFraming(commandText)) return null;
961
+ return {
962
+ hookSpecificOutput: {
963
+ hookEventName: "PreToolUse",
964
+ },
965
+ systemMessage:
966
+ "Sloppy fallback/workaround framing detected: don't make potential slop. Consult an architect for a concrete architecture, or ask the user if this is an environment issue before adding bypass/fallback code.",
967
+ };
968
+ }
969
+
619
970
  function commandInvokesOmxQuestion(command: string): boolean {
620
971
  const tokens = tokenizeShellCommand(command)?.map((token) => token.toLowerCase()) ?? [];
621
972
  for (let index = 0; index < tokens.length; index += 1) {
@@ -746,6 +1097,8 @@ export function buildNativePreToolUseOutput(
746
1097
  safeString(payload.cwd).trim() || process.cwd(),
747
1098
  );
748
1099
  if (documentRefreshWarning) return documentRefreshWarning;
1100
+ const sloppyFallbackWarning = buildSloppyFallbackPreToolUseOutput(normalized.normalizedCommand);
1101
+ if (sloppyFallbackWarning) return sloppyFallbackWarning;
749
1102
  if (!matchesDestructiveFixture(normalized.normalizedCommand)) return null;
750
1103
 
751
1104
  return {
@@ -28,7 +28,8 @@ const runOnce = process.argv.includes('--once');
28
28
  const pollMs = Math.max(250, asNumber(argValue('--poll-ms', process.env.OMX_HOOK_DERIVED_POLL_MS || '800'), 800));
29
29
  const maxFileAgeMs = Math.max(10_000, asNumber(argValue('--file-age-ms', process.env.OMX_HOOK_DERIVED_FILE_AGE_MS || '90000'), 90000));
30
30
 
31
- const omxDir = join(cwd, '.omx');
31
+ const runtimeRoot = resolve(process.env.OMX_ROOT || process.env.OMX_STATE_ROOT || cwd);
32
+ const omxDir = join(runtimeRoot, '.omx');
32
33
  const logsDir = join(omxDir, 'logs');
33
34
  const stateDir = join(omxDir, 'state');
34
35
  const watcherStatePath = join(stateDir, 'hook-derived-watcher-state.json');
@@ -142,7 +142,8 @@ const maxLifetimeMs = runOnce
142
142
  )
143
143
  );
144
144
 
145
- const omxDir = join(cwd, '.omx');
145
+ const runtimeRoot = resolve(process.env.OMX_ROOT || process.env.OMX_STATE_ROOT || cwd);
146
+ const omxDir = join(runtimeRoot, '.omx');
146
147
  const logsDir = join(omxDir, 'logs');
147
148
  const stateDir = join(omxDir, 'state');
148
149
  const statePath = join(stateDir, 'notify-fallback-state.json');
@@ -34,7 +34,6 @@ export function classifyLeaderActionState({
34
34
  allWorkersIdle = false,
35
35
  workerPanesAlive = false,
36
36
  taskCounts = {},
37
- teamProgressStalled = false,
38
37
  } = {}) {
39
38
  const pending = Number.isFinite(taskCounts.pending) ? taskCounts.pending : 0;
40
39
  const blocked = Number.isFinite(taskCounts.blocked) ? taskCounts.blocked : 0;
@@ -43,10 +42,9 @@ export function classifyLeaderActionState({
43
42
  const pendingFollowUpTasks = allWorkersIdle && pending > 0 && blocked === 0 && inProgress === 0;
44
43
  const blockedWaitingOnLeader = allWorkersIdle && blocked > 0 && pending === 0 && inProgress === 0;
45
44
  const terminalWaitingOnLeader = allWorkersIdle && tasksComplete && workerPanesAlive;
46
- const stalledWaitingOnLeader = blockedWaitingOnLeader || teamProgressStalled;
47
45
 
48
46
  if (terminalWaitingOnLeader) return 'done_waiting_on_leader';
49
- if (stalledWaitingOnLeader) return 'stuck_waiting_on_leader';
47
+ if (blockedWaitingOnLeader) return 'stuck_waiting_on_leader';
50
48
  if (pendingFollowUpTasks) return 'still_actionable';
51
49
  return 'still_actionable';
52
50
  }
@@ -75,23 +75,6 @@ export function resolveLeaderStalenessThresholdMs() {
75
75
  return 180_000;
76
76
  }
77
77
 
78
- export function resolveFallbackProgressStallThresholdMs() {
79
- const raw = safeString(process.env.OMX_TEAM_PROGRESS_STALL_MS || '');
80
- const parsed = asNumber(raw);
81
- // Fallback-only threshold used when worker turn-count signals are unavailable.
82
- // Default: 2 minutes. Guard against unreasonable values.
83
- if (parsed !== null && parsed >= 10_000 && parsed <= 60 * 60_000) return parsed;
84
- return 120_000;
85
- }
86
-
87
- export function resolveWorkerTurnStallThresholdMs() {
88
- const raw = safeString(process.env.OMX_TEAM_WORKER_TURN_STALL_MS || '');
89
- const parsed = asNumber(raw);
90
- // Default: 30 seconds. Guard against unreasonable values.
91
- if (parsed !== null && parsed >= 10_000 && parsed <= 10 * 60_000) return parsed;
92
- return 30_000;
93
- }
94
-
95
78
  function buildStatusCheckReminder(teamName) {
96
79
  return `Next: check messages; keep orchestrating; if done, gracefully shut down: omx team shutdown ${teamName}.`;
97
80
  }
@@ -104,27 +87,6 @@ function buildWorkerStartEvidenceReminder(teamName, workerName) {
104
87
  return `Next: check ${workerName} msg/output, confirm task in omx team status ${teamName}, then reassign/nudge.`;
105
88
  }
106
89
 
107
- function classifyLeaderActionState({
108
- allWorkersIdle = false,
109
- workerPanesAlive = false,
110
- taskCounts = {},
111
- teamProgressStalled = false,
112
- } = {}) {
113
- const pending = Number.isFinite(taskCounts.pending) ? taskCounts.pending : 0;
114
- const blocked = Number.isFinite(taskCounts.blocked) ? taskCounts.blocked : 0;
115
- const inProgress = Number.isFinite(taskCounts.in_progress) ? taskCounts.in_progress : 0;
116
- const tasksComplete = pending === 0 && blocked === 0 && inProgress === 0;
117
- const pendingFollowUpTasks = allWorkersIdle && pending > 0 && blocked === 0 && inProgress === 0;
118
- const blockedWaitingOnLeader = allWorkersIdle && blocked > 0 && pending === 0 && inProgress === 0;
119
- const terminalWaitingOnLeader = allWorkersIdle && tasksComplete && workerPanesAlive;
120
- const stalledWaitingOnLeader = blockedWaitingOnLeader || teamProgressStalled;
121
-
122
- if (terminalWaitingOnLeader) return 'done_waiting_on_leader';
123
- if (stalledWaitingOnLeader) return 'stuck_waiting_on_leader';
124
- if (pendingFollowUpTasks) return 'still_actionable';
125
- return 'still_actionable';
126
- }
127
-
128
90
  function buildLeaderActionGuidance(teamName, {
129
91
  allWorkersIdle = false,
130
92
  workerPanesAlive = false,
@@ -588,8 +550,6 @@ export async function maybeNudgeTeamLeader({
588
550
  }) {
589
551
  const intervalMs = resolveLeaderNudgeIntervalMs();
590
552
  const idleCooldownMs = resolveLeaderAllIdleNudgeCooldownMs();
591
- const fallbackProgressStallThresholdMs = resolveFallbackProgressStallThresholdMs();
592
- const workerTurnStallThresholdMs = resolveWorkerTurnStallThresholdMs();
593
553
  const nowMs = Date.now();
594
554
  const nowIso = new Date().toISOString();
595
555
  const omxDir = join(cwd, '.omx');
@@ -715,7 +675,6 @@ export async function maybeNudgeTeamLeader({
715
675
  const previousProgressAtMs = previousProgressAtIso ? Date.parse(previousProgressAtIso) : NaN;
716
676
  const previousTurnCounts = readPreviousWorkerTurnCounts(previousSignature);
717
677
  const workerTurnProgress = hasWorkerTurnProgress(progressSnapshot.workerSnapshot, previousTurnCounts);
718
- const hasTrackableTurnSignals = hasTrackableActiveWorkerTurns(progressSnapshot.workerSnapshot, previousTurnCounts);
719
678
  const progressChanged = !previousSignature || previousSignature !== progressSnapshot.signature || workerTurnProgress;
720
679
  const extraProgressEvidenceMs = await readLatestTeamProgressEvidenceMs(cwd, teamName).catch(() => Number.NaN);
721
680
  const effectiveProgressAtMs = progressChanged || !Number.isFinite(previousProgressAtMs)
@@ -725,22 +684,15 @@ export async function maybeNudgeTeamLeader({
725
684
  ? Math.max(effectiveProgressAtMs, extraProgressEvidenceMs)
726
685
  : effectiveProgressAtMs;
727
686
  const effectiveProgressAtIso = new Date(latestProgressEvidenceMs).toISOString();
728
- const stalledForMs = Math.max(0, nowMs - latestProgressEvidenceMs);
729
- const stallThresholdMs = hasTrackableTurnSignals ? workerTurnStallThresholdMs : fallbackProgressStallThresholdMs;
730
- const teamProgressStalled =
731
- progressSnapshot.workRemaining
732
- && paneStatus.alive
733
- && !allWorkersIdle
734
- && !progressChanged
735
- && stalledForMs >= stallThresholdMs;
736
687
  const hasFreshProgressEvidence =
737
688
  progressSnapshot.workRemaining
738
- && stalledForMs < stallThresholdMs;
689
+ && (progressChanged
690
+ || (Number.isFinite(extraProgressEvidenceMs)
691
+ && (nowMs - extraProgressEvidenceMs) < resolveLeaderStalenessThresholdMs()));
739
692
  const leaderActionState = classifyLeaderActionState({
740
693
  allWorkersIdle,
741
694
  workerPanesAlive: paneStatus.alive,
742
695
  taskCounts: progressSnapshot.taskCounts,
743
- teamProgressStalled,
744
696
  });
745
697
  const leaderActionGuidance = buildLeaderActionGuidance(teamName, {
746
698
  allWorkersIdle,
@@ -773,8 +725,6 @@ export async function maybeNudgeTeamLeader({
773
725
  // Stale-leader follow-up is the only periodic visible nudge path.
774
726
  // This keeps the leader pane quieter when the leader is not actually stale.
775
727
  const stalePanesNudge = paneStatus.alive && leaderStale && !hasFreshProgressEvidence;
776
- const previousStalledTeamNudge = prevReason === 'stuck_waiting_on_leader';
777
- const stalledTeamNudge = teamProgressStalled && (dueByTime || !previousStalledTeamNudge);
778
728
  const staleFollowupDue = stalePanesNudge && dueByTime;
779
729
  const hasActionableNewMessage = hasNewMessage && (allowFreshMailboxNudges || leaderStale);
780
730
 
@@ -800,12 +750,6 @@ export async function maybeNudgeTeamLeader({
800
750
  `Team ${teamName}: ${ackWithoutStartEvidence.worker} said "${ackWithoutStartEvidence.body}" `
801
751
  + `but has no start evidence (status: ${ackWithoutStartEvidence.statusState}). `
802
752
  + buildWorkerStartEvidenceReminder(teamName, ackWithoutStartEvidence.worker);
803
- } else if (stalledTeamNudge) {
804
- nudgeReason = 'stuck_waiting_on_leader';
805
- const stallPrefix = leaderStale ? 'leader stale, ' : 'worker panes stalled, ';
806
- text =
807
- `Team ${teamName}: ${stallPrefix}no progress ${formatDurationMs(stalledForMs)}. `
808
- + leaderActionGuidance;
809
753
  } else if (stalePanesNudge && hasActionableNewMessage) {
810
754
  nudgeReason = 'stale_leader_with_messages';
811
755
  text =
@@ -838,7 +782,7 @@ export async function maybeNudgeTeamLeader({
838
782
  + (progressSnapshot.taskCounts.blocked || 0)
839
783
  + (progressSnapshot.taskCounts.in_progress || 0),
840
784
  unread_leader_message_count: unreadLeaderMessageCount,
841
- stalled_for_ms: teamProgressStalled ? stalledForMs : null,
785
+ stalled_for_ms: null,
842
786
  source: source === 'notify_fallback_watcher' ? 'notify_hook' : source,
843
787
  };
844
788
  await writeTeamLeaderAttention(teamName, {
@@ -855,7 +799,7 @@ export async function maybeNudgeTeamLeader({
855
799
  leader_session_stopped_at: null,
856
800
  unread_leader_message_count: unreadLeaderMessageCount,
857
801
  work_remaining: progressSnapshot.workRemaining,
858
- stalled_for_ms: teamProgressStalled ? stalledForMs : null,
802
+ stalled_for_ms: null,
859
803
  }, cwd).catch(() => {});
860
804
 
861
805
  if (!nudgeReason) continue;
@@ -1001,7 +945,7 @@ export async function maybeNudgeTeamLeader({
1001
945
  pane_count: paneStatus.paneCount,
1002
946
  leader_stale: leaderStale,
1003
947
  message_count: messages.length,
1004
- stalled_for_ms: teamProgressStalled ? stalledForMs : undefined,
948
+ stalled_for_ms: undefined,
1005
949
  missing_signal_workers: progressSnapshot.missingSignalWorkers,
1006
950
  visible_injection_suppressed: true,
1007
951
  suppression_reason: LEADER_PANE_SAME_CLASSIFIED_STATE_SUPPRESSED_REASON,
@@ -1059,7 +1003,7 @@ export async function maybeNudgeTeamLeader({
1059
1003
  pane_count: paneStatus.paneCount,
1060
1004
  leader_stale: leaderStale,
1061
1005
  message_count: messages.length,
1062
- stalled_for_ms: teamProgressStalled ? stalledForMs : undefined,
1006
+ stalled_for_ms: undefined,
1063
1007
  missing_signal_workers: progressSnapshot.missingSignalWorkers,
1064
1008
  });
1065
1009
  } catch { /* ignore */ }