@jaimevalasek/aioson 1.7.0 → 1.8.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 (383) hide show
  1. package/CHANGELOG.md +60 -0
  2. package/README.md +153 -10
  3. package/docs/en/cli-reference.md +56 -1
  4. package/docs/en/i18n.md +18 -18
  5. package/docs/en/schemas/index.json +10 -0
  6. package/docs/en/schemas/parallel-assign.schema.json +9 -0
  7. package/docs/en/schemas/parallel-doctor.schema.json +36 -0
  8. package/docs/en/schemas/parallel-guard.schema.json +63 -0
  9. package/docs/en/schemas/parallel-merge.schema.json +84 -0
  10. package/docs/en/schemas/parallel-status.schema.json +91 -1
  11. package/docs/integrations/apps-publish-marketplace.md +94 -0
  12. package/docs/pt/README.md +9 -0
  13. package/docs/pt/agentes.md +324 -3
  14. package/docs/pt/clientes-ai.md +7 -3
  15. package/docs/pt/comandos-cli.md +160 -13
  16. package/docs/pt/compress-agents.md +304 -0
  17. package/docs/pt/design-docs-governance.md +59 -0
  18. package/docs/pt/feature-archive.md +191 -0
  19. package/docs/pt/genome-3.0-spec.md +115 -4
  20. package/docs/pt/genome-distribution.md +232 -0
  21. package/docs/pt/inicio-rapido.md +1 -0
  22. package/docs/pt/motor-hardening.md +492 -0
  23. package/docs/pt/runner-system.md +113 -0
  24. package/package.json +2 -1
  25. package/src/agent-manifests.js +66 -0
  26. package/src/agents.js +27 -7
  27. package/src/autonomy-policy.js +139 -0
  28. package/src/brain-query.js +161 -0
  29. package/src/cli.js +1377 -1099
  30. package/src/commands/agents.js +102 -7
  31. package/src/commands/artifact-validate.js +33 -4
  32. package/src/commands/auth.js +272 -0
  33. package/src/commands/brain-query.js +44 -0
  34. package/src/commands/briefing.js +344 -0
  35. package/src/commands/commit-prepare.js +547 -0
  36. package/src/commands/compress-agents.js +416 -0
  37. package/src/commands/context-health.js +4 -2
  38. package/src/commands/context-trim.js +17 -11
  39. package/src/commands/design-hybrid-options.js +3 -3
  40. package/src/commands/devlog-process.js +6 -4
  41. package/src/commands/dossier.js +423 -0
  42. package/src/commands/feature-archive.js +513 -0
  43. package/src/commands/feature-close.js +123 -18
  44. package/src/commands/gate-approve.js +198 -0
  45. package/src/commands/gate-check.js +24 -5
  46. package/src/commands/genome-doctor.js +166 -9
  47. package/src/commands/git-guard.js +170 -0
  48. package/src/commands/harness.js +121 -0
  49. package/src/commands/implementation-plan.js +47 -20
  50. package/src/commands/init.js +6 -2
  51. package/src/commands/install.js +6 -2
  52. package/src/commands/live.js +497 -56
  53. package/src/commands/locale-apply.js +9 -6
  54. package/src/commands/locale-diff.js +11 -112
  55. package/src/commands/mcp-doctor.js +2 -1
  56. package/src/commands/mcp-init.js +4 -10
  57. package/src/commands/memory.js +234 -0
  58. package/src/commands/parallel-assign.js +107 -27
  59. package/src/commands/parallel-doctor.js +416 -3
  60. package/src/commands/parallel-guard.js +241 -0
  61. package/src/commands/parallel-init.js +66 -4
  62. package/src/commands/parallel-merge.js +299 -0
  63. package/src/commands/parallel-status.js +147 -3
  64. package/src/commands/preflight.js +63 -4
  65. package/src/commands/qa-init.js +10 -5
  66. package/src/commands/revision.js +235 -0
  67. package/src/commands/scaffold-complete.js +188 -0
  68. package/src/commands/security-audit.js +275 -0
  69. package/src/commands/security-scan.js +376 -0
  70. package/src/commands/self-implement-loop.js +46 -2
  71. package/src/commands/setup-context.js +11 -10
  72. package/src/commands/squad-agent-create.js +51 -9
  73. package/src/commands/squad-investigate.js +53 -0
  74. package/src/commands/squad-plan.js +33 -1
  75. package/src/commands/squad-scaffold.js +4 -3
  76. package/src/commands/squad-score.js +71 -14
  77. package/src/commands/squad-status.js +22 -1
  78. package/src/commands/squad-validate.js +93 -2
  79. package/src/commands/store-genome.js +304 -0
  80. package/src/commands/store-skill.js +247 -0
  81. package/src/commands/store-squad.js +431 -0
  82. package/src/commands/store-system.js +392 -0
  83. package/src/commands/tool-capabilities.js +63 -0
  84. package/src/commands/update.js +3 -3
  85. package/src/commands/verify-gate.js +40 -0
  86. package/src/commands/workflow-execute.js +644 -155
  87. package/src/commands/workflow-harden.js +231 -0
  88. package/src/commands/workflow-heal.js +136 -0
  89. package/src/commands/workflow-next.js +460 -22
  90. package/src/commands/workflow-status.js +328 -138
  91. package/src/commands/workspace.js +144 -0
  92. package/src/constants.js +55 -75
  93. package/src/context-memory.js +133 -4
  94. package/src/context-writer.js +2 -1
  95. package/src/context.js +32 -2
  96. package/src/doctor.js +46 -6
  97. package/src/dossier/codemap-store.js +267 -0
  98. package/src/dossier/dossier-bootstrap.js +222 -0
  99. package/src/dossier/dossier-compact.js +159 -0
  100. package/src/dossier/lock.js +128 -0
  101. package/src/dossier/revision-store.js +313 -0
  102. package/src/dossier/schema.js +155 -0
  103. package/src/dossier/store.js +400 -0
  104. package/src/execution-gateway.js +3 -0
  105. package/src/friction-scanner.js +202 -0
  106. package/src/genome-schema.js +24 -1
  107. package/src/genomes.js +33 -0
  108. package/src/handoff-contract.js +363 -0
  109. package/src/handoff-validator.js +45 -0
  110. package/src/harness/circuit-breaker.js +135 -0
  111. package/src/i18n/messages/en.js +317 -22
  112. package/src/i18n/messages/es.js +259 -18
  113. package/src/i18n/messages/fr.js +260 -18
  114. package/src/i18n/messages/pt-BR.js +313 -22
  115. package/src/install-profile.js +0 -16
  116. package/src/installer.js +70 -6
  117. package/src/lib/git-commit-guard.js +691 -0
  118. package/src/lib/security/artifact-reader.js +167 -0
  119. package/src/lib/security/exit-codes.js +51 -0
  120. package/src/lib/security/findings-writer.js +176 -0
  121. package/src/lib/security/runtime-events.js +77 -0
  122. package/src/lib/security/secrets-regex.js +115 -0
  123. package/src/lib/store/security-scan.js +173 -0
  124. package/src/lib/terminal-checkbox.js +130 -0
  125. package/src/lib/tmux-launcher.js +163 -0
  126. package/src/lib/tool-capabilities.js +102 -0
  127. package/src/locales.js +12 -8
  128. package/src/parallel-workspace.js +756 -0
  129. package/src/parser.js +8 -1
  130. package/src/path-guard.js +47 -0
  131. package/src/preflight-engine.js +237 -26
  132. package/src/self-healing.js +142 -0
  133. package/src/session-handoff.js +111 -1
  134. package/src/squad/squad-scaffold.js +183 -19
  135. package/src/test-briefing.js +226 -0
  136. package/src/updater.js +1 -1
  137. package/src/utils.js +3 -0
  138. package/src/workflow-gates.js +185 -0
  139. package/template/.aioson/agents/analyst.md +76 -130
  140. package/template/.aioson/agents/architect.md +53 -86
  141. package/template/.aioson/agents/committer.md +161 -0
  142. package/template/.aioson/agents/copywriter.md +463 -0
  143. package/template/.aioson/agents/cypher.md +252 -0
  144. package/template/.aioson/agents/dev.md +112 -600
  145. package/template/.aioson/agents/deyvin.md +33 -235
  146. package/template/.aioson/agents/discover.md +235 -0
  147. package/template/.aioson/agents/discovery-design-doc.md +17 -252
  148. package/template/.aioson/agents/genome.md +76 -26
  149. package/template/.aioson/agents/manifests/analyst.manifest.json +26 -0
  150. package/template/.aioson/agents/manifests/architect.manifest.json +23 -0
  151. package/template/.aioson/agents/manifests/committer.manifest.json +23 -0
  152. package/template/.aioson/agents/manifests/dev.manifest.json +37 -0
  153. package/template/.aioson/agents/manifests/orchestrator.manifest.json +30 -0
  154. package/template/.aioson/agents/manifests/pentester.manifest.json +39 -0
  155. package/template/.aioson/agents/manifests/pm.manifest.json +26 -0
  156. package/template/.aioson/agents/manifests/product.manifest.json +23 -0
  157. package/template/.aioson/agents/manifests/qa.manifest.json +25 -0
  158. package/template/.aioson/agents/manifests/setup.manifest.json +20 -0
  159. package/template/.aioson/agents/manifests/ux-ui.manifest.json +24 -0
  160. package/template/.aioson/agents/neo.md +10 -8
  161. package/template/.aioson/agents/orache.md +2 -6
  162. package/template/.aioson/agents/orchestrator.md +81 -182
  163. package/template/.aioson/agents/pentester.md +235 -0
  164. package/template/.aioson/agents/pm.md +40 -104
  165. package/template/.aioson/agents/product.md +99 -344
  166. package/template/.aioson/agents/profiler-enricher.md +57 -6
  167. package/template/.aioson/agents/profiler-forge.md +17 -7
  168. package/template/.aioson/agents/profiler-researcher.md +29 -6
  169. package/template/.aioson/agents/qa.md +165 -410
  170. package/template/.aioson/agents/setup.md +52 -262
  171. package/template/.aioson/agents/sheldon.md +122 -754
  172. package/template/.aioson/agents/site-forge.md +111 -1583
  173. package/template/.aioson/agents/squad.md +139 -1820
  174. package/template/.aioson/agents/tester.md +10 -0
  175. package/template/.aioson/agents/ux-ui.md +103 -645
  176. package/template/.aioson/agents/validator.md +69 -0
  177. package/template/.aioson/brains/scripts/query.js +5 -1
  178. package/template/.aioson/config/autonomy-protocol.json +43 -0
  179. package/template/.aioson/config.md +43 -15
  180. package/template/.aioson/constitution.md +36 -33
  181. package/template/.aioson/context/design-doc.md +136 -0
  182. package/template/.aioson/context/project-map.md +57 -0
  183. package/template/.aioson/design-docs/code-reuse.md +48 -0
  184. package/template/.aioson/design-docs/componentization.md +47 -0
  185. package/template/.aioson/design-docs/file-size.md +52 -0
  186. package/template/.aioson/design-docs/folder-structure.md +51 -0
  187. package/template/.aioson/design-docs/naming.md +54 -0
  188. package/template/.aioson/docs/LAYERS.md +12 -2
  189. package/template/.aioson/docs/dev/execution-discipline.md +106 -0
  190. package/template/.aioson/docs/dev/stack-conventions.md +83 -0
  191. package/template/.aioson/docs/deyvin/continuity-recovery.md +57 -0
  192. package/template/.aioson/docs/deyvin/debugging-escalation.md +30 -0
  193. package/template/.aioson/docs/deyvin/pair-execution.md +44 -0
  194. package/template/.aioson/docs/deyvin/runtime-handoffs.md +36 -0
  195. package/template/.aioson/docs/product/conversation-playbook.md +116 -0
  196. package/template/.aioson/docs/product/prd-contract.md +107 -0
  197. package/template/.aioson/docs/product/quality-lens.md +57 -0
  198. package/template/.aioson/docs/product/research-loop.md +65 -0
  199. package/template/.aioson/docs/sheldon/enrichment-paths.md +134 -0
  200. package/template/.aioson/docs/sheldon/quality-lens.md +57 -0
  201. package/template/.aioson/docs/sheldon/research-loop.md +56 -0
  202. package/template/.aioson/docs/sheldon/web-intelligence.md +75 -0
  203. package/template/.aioson/docs/site-forge-build.md +195 -0
  204. package/template/.aioson/docs/site-forge-extraction.md +135 -0
  205. package/template/.aioson/docs/site-forge-qa.md +155 -0
  206. package/template/.aioson/docs/site-forge-recon.md +434 -0
  207. package/template/.aioson/docs/site-forge-transform.md +249 -0
  208. package/template/.aioson/docs/squad/content-output.md +91 -0
  209. package/template/.aioson/docs/squad/creation-flow.md +135 -0
  210. package/template/.aioson/docs/squad/domain-classification.md +117 -0
  211. package/template/.aioson/docs/squad/genome-bindings.md +47 -0
  212. package/template/.aioson/docs/squad/package-contract.md +234 -0
  213. package/template/.aioson/docs/squad/quality-lens.md +56 -0
  214. package/template/.aioson/docs/squad/research-loop.md +59 -0
  215. package/template/.aioson/docs/squad/session-operations.md +117 -0
  216. package/template/.aioson/docs/squad/workflow-quality.md +165 -0
  217. package/template/.aioson/docs/ux-ui/accessibility-audit.md +55 -0
  218. package/template/.aioson/docs/ux-ui/audit-mode.md +86 -0
  219. package/template/.aioson/docs/ux-ui/component-map.md +35 -0
  220. package/template/.aioson/docs/ux-ui/design-execution.md +111 -0
  221. package/template/.aioson/docs/ux-ui/design-gate.md +27 -0
  222. package/template/.aioson/docs/ux-ui/research-mode.md +39 -0
  223. package/template/.aioson/docs/ux-ui/site-delivery.md +156 -0
  224. package/template/.aioson/docs/ux-ui/token-contract.md +57 -0
  225. package/template/.aioson/genomes/copywriting.md +204 -0
  226. package/template/.aioson/genomes/copywriting.meta.json +48 -0
  227. package/template/.aioson/git-guard.json +11 -0
  228. package/template/.aioson/mcp/servers.md +0 -1
  229. package/template/.aioson/rules/agent-language-policy.md +93 -0
  230. package/template/.aioson/rules/aioson-context-boundary.md +63 -0
  231. package/template/.aioson/rules/canonical-path-contract.md +47 -0
  232. package/template/.aioson/rules/data-format-convention.md +24 -86
  233. package/template/.aioson/rules/disk-first-artifacts.md +44 -0
  234. package/template/.aioson/rules/output-brevity.md +44 -0
  235. package/template/.aioson/rules/prd-section-ownership.md +49 -0
  236. package/template/.aioson/rules/security-baseline.md +139 -0
  237. package/template/.aioson/rules/spec-level-ownership.md +61 -0
  238. package/template/.aioson/rules/squad-driver-pattern.md +81 -0
  239. package/template/.aioson/schemas/squad-blueprint.schema.json +24 -0
  240. package/template/.aioson/schemas/squad-manifest.schema.json +44 -0
  241. package/template/.aioson/skills/design/cognitive-core-ui/references/motion.md +2 -0
  242. package/template/.aioson/skills/marketing/references/anti-patterns.md +254 -0
  243. package/template/.aioson/skills/marketing/references/fascinations.md +192 -0
  244. package/template/.aioson/skills/marketing/references/five-acts.md +248 -0
  245. package/template/.aioson/skills/marketing/references/market-intelligence.md +198 -0
  246. package/template/.aioson/skills/marketing/references/offer-structure.md +203 -0
  247. package/template/.aioson/skills/marketing/references/one-belief.md +149 -0
  248. package/template/.aioson/skills/marketing/references/patterns.md +218 -0
  249. package/template/.aioson/skills/marketing/references/pms-research.md +193 -0
  250. package/template/.aioson/skills/marketing/vsl-craft.md +385 -0
  251. package/template/.aioson/skills/process/aioson-spec-driven/references/pm.md +30 -0
  252. package/template/.aioson/skills/process/secure-tdd/SKILL.md +97 -0
  253. package/template/.aioson/skills/process/secure-tdd/references/nextjs.md +81 -0
  254. package/template/.aioson/skills/process/secure-tdd/references/node-express.md +91 -0
  255. package/template/.aioson/skills/process/secure-tdd/references/planned-stacks.md +33 -0
  256. package/template/.aioson/skills/static/harness-validate/SKILL.md +46 -0
  257. package/template/.aioson/skills/static/landing-page-deploy.md +192 -0
  258. package/template/.aioson/skills/static/landing-page-forge.md +730 -0
  259. package/template/.aioson/skills/static/ui-ux-modern.md +1 -0
  260. package/template/.aioson/skills/static/web-research-cache.md +3 -0
  261. package/template/.aioson/tasks/squad-create.md +56 -7
  262. package/template/.aioson/tasks/squad-design.md +80 -2
  263. package/template/.aioson/tasks/squad-investigate.md +14 -1
  264. package/template/.aioson/templates/squads/digital-marketing-agency/template.json +96 -0
  265. package/template/.claude/commands/aioson/agent/committer.md +5 -0
  266. package/template/.claude/commands/aioson/agent/copywriter.md +5 -0
  267. package/template/.claude/commands/aioson/agent/cypher.md +5 -0
  268. package/template/.claude/commands/aioson/agent/pair.md +5 -0
  269. package/template/.claude/commands/aioson/agent/validator.md +5 -0
  270. package/template/.gemini/commands/aios-analyst.toml +6 -3
  271. package/template/.gemini/commands/aios-architect.toml +7 -6
  272. package/template/.gemini/commands/aios-committer.toml +7 -0
  273. package/template/.gemini/commands/aios-copywriter.toml +7 -0
  274. package/template/.gemini/commands/aios-cypher.toml +7 -0
  275. package/template/.gemini/commands/aios-dev.toml +8 -7
  276. package/template/.gemini/commands/aios-deyvin.toml +6 -5
  277. package/template/.gemini/commands/aios-discovery-design-doc.toml +6 -3
  278. package/template/.gemini/commands/aios-genome.toml +7 -0
  279. package/template/.gemini/commands/aios-neo.toml +5 -3
  280. package/template/.gemini/commands/aios-orache.toml +7 -0
  281. package/template/.gemini/commands/aios-orchestrator.toml +8 -7
  282. package/template/.gemini/commands/aios-pair.toml +6 -5
  283. package/template/.gemini/commands/aios-pm.toml +8 -7
  284. package/template/.gemini/commands/aios-product.toml +5 -3
  285. package/template/.gemini/commands/aios-qa.toml +6 -5
  286. package/template/.gemini/commands/aios-setup.toml +5 -2
  287. package/template/.gemini/commands/aios-sheldon.toml +7 -0
  288. package/template/.gemini/commands/aios-site-forge.toml +7 -0
  289. package/template/.gemini/commands/aios-squad.toml +7 -0
  290. package/template/.gemini/commands/aios-tester.toml +6 -5
  291. package/template/.gemini/commands/aios-ux-ui.toml +8 -7
  292. package/template/.gemini/commands/aios-validator.toml +7 -0
  293. package/template/AGENTS.md +12 -1
  294. package/template/CLAUDE.md +6 -1
  295. package/template/.aioson/locales/en/agents/analyst.md +0 -244
  296. package/template/.aioson/locales/en/agents/architect.md +0 -245
  297. package/template/.aioson/locales/en/agents/dev.md +0 -397
  298. package/template/.aioson/locales/en/agents/deyvin.md +0 -137
  299. package/template/.aioson/locales/en/agents/discovery-design-doc.md +0 -27
  300. package/template/.aioson/locales/en/agents/genome.md +0 -212
  301. package/template/.aioson/locales/en/agents/neo.md +0 -8
  302. package/template/.aioson/locales/en/agents/orache.md +0 -6
  303. package/template/.aioson/locales/en/agents/orchestrator.md +0 -189
  304. package/template/.aioson/locales/en/agents/pair.md +0 -5
  305. package/template/.aioson/locales/en/agents/pm.md +0 -84
  306. package/template/.aioson/locales/en/agents/product.md +0 -378
  307. package/template/.aioson/locales/en/agents/profiler-enricher.md +0 -5
  308. package/template/.aioson/locales/en/agents/profiler-forge.md +0 -5
  309. package/template/.aioson/locales/en/agents/profiler-researcher.md +0 -5
  310. package/template/.aioson/locales/en/agents/qa.md +0 -270
  311. package/template/.aioson/locales/en/agents/setup.md +0 -421
  312. package/template/.aioson/locales/en/agents/sheldon.md +0 -455
  313. package/template/.aioson/locales/en/agents/squad.md +0 -449
  314. package/template/.aioson/locales/en/agents/tester.md +0 -6
  315. package/template/.aioson/locales/en/agents/ux-ui.md +0 -668
  316. package/template/.aioson/locales/es/agents/analyst.md +0 -225
  317. package/template/.aioson/locales/es/agents/architect.md +0 -245
  318. package/template/.aioson/locales/es/agents/dev.md +0 -370
  319. package/template/.aioson/locales/es/agents/deyvin.md +0 -99
  320. package/template/.aioson/locales/es/agents/discovery-design-doc.md +0 -21
  321. package/template/.aioson/locales/es/agents/genome.md +0 -104
  322. package/template/.aioson/locales/es/agents/neo.md +0 -50
  323. package/template/.aioson/locales/es/agents/orache.md +0 -105
  324. package/template/.aioson/locales/es/agents/orchestrator.md +0 -194
  325. package/template/.aioson/locales/es/agents/pair.md +0 -7
  326. package/template/.aioson/locales/es/agents/pm.md +0 -90
  327. package/template/.aioson/locales/es/agents/product.md +0 -372
  328. package/template/.aioson/locales/es/agents/profiler-enricher.md +0 -7
  329. package/template/.aioson/locales/es/agents/profiler-forge.md +0 -7
  330. package/template/.aioson/locales/es/agents/profiler-researcher.md +0 -7
  331. package/template/.aioson/locales/es/agents/qa.md +0 -198
  332. package/template/.aioson/locales/es/agents/setup.md +0 -405
  333. package/template/.aioson/locales/es/agents/sheldon.md +0 -309
  334. package/template/.aioson/locales/es/agents/squad.md +0 -532
  335. package/template/.aioson/locales/es/agents/tester.md +0 -9
  336. package/template/.aioson/locales/es/agents/ux-ui.md +0 -212
  337. package/template/.aioson/locales/fr/agents/analyst.md +0 -225
  338. package/template/.aioson/locales/fr/agents/architect.md +0 -245
  339. package/template/.aioson/locales/fr/agents/dev.md +0 -370
  340. package/template/.aioson/locales/fr/agents/deyvin.md +0 -99
  341. package/template/.aioson/locales/fr/agents/discovery-design-doc.md +0 -21
  342. package/template/.aioson/locales/fr/agents/genome.md +0 -104
  343. package/template/.aioson/locales/fr/agents/neo.md +0 -50
  344. package/template/.aioson/locales/fr/agents/orache.md +0 -106
  345. package/template/.aioson/locales/fr/agents/orchestrator.md +0 -194
  346. package/template/.aioson/locales/fr/agents/pair.md +0 -7
  347. package/template/.aioson/locales/fr/agents/pm.md +0 -90
  348. package/template/.aioson/locales/fr/agents/product.md +0 -372
  349. package/template/.aioson/locales/fr/agents/profiler-enricher.md +0 -7
  350. package/template/.aioson/locales/fr/agents/profiler-forge.md +0 -7
  351. package/template/.aioson/locales/fr/agents/profiler-researcher.md +0 -7
  352. package/template/.aioson/locales/fr/agents/qa.md +0 -198
  353. package/template/.aioson/locales/fr/agents/setup.md +0 -405
  354. package/template/.aioson/locales/fr/agents/sheldon.md +0 -309
  355. package/template/.aioson/locales/fr/agents/squad.md +0 -532
  356. package/template/.aioson/locales/fr/agents/tester.md +0 -9
  357. package/template/.aioson/locales/fr/agents/ux-ui.md +0 -212
  358. package/template/.aioson/locales/pt-BR/agents/analyst.md +0 -319
  359. package/template/.aioson/locales/pt-BR/agents/architect.md +0 -284
  360. package/template/.aioson/locales/pt-BR/agents/dev.md +0 -483
  361. package/template/.aioson/locales/pt-BR/agents/deyvin.md +0 -184
  362. package/template/.aioson/locales/pt-BR/agents/discovery-design-doc.md +0 -198
  363. package/template/.aioson/locales/pt-BR/agents/genome.md +0 -297
  364. package/template/.aioson/locales/pt-BR/agents/neo.md +0 -208
  365. package/template/.aioson/locales/pt-BR/agents/orache.md +0 -137
  366. package/template/.aioson/locales/pt-BR/agents/orchestrator.md +0 -324
  367. package/template/.aioson/locales/pt-BR/agents/pair.md +0 -5
  368. package/template/.aioson/locales/pt-BR/agents/pm.md +0 -182
  369. package/template/.aioson/locales/pt-BR/agents/product.md +0 -466
  370. package/template/.aioson/locales/pt-BR/agents/profiler-enricher.md +0 -5
  371. package/template/.aioson/locales/pt-BR/agents/profiler-forge.md +0 -5
  372. package/template/.aioson/locales/pt-BR/agents/profiler-researcher.md +0 -5
  373. package/template/.aioson/locales/pt-BR/agents/qa.md +0 -300
  374. package/template/.aioson/locales/pt-BR/agents/setup.md +0 -533
  375. package/template/.aioson/locales/pt-BR/agents/sheldon.md +0 -323
  376. package/template/.aioson/locales/pt-BR/agents/squad.md +0 -1330
  377. package/template/.aioson/locales/pt-BR/agents/tester.md +0 -449
  378. package/template/.aioson/locales/pt-BR/agents/ux-ui.md +0 -669
  379. package/template/.aioson/skills/design-system/components/SKILL.md:Zone.Identifier +0 -0
  380. package/template/.aioson/skills/design-system/dashboards/SKILL.md:Zone.Identifier +0 -0
  381. package/template/.aioson/skills/design-system/foundations/SKILL.md:Zone.Identifier +0 -0
  382. package/template/.aioson/skills/design-system/motion/SKILL.md:Zone.Identifier +0 -0
  383. package/template/.aioson/skills/design-system/patterns/SKILL.md:Zone.Identifier +0 -0
@@ -1,113 +1,495 @@
1
1
  'use strict';
2
2
 
3
3
  /**
4
- * aioson workflow:execute — orchestrate the full agent workflow for a feature.
4
+ * aioson workflow:execute — unified runner shell on top of workflow:next.
5
5
  *
6
- * Uses agent:prompt, gate:check, pulse:update, feature:close as building blocks.
7
- * Always supports --dry-run to preview the plan without executing.
8
- *
9
- * Usage:
10
- * aioson workflow:execute . --feature=checkout --tool=claude --dry-run
11
- * aioson workflow:execute . --feature=checkout --tool=claude
12
- * aioson workflow:execute . --feature=checkout --tool=claude --start-from=dev
13
- * aioson workflow:execute . --feature=checkout --json --dry-run
6
+ * Dry-run previews the next actionable steps using the real workflow state.
7
+ * Execution advances one or more valid checkpoints and writes a resumable snapshot.
14
8
  */
15
9
 
10
+ const fs = require('node:fs/promises');
16
11
  const path = require('node:path');
17
- const { execSync } = require('node:child_process');
18
12
  const {
19
13
  detectClassification,
20
14
  scanArtifacts,
21
15
  readPhaseGates
22
16
  } = require('../preflight-engine');
17
+ const {
18
+ readAutonomyProtocol,
19
+ getToolPolicy,
20
+ canRunHeadless,
21
+ resolveEffectiveMode
22
+ } = require('../autonomy-policy');
23
+ const { readAgentManifest } = require('../agent-manifests');
24
+ const { exists, ensureDir } = require('../utils');
25
+ const { validateHandoffContract } = require('../handoff-contract');
26
+ const { readHandoff, readHandoffProtocol } = require('../session-handoff');
27
+ const {
28
+ STATE_RELATIVE_PATH,
29
+ buildDefaultWorkflowConfig,
30
+ readWorkflowConfig,
31
+ runWorkflowNext
32
+ } = require('./workflow-next');
33
+ const { runWorkflowStatus } = require('./workflow-status');
34
+ const {
35
+ PARALLEL_RELATIVE_DIR,
36
+ collectWritePathConflicts,
37
+ extractStatusWritePathItems
38
+ } = require('../parallel-workspace');
23
39
 
24
40
  const BAR = '━'.repeat(45);
41
+ const EXECUTION_STATE_RELATIVE_PATH = '.aioson/context/workflow-execute.json';
42
+
43
+ const STEP_META = {
44
+ setup: { description: 'Initialize project context', gate_before: null, gate_after: null },
45
+ product: { description: 'Generate PRD', gate_before: null, gate_after: null },
46
+ analyst: { description: 'Map requirements + spec', gate_before: null, gate_after: 'A' },
47
+ architect: { description: 'Architecture design', gate_before: 'A', gate_after: 'B' },
48
+ 'ux-ui': { description: 'UI/UX design', gate_before: 'A', gate_after: 'B', optional: true },
49
+ pm: { description: 'Backlog + PM plan', gate_before: 'B', gate_after: 'C' },
50
+ orchestrator: { description: 'Coordinate execution lanes', gate_before: 'C', gate_after: null },
51
+ dev: { description: 'Implementation', gate_before: null, gate_after: 'C' },
52
+ qa: { description: 'QA + feature closure', gate_before: 'C', gate_after: 'D' },
53
+ committer: { description: 'Prepare commit', gate_before: 'D', gate_after: null }
54
+ };
25
55
 
26
- const WORKFLOW_BY_CLASSIFICATION = {
27
- MICRO: [
28
- { agent: 'dev', gate_before: null, gate_after: null, description: 'Direct implementation' }
29
- ],
30
- SMALL: [
31
- { agent: 'product', gate_before: null, gate_after: null, description: 'Generate PRD' },
32
- { agent: 'sheldon', gate_before: null, gate_after: null, description: 'Enrich PRD (recommended)', optional: true },
33
- { agent: 'analyst', gate_before: null, gate_after: 'A', description: 'Map requirements + spec' },
34
- { agent: 'dev', gate_before: 'A', gate_after: 'C', description: 'Implementation' },
35
- { agent: 'qa', gate_before: 'C', gate_after: 'D', description: 'QA + feature closure' }
36
- ],
37
- MEDIUM: [
38
- { agent: 'product', gate_before: null, gate_after: null, description: 'Generate PRD' },
39
- { agent: 'sheldon', gate_before: null, gate_after: null, description: 'Enrich PRD (required)', optional: false },
40
- { agent: 'analyst', gate_before: null, gate_after: 'A', description: 'Map requirements + spec' },
41
- { agent: 'architect', gate_before: 'A', gate_after: 'B', description: 'Architecture design' },
42
- { agent: 'ux-ui', gate_before: 'A', gate_after: 'B', description: 'UI/UX design', optional: true },
43
- { agent: 'pm', gate_before: 'B', gate_after: null, description: 'Backlog + PM plan' },
44
- { agent: 'dev', gate_before: 'C', gate_after: 'C', description: 'Implementation' },
45
- { agent: 'qa', gate_before: 'C', gate_after: 'D', description: 'QA + feature closure' }
46
- ]
56
+ const GATE_NAMES = {
57
+ A: 'requirements',
58
+ B: 'design',
59
+ C: 'plan',
60
+ D: 'execution'
47
61
  };
48
62
 
49
- const GATE_NAMES = { A: 'requirements', B: 'design', C: 'plan', D: 'execution' };
63
+ const GATE_RESPONSIBLE_AGENT = {
64
+ A: '@analyst',
65
+ B: '@architect',
66
+ C: '@pm (for MEDIUM) or @dev (for SMALL/MICRO)',
67
+ D: '@qa'
68
+ };
69
+
70
+ async function readJsonIfExists(filePath) {
71
+ if (!(await exists(filePath))) return null;
72
+ try {
73
+ const raw = await fs.readFile(filePath, 'utf8');
74
+ return JSON.parse(raw);
75
+ } catch {
76
+ return null;
77
+ }
78
+ }
79
+
80
+ async function writeJson(filePath, payload) {
81
+ await ensureDir(path.dirname(filePath));
82
+ await fs.writeFile(filePath, `${JSON.stringify(payload, null, 2)}\n`, 'utf8');
83
+ }
84
+
85
+ function normalizeClassification(value, fallback = 'SMALL') {
86
+ const safe = String(value || '').trim().toUpperCase();
87
+ return ['MICRO', 'SMALL', 'MEDIUM'].includes(safe) ? safe : fallback;
88
+ }
89
+
90
+ function normalizeAgentName(value) {
91
+ return String(value || '').trim().toLowerCase().replace(/^@/, '');
92
+ }
93
+
94
+ function findNextFromSequence(sequence, completed, skipped = []) {
95
+ const done = new Set([...(completed || []), ...(skipped || [])].map(normalizeAgentName));
96
+ return sequence.find((stage) => !done.has(normalizeAgentName(stage))) || null;
97
+ }
98
+
99
+ function getFocusStage(state) {
100
+ if (!state || typeof state !== 'object') return null;
101
+ return state.current || state.next || null;
102
+ }
103
+
104
+ function isGateApproved(gates, gateLetter) {
105
+ if (!gateLetter) return true;
106
+ const gateName = GATE_NAMES[gateLetter];
107
+ return gateName ? gates[gateName] === 'approved' : true;
108
+ }
109
+
110
+ async function resolveFeatureSequence(targetDir, classification) {
111
+ const fallback = buildDefaultWorkflowConfig();
112
+ try {
113
+ const { config } = await readWorkflowConfig(targetDir);
114
+ const sequence = config.feature && config.feature[classification];
115
+ return Array.isArray(sequence) && sequence.length > 0
116
+ ? [...sequence]
117
+ : [...(fallback.feature[classification] || fallback.feature.SMALL)];
118
+ } catch {
119
+ return [...(fallback.feature[classification] || fallback.feature.SMALL)];
120
+ }
121
+ }
122
+
123
+ function inferCompletedStagesFromArtifacts(sequence, artifacts, gates) {
124
+ const completed = [];
125
+
126
+ for (const stage of sequence) {
127
+ const normalized = normalizeAgentName(stage);
128
+ let inferred = false;
129
+
130
+ if (normalized === 'product') {
131
+ inferred = Boolean(artifacts.prd && artifacts.prd.exists);
132
+ } else if (normalized === 'analyst') {
133
+ inferred = Boolean(artifacts.requirements && artifacts.requirements.exists && gates.requirements === 'approved');
134
+ } else if (normalized === 'architect') {
135
+ inferred = Boolean(artifacts.architecture && artifacts.architecture.exists && gates.design === 'approved');
136
+ } else if (normalized === 'pm') {
137
+ inferred = Boolean(artifacts.implementation_plan && artifacts.implementation_plan.exists && gates.plan === 'approved');
138
+ } else if (normalized === 'qa') {
139
+ inferred = gates.execution === 'approved';
140
+ } else {
141
+ break;
142
+ }
143
+
144
+ if (!inferred) break;
145
+ completed.push(normalized);
146
+ }
147
+
148
+ return completed;
149
+ }
150
+
151
+ async function seedFeatureWorkflowState(targetDir, slug, classification, startFrom) {
152
+ const statePath = path.join(targetDir, STATE_RELATIVE_PATH);
153
+ const existing = await readJsonIfExists(statePath);
154
+ const focusStage = getFocusStage(existing);
155
+
156
+ if (
157
+ existing &&
158
+ existing.mode === 'feature' &&
159
+ existing.featureSlug &&
160
+ existing.featureSlug !== slug &&
161
+ focusStage
162
+ ) {
163
+ return {
164
+ ok: false,
165
+ reason: 'different_active_feature',
166
+ active_feature: existing.featureSlug,
167
+ active_stage: focusStage
168
+ };
169
+ }
170
+
171
+ if (existing && existing.mode === 'feature' && existing.featureSlug === slug) {
172
+ return {
173
+ ok: true,
174
+ resumed: true,
175
+ state: existing,
176
+ statePath: STATE_RELATIVE_PATH
177
+ };
178
+ }
50
179
 
51
- async function buildExecutionPlan(targetDir, slug, classification, startFrom) {
52
- const steps = WORKFLOW_BY_CLASSIFICATION[classification] || WORKFLOW_BY_CLASSIFICATION.SMALL;
53
180
  const artifacts = await scanArtifacts(targetDir, slug);
54
181
  const gates = await readPhaseGates(targetDir, slug);
182
+ const sequence = await resolveFeatureSequence(targetDir, classification);
183
+ const completed = inferCompletedStagesFromArtifacts(sequence, artifacts, gates);
184
+ const normalizedStartFrom = startFrom ? normalizeAgentName(startFrom) : null;
185
+
186
+ let skipped = [];
187
+ let next = findNextFromSequence(sequence, completed, skipped);
188
+
189
+ if (normalizedStartFrom && sequence.includes(normalizedStartFrom)) {
190
+ const targetIndex = sequence.indexOf(normalizedStartFrom);
191
+ skipped = sequence.slice(0, targetIndex).filter((stage) => !completed.includes(stage));
192
+ next = normalizedStartFrom;
193
+ }
194
+
195
+ const state = {
196
+ version: 1,
197
+ mode: 'feature',
198
+ classification,
199
+ sequence,
200
+ current: null,
201
+ next,
202
+ completed,
203
+ skipped,
204
+ featureSlug: slug,
205
+ detour: null,
206
+ updatedAt: new Date().toISOString()
207
+ };
55
208
 
56
- const plan = [];
57
- let stepNum = 1;
58
- let startFromReached = !startFrom;
209
+ await writeJson(statePath, state);
210
+ return {
211
+ ok: true,
212
+ resumed: false,
213
+ state,
214
+ statePath: STATE_RELATIVE_PATH
215
+ };
216
+ }
217
+
218
+ async function buildExecutionPlan(targetDir, slug, classification, workflowState = null, startFrom = null) {
219
+ const sequence = workflowState && Array.isArray(workflowState.sequence) && workflowState.sequence.length > 0
220
+ ? [...workflowState.sequence]
221
+ : await resolveFeatureSequence(targetDir, classification);
222
+ const artifacts = await scanArtifacts(targetDir, slug);
223
+ const gates = await readPhaseGates(targetDir, slug);
224
+ const normalizedStartFrom = startFrom ? normalizeAgentName(startFrom) : null;
225
+ const focusStage = getFocusStage(workflowState);
226
+ const inferredCompleted = inferCompletedStagesFromArtifacts(sequence, artifacts, gates);
227
+ const completedSet = new Set((workflowState && workflowState.completed) || inferredCompleted);
228
+ const skippedSet = new Set((workflowState && workflowState.skipped) || []);
229
+
230
+ const applyStartFrom = Boolean(
231
+ normalizedStartFrom &&
232
+ sequence.includes(normalizedStartFrom) &&
233
+ (!workflowState || (!workflowState.current && workflowState.next === normalizedStartFrom))
234
+ );
235
+
236
+ const scopedSequence = applyStartFrom
237
+ ? sequence.slice(sequence.indexOf(normalizedStartFrom)).filter(Boolean)
238
+ : sequence;
239
+
240
+ const steps = [];
241
+ for (const [index, agent] of scopedSequence.entries()) {
242
+ const meta = STEP_META[agent] || {
243
+ description: `Execute @${agent}`,
244
+ gate_before: null,
245
+ gate_after: null,
246
+ optional: false
247
+ };
59
248
 
60
- for (const step of steps) {
61
- if (startFrom && !startFromReached) {
62
- if (step.agent === startFrom) startFromReached = true;
63
- else continue;
249
+ let status = 'pending';
250
+ if (completedSet.has(agent)) status = 'completed';
251
+ else if (skippedSet.has(agent)) status = 'skipped';
252
+ else if (focusStage === agent) status = 'active';
253
+
254
+ const predictedBlockers = [];
255
+ if (status !== 'completed' && status !== 'skipped' && meta.gate_before && !isGateApproved(gates, meta.gate_before)) {
256
+ const responsible = GATE_RESPONSIBLE_AGENT[meta.gate_before] || 'previous agent';
257
+ const featureArg = slug ? ` --feature=${slug}` : '';
258
+ predictedBlockers.push(
259
+ `Gate ${meta.gate_before} (${GATE_NAMES[meta.gate_before] || meta.gate_before}) not approved — ` +
260
+ `responsible: ${responsible} — ` +
261
+ `approve with: aioson gate:approve .${featureArg} --gate=${meta.gate_before}`
262
+ );
263
+ if (status === 'pending') status = 'blocked';
64
264
  }
65
265
 
66
- // Determine if step can be skipped (artifact already exists)
67
- let skip = false;
68
- let skipReason = null;
69
-
70
- if (step.agent === 'product' && artifacts.prd.exists) {
71
- skip = true; skipReason = 'prd already exists';
72
- } else if (step.agent === 'sheldon' && artifacts.sheldon_enrichment.exists) {
73
- skip = true; skipReason = 'sheldon enrichment already exists';
74
- } else if (step.agent === 'analyst' && artifacts.requirements.exists && gates.requirements === 'approved') {
75
- skip = true; skipReason = 'requirements + Gate A already approved';
76
- } else if (step.agent === 'architect' && artifacts.architecture.exists && gates.design === 'approved') {
77
- skip = true; skipReason = 'architecture + Gate B already approved';
266
+ if (status === 'active' && workflowState) {
267
+ const contractCheck = await validateHandoffContract(targetDir, workflowState, agent);
268
+ if (!contractCheck.ok) {
269
+ predictedBlockers.push(...contractCheck.missing);
270
+ }
78
271
  }
79
272
 
80
- plan.push({
81
- step: stepNum++,
82
- agent: step.agent,
83
- description: step.description,
84
- gate_before: step.gate_before,
85
- gate_after: step.gate_after,
86
- optional: step.optional || false,
273
+ const skip = status === 'skipped' || (
274
+ status === 'completed' &&
275
+ inferredCompleted.includes(agent)
276
+ );
277
+ const skipReason = status === 'skipped'
278
+ ? 'workflow state marks this stage as skipped'
279
+ : skip
280
+ ? 'artifacts already satisfy this stage'
281
+ : null;
282
+
283
+ steps.push({
284
+ step: index + 1,
285
+ agent,
286
+ description: meta.description,
287
+ gate_before: meta.gate_before,
288
+ gate_after: meta.gate_after,
289
+ optional: Boolean(meta.optional),
290
+ status,
87
291
  skip,
88
- skip_reason: skipReason
292
+ skip_reason: skipReason,
293
+ predicted_blockers: predictedBlockers
89
294
  });
90
295
  }
91
296
 
92
- return plan;
297
+ return {
298
+ steps,
299
+ artifacts,
300
+ gates,
301
+ sequence
302
+ };
303
+ }
304
+
305
+ function buildCheckpointPayload(activation, handoff, handoffProtocol) {
306
+ const safeActivation = activation && typeof activation === 'object' ? activation : {};
307
+ return {
308
+ active_stage: safeActivation.agent || null,
309
+ current: safeActivation.current || null,
310
+ next: safeActivation.next || null,
311
+ effective_mode: safeActivation.effectiveMode || null,
312
+ instruction_path: safeActivation.instructionPath || null,
313
+ prompt: safeActivation.prompt || null,
314
+ handoff,
315
+ handoff_protocol: handoffProtocol
316
+ };
317
+ }
318
+
319
+ async function writeExecutionCheckpoint(targetDir, payload) {
320
+ const execPath = path.join(targetDir, EXECUTION_STATE_RELATIVE_PATH);
321
+ const existing = await readJsonIfExists(execPath);
322
+ const history = Array.isArray(existing && existing.history) ? [...existing.history] : [];
323
+ if (payload.checkpoint) {
324
+ history.push({
325
+ at: new Date().toISOString(),
326
+ active_stage: payload.checkpoint.active_stage || null,
327
+ next: payload.checkpoint.next || null,
328
+ effective_mode: payload.checkpoint.effective_mode || null,
329
+ handoff_to: payload.checkpoint.handoff && payload.checkpoint.handoff.next_agent
330
+ ? String(payload.checkpoint.handoff.next_agent).replace(/^@/, '')
331
+ : null
332
+ });
333
+ }
334
+ const nextPayload = {
335
+ version: 1,
336
+ feature: payload.feature,
337
+ classification: payload.classification,
338
+ tool: payload.tool,
339
+ requested_mode: payload.requestedMode || null,
340
+ status: payload.status,
341
+ started_at: existing && existing.feature === payload.feature ? existing.started_at : new Date().toISOString(),
342
+ updated_at: new Date().toISOString(),
343
+ resumed_count: existing && existing.feature === payload.feature ? Number(existing.resumed_count || 0) + (payload.resumed ? 1 : 0) : (payload.resumed ? 1 : 0),
344
+ workflow_state_path: STATE_RELATIVE_PATH,
345
+ checkpoint: payload.checkpoint || null,
346
+ status_snapshot: payload.statusSnapshot || null,
347
+ suggestion: payload.suggestion || null,
348
+ resume_command: payload.resumeCommand || null,
349
+ history
350
+ };
351
+ await writeJson(execPath, nextPayload);
352
+ return nextPayload;
353
+ }
354
+
355
+ async function readStatusSnapshot(targetDir, tool, t) {
356
+ return runWorkflowStatus({
357
+ args: [targetDir],
358
+ options: { json: true, tool },
359
+ logger: { log() {}, error() {} },
360
+ t
361
+ });
362
+ }
363
+
364
+ function parseLaneStatusIndex(fileName) {
365
+ const match = String(fileName || '').match(/^agent-(\d+)\.status\.md$/);
366
+ if (!match) return null;
367
+ const value = Number(match[1]);
368
+ if (!Number.isFinite(value) || value <= 0) return null;
369
+ return Math.floor(value);
370
+ }
371
+
372
+ async function readLaneWritePaths(parallelDir, index) {
373
+ const absPath = path.join(parallelDir, `agent-${index}.status.md`);
374
+ try {
375
+ const content = await fs.readFile(absPath, 'utf8');
376
+ return { lane: index, writePathItems: extractStatusWritePathItems(content) };
377
+ } catch {
378
+ return { lane: index, writePathItems: [] };
379
+ }
93
380
  }
94
381
 
95
- function runCommand(cmd) {
382
+ async function runLaneGuardPreflight(targetDir, laneIndex) {
383
+ const parallelDir = path.join(targetDir, PARALLEL_RELATIVE_DIR);
384
+ if (!(await exists(parallelDir))) {
385
+ return { ok: true, skipped: true, reason: 'no_parallel_workspace' };
386
+ }
387
+
388
+ let entries;
96
389
  try {
97
- execSync(cmd, { stdio: 'inherit' });
98
- return { ok: true };
99
- } catch (err) {
100
- return { ok: false, error: err.message };
390
+ entries = await fs.readdir(parallelDir);
391
+ } catch {
392
+ return { ok: true, skipped: true, reason: 'parallel_dir_unreadable' };
393
+ }
394
+
395
+ const laneIndices = entries
396
+ .map(parseLaneStatusIndex)
397
+ .filter((v) => v !== null)
398
+ .sort((a, b) => a - b);
399
+
400
+ if (!laneIndices.includes(laneIndex)) {
401
+ return { ok: false, skipped: false, reason: 'lane_not_found', lane: laneIndex };
402
+ }
403
+
404
+ const lanes = await Promise.all(laneIndices.map((i) => readLaneWritePaths(parallelDir, i)));
405
+ const conflictReport = collectWritePathConflicts(lanes);
406
+ const laneConflicts = conflictReport.conflicts.filter((c) =>
407
+ Array.isArray(c.lanes) && c.lanes.includes(laneIndex)
408
+ );
409
+ const targetLane = lanes.find((l) => l.lane === laneIndex);
410
+ const writePathCount = targetLane ? targetLane.writePathItems.length : 0;
411
+ const unassigned = writePathCount === 0;
412
+
413
+ return {
414
+ ok: laneConflicts.length === 0 && !unassigned,
415
+ skipped: false,
416
+ lane: laneIndex,
417
+ writePathCount,
418
+ unassigned,
419
+ conflictCount: laneConflicts.length,
420
+ conflicts: laneConflicts,
421
+ invalidCount: conflictReport.invalidCount,
422
+ invalidPatterns: conflictReport.invalidPatterns
423
+ };
424
+ }
425
+
426
+ async function performRunnerTransition(targetDir, suggestion, tool, requestedMode, logger, t) {
427
+ if (!suggestion || !suggestion.action) {
428
+ return { ok: false, reason: 'missing_suggestion' };
429
+ }
430
+
431
+ if (suggestion.action === 'workflow_complete') {
432
+ return { ok: true, transition: 'complete', result: null };
433
+ }
434
+
435
+ if (suggestion.action === 'activate_stage' || suggestion.action === 'continue_stage') {
436
+ const result = await runWorkflowNext({
437
+ args: [targetDir],
438
+ options: {
439
+ tool,
440
+ ...(requestedMode ? { mode: requestedMode } : {}),
441
+ ...(suggestion.agent ? { agent: suggestion.agent } : {})
442
+ },
443
+ logger,
444
+ t
445
+ });
446
+ return {
447
+ ok: true,
448
+ transition: 'activate',
449
+ agent: suggestion.agent || null,
450
+ result
451
+ };
452
+ }
453
+
454
+ if (suggestion.action === 'complete_stage' && suggestion.agent) {
455
+ const safeAgent = normalizeAgentName(suggestion.agent);
456
+ const result = await runWorkflowNext({
457
+ args: [targetDir],
458
+ options: {
459
+ tool,
460
+ complete: safeAgent,
461
+ ...(requestedMode ? { mode: requestedMode } : {}),
462
+ ...((safeAgent === 'dev' || safeAgent === 'qa') ? { 'auto-heal': true } : {})
463
+ },
464
+ logger,
465
+ t
466
+ });
467
+ return {
468
+ ok: true,
469
+ transition: 'complete',
470
+ agent: safeAgent,
471
+ result
472
+ };
101
473
  }
474
+
475
+ return { ok: false, reason: 'unsupported_suggestion_action', action: suggestion.action };
102
476
  }
103
477
 
104
478
  async function runWorkflowExecute({ args, options = {}, logger }) {
105
479
  const targetDir = path.resolve(process.cwd(), args[0] || '.');
106
- const slug = options.feature ? String(options.feature) : null;
107
- const tool = options.tool ? String(options.tool) : 'claude';
480
+ const slug = options.feature ? String(options.feature).trim() : null;
481
+ const tool = options.tool ? String(options.tool).trim() : 'claude';
482
+ const requestedMode = options.mode ? String(options.mode).trim() : null;
108
483
  const dryRun = Boolean(options['dry-run'] || options.dry);
109
- const startFrom = options['start-from'] ? String(options['start-from']) : null;
484
+ const startFrom = options['start-from'] ? String(options['start-from']).trim() : null;
110
485
  const skipOptional = Boolean(options['skip-optional']);
486
+ const parsedMaxCheckpoints = Number.parseInt(String(options['max-checkpoints'] || '1'), 10);
487
+ const maxCheckpoints = Number.isInteger(parsedMaxCheckpoints) && parsedMaxCheckpoints > 0
488
+ ? parsedMaxCheckpoints
489
+ : 1;
490
+ const parsedLane = options.lane !== undefined ? Number(options.lane) : null;
491
+ const laneIndex = Number.isInteger(parsedLane) && parsedLane > 0 ? parsedLane : null;
492
+ const t = (key, payload) => payload?.agent || payload?.stage || key;
111
493
 
112
494
  if (!slug) {
113
495
  if (options.json) return { ok: false, reason: 'missing_feature' };
@@ -116,22 +498,89 @@ async function runWorkflowExecute({ args, options = {}, logger }) {
116
498
  }
117
499
 
118
500
  let classification = await detectClassification(targetDir, slug);
119
- if (!classification) classification = options.classification ? String(options.classification).toUpperCase() : 'SMALL';
501
+ if (!classification) {
502
+ classification = options.classification ? String(options.classification).toUpperCase() : 'SMALL';
503
+ }
504
+ classification = normalizeClassification(classification, 'SMALL');
505
+
506
+ const autonomyProtocol = await readAutonomyProtocol(targetDir);
507
+ const toolPolicy = getToolPolicy(autonomyProtocol, tool);
508
+ if (requestedMode === 'headless' && !canRunHeadless(toolPolicy)) {
509
+ const failure = { ok: false, reason: 'headless_not_supported', tool };
510
+ if (options.json) return failure;
511
+ logger.error(`Tool ${tool} does not support headless mode. Fallback required.`);
512
+ return failure;
513
+ }
120
514
 
121
- const plan = await buildExecutionPlan(targetDir, slug, classification, startFrom);
122
- const activePlan = plan.filter((s) => !s.skip && !(skipOptional && s.optional));
123
- const skippedPlan = plan.filter((s) => s.skip);
515
+ const parallelGuard = laneIndex !== null
516
+ ? await runLaneGuardPreflight(targetDir, laneIndex)
517
+ : null;
124
518
 
125
- if (dryRun || options.json) {
519
+ if (parallelGuard && !parallelGuard.ok && !parallelGuard.skipped) {
520
+ if (parallelGuard.reason === 'lane_not_found') {
521
+ const failure = { ok: false, reason: 'parallel_lane_not_found', lane: laneIndex };
522
+ if (options.json) return failure;
523
+ logger.error(`Lane ${laneIndex} not found in parallel workspace.`);
524
+ return failure;
525
+ }
526
+ if (parallelGuard.conflictCount > 0) {
527
+ logger.error(
528
+ `[parallel:guard] Lane ${laneIndex} has ${parallelGuard.conflictCount} write-scope conflict(s) with other lanes. Proceeding with warning.`
529
+ );
530
+ }
531
+ if (parallelGuard.unassigned) {
532
+ logger.error(
533
+ `[parallel:guard] Lane ${laneIndex} has no write paths declared. Run parallel:assign before executing.`
534
+ );
535
+ }
536
+ }
537
+
538
+ const seeded = await seedFeatureWorkflowState(targetDir, slug, classification, startFrom);
539
+ if (!seeded.ok) {
540
+ if (options.json) return seeded;
541
+ logger.error(
542
+ `Another active feature workflow is in progress: ${seeded.active_feature} (@${seeded.active_stage}).`
543
+ );
544
+ return seeded;
545
+ }
546
+
547
+ const planData = await buildExecutionPlan(targetDir, slug, classification, seeded.state, startFrom);
548
+ for (const step of planData.steps) {
549
+ const manifest = await readAgentManifest(targetDir, step.agent);
550
+ step.effective_mode = resolveEffectiveMode({
551
+ protocol: autonomyProtocol,
552
+ tool,
553
+ agentId: step.agent,
554
+ manifest,
555
+ requestedMode
556
+ });
557
+ }
558
+
559
+ const activePlan = planData.steps.filter((step) => step.status !== 'completed' && !(skipOptional && step.optional));
560
+ const blockedSteps = planData.steps.filter((step) => step.predicted_blockers.length > 0);
561
+ const statusSnapshot = await readStatusSnapshot(targetDir, tool, t);
562
+ const resumeCommand = `aioson workflow:execute ${targetDir} --feature=${slug} --tool=${tool}${requestedMode ? ` --mode=${requestedMode}` : ''}${maxCheckpoints !== 1 ? ` --max-checkpoints=${maxCheckpoints}` : ''}`;
563
+
564
+ if (dryRun) {
126
565
  const result = {
127
566
  ok: true,
128
567
  feature: slug,
129
568
  classification,
130
569
  tool,
570
+ requested_mode: requestedMode,
131
571
  dry_run: true,
132
- steps: plan,
572
+ resumed: seeded.resumed,
573
+ state_path: seeded.statePath,
574
+ execution_state_path: EXECUTION_STATE_RELATIVE_PATH,
575
+ max_checkpoints: maxCheckpoints,
576
+ steps: planData.steps,
133
577
  active_steps: activePlan.length,
134
- skipped_steps: skippedPlan.length
578
+ blocked_steps: blockedSteps.length,
579
+ gates: planData.gates,
580
+ status_snapshot: statusSnapshot,
581
+ suggestion: statusSnapshot && statusSnapshot.suggestion ? statusSnapshot.suggestion : null,
582
+ resume_command: resumeCommand,
583
+ parallel_guard: parallelGuard
135
584
  };
136
585
 
137
586
  if (options.json) return result;
@@ -139,103 +588,143 @@ async function runWorkflowExecute({ args, options = {}, logger }) {
139
588
  logger.log('');
140
589
  logger.log(`Workflow Execution Plan — ${slug} (${classification})`);
141
590
  logger.log(BAR);
142
-
143
- for (const step of plan) {
144
- const icon = step.skip ? '○ (skip)' : `Step ${step.step}:`;
145
- const optional = step.optional ? ' (optional)' : '';
146
- const gateInfo = step.gate_after ? ` → Gate ${step.gate_after} check` : '';
147
- const skipInfo = step.skip ? ` — ${step.skip_reason}` : '';
148
- logger.log(`${icon} @${step.agent}${optional} ${step.description}${gateInfo}${skipInfo}`);
591
+ for (const step of planData.steps) {
592
+ const gateInfo = step.gate_after ? ` → Gate ${step.gate_after}` : '';
593
+ const statusInfo = `[${step.status}]`;
594
+ const modeInfo = step.effective_mode ? ` [mode=${step.effective_mode}]` : '';
595
+ logger.log(`Step ${step.step}: @${step.agent} ${statusInfo} ${step.description}${gateInfo}${modeInfo}`);
596
+ for (const blocker of step.predicted_blockers) {
597
+ logger.log(` - blocker: ${blocker}`);
598
+ }
149
599
  }
150
-
151
600
  logger.log('');
152
- logger.log(`Gates enforced: ${plan.filter((s) => s.gate_after && !s.skip).map((s) => s.gate_after).join(', ') || 'none'}`);
153
- logger.log(`Active sessions: ${activePlan.length} | Skipped: ${skippedPlan.length}`);
154
- logger.log('');
155
- logger.log('Run without --dry-run to execute.');
601
+ logger.log(`Blocked steps: ${blockedSteps.length} | Remaining: ${activePlan.length}`);
602
+ logger.log(`Resume state: ${seeded.resumed ? 'existing workflow state reused' : 'new workflow state seeded'}`);
603
+ if (statusSnapshot && statusSnapshot.suggestion && statusSnapshot.suggestion.command) {
604
+ logger.log(`Suggested command: ${statusSnapshot.suggestion.command}`);
605
+ }
156
606
  logger.log('');
157
-
158
607
  return result;
159
608
  }
160
609
 
161
- // Execute
162
- logger.log('');
163
- logger.log(`Workflow Execution ${slug} (${classification})`);
164
- logger.log(BAR);
165
-
166
- let completed = 0;
167
- let failed = 0;
168
- const executionLog = [];
169
-
170
- for (const step of plan) {
171
- if (step.skip) {
172
- logger.log(`[skip] @${step.agent} — ${step.skip_reason}`);
173
- executionLog.push({ step: step.step, agent: step.agent, status: 'skipped', reason: step.skip_reason });
174
- continue;
610
+ const executionTransitions = [];
611
+ let activation = null;
612
+ let currentStatus = statusSnapshot;
613
+
614
+ for (let index = 0; index < maxCheckpoints; index += 1) {
615
+ const suggestion = currentStatus && currentStatus.suggestion ? currentStatus.suggestion : null;
616
+ let transitionResult;
617
+
618
+ try {
619
+ transitionResult = await performRunnerTransition(
620
+ targetDir,
621
+ suggestion,
622
+ tool,
623
+ requestedMode,
624
+ logger,
625
+ t
626
+ );
627
+ } catch (error) {
628
+ const failure = {
629
+ ok: false,
630
+ reason: 'workflow_next_failed',
631
+ feature: slug,
632
+ classification,
633
+ message: error.message,
634
+ transitions: executionTransitions
635
+ };
636
+ if (options.json) return failure;
637
+ logger.error(error.message);
638
+ return failure;
175
639
  }
176
640
 
177
- if (skipOptional && step.optional) {
178
- logger.log(`[skip] @${step.agent} optional, skipped`);
179
- executionLog.push({ step: step.step, agent: step.agent, status: 'skipped', reason: 'optional' });
180
- continue;
641
+ if (!transitionResult.ok) {
642
+ const failure = {
643
+ ok: false,
644
+ reason: transitionResult.reason || 'runner_transition_failed',
645
+ feature: slug,
646
+ classification,
647
+ transitions: executionTransitions
648
+ };
649
+ if (options.json) return failure;
650
+ logger.error(`Runner transition failed: ${failure.reason}`);
651
+ return failure;
181
652
  }
182
653
 
183
- // Gate check before
184
- if (step.gate_before) {
185
- logger.log(`[Gate ${step.gate_before} check] pre-step ${step.step}...`);
186
- const gateCmd = `aioson gate:check ${targetDir} --feature=${slug} --gate=${step.gate_before}`;
187
- const gateResult = runCommand(gateCmd);
188
- if (!gateResult.ok) {
189
- logger.log(`[Gate ${step.gate_before}] BLOCKED — cannot proceed with @${step.agent}`);
190
- executionLog.push({ step: step.step, agent: step.agent, status: 'blocked', gate: step.gate_before });
191
- failed++;
192
- break;
193
- }
194
- }
195
-
196
- logger.log(`[Step ${step.step}/${activePlan.length}] @${step.agent} — ${step.description}...`);
197
- const agentCmd = `aioson agent:prompt ${targetDir} --agent=${step.agent} --feature=${slug} --tool=${tool}`;
198
- const agentResult = runCommand(agentCmd);
199
-
200
- if (!agentResult.ok) {
201
- logger.log(`[Step ${step.step}] @${step.agent} FAILED`);
202
- executionLog.push({ step: step.step, agent: step.agent, status: 'failed' });
203
- failed++;
654
+ if (transitionResult.transition === 'complete' && !transitionResult.result) {
204
655
  break;
205
656
  }
206
657
 
207
- // Gate check after
208
- if (step.gate_after) {
209
- logger.log(`[Gate ${step.gate_after} check] post-step ${step.step}...`);
210
- }
658
+ activation = transitionResult.result || activation;
659
+ executionTransitions.push({
660
+ index: index + 1,
661
+ transition: transitionResult.transition,
662
+ agent: transitionResult.agent || null,
663
+ active_stage: activation && activation.agent ? activation.agent : null,
664
+ next_stage: activation && activation.next ? activation.next : null,
665
+ completed_stage: activation && activation.completedStage ? activation.completedStage : null
666
+ });
211
667
 
212
- // Pulse update
213
- const pulseCmd = `aioson pulse:update ${targetDir} --agent=${step.agent} --feature=${slug} --action="${step.description}" 2>/dev/null || true`;
214
- runCommand(pulseCmd);
668
+ currentStatus = await readStatusSnapshot(targetDir, tool, t);
215
669
 
216
- executionLog.push({ step: step.step, agent: step.agent, status: 'completed' });
217
- completed++;
218
- logger.log(`[Step ${step.step}] @${step.agent} ✓`);
219
- }
220
-
221
- const allDone = completed === activePlan.length;
222
- if (allDone) {
223
- logger.log('');
224
- logger.log(`Workflow complete: ${slug} → done`);
225
- logger.log(`Total sessions: ${completed}`);
226
- } else {
227
- logger.log('');
228
- logger.log(`Workflow stopped: ${completed} completed, ${failed} failed.`);
670
+ const nextSuggestion = currentStatus && currentStatus.suggestion ? currentStatus.suggestion : null;
671
+ if (!nextSuggestion || nextSuggestion.action === 'continue_stage' || nextSuggestion.action === 'workflow_complete') {
672
+ break;
673
+ }
229
674
  }
230
675
 
231
- return {
232
- ok: allDone,
676
+ const handoff = await readHandoff(targetDir);
677
+ const handoffProtocol = await readHandoffProtocol(targetDir);
678
+ const refreshedStatus = currentStatus || await readStatusSnapshot(targetDir, tool, t);
679
+ const executionState = await writeExecutionCheckpoint(targetDir, {
233
680
  feature: slug,
234
681
  classification,
235
- completed,
236
- failed,
237
- execution_log: executionLog
682
+ tool,
683
+ requestedMode,
684
+ resumed: seeded.resumed,
685
+ status: activation && activation.agent ? 'active' : 'completed',
686
+ checkpoint: buildCheckpointPayload(activation, handoff, handoffProtocol),
687
+ statusSnapshot: refreshedStatus,
688
+ suggestion: refreshedStatus && refreshedStatus.suggestion ? refreshedStatus.suggestion : null,
689
+ resumeCommand
690
+ });
691
+
692
+ const result = {
693
+ ok: true,
694
+ feature: slug,
695
+ classification,
696
+ tool,
697
+ requested_mode: requestedMode,
698
+ resumed: seeded.resumed,
699
+ state_path: seeded.statePath,
700
+ execution_state_path: EXECUTION_STATE_RELATIVE_PATH,
701
+ max_checkpoints: maxCheckpoints,
702
+ checkpoint: executionState.checkpoint,
703
+ execution_state: executionState,
704
+ status_snapshot: refreshedStatus,
705
+ suggestion: refreshedStatus && refreshedStatus.suggestion ? refreshedStatus.suggestion : null,
706
+ resume_command: resumeCommand,
707
+ transitions: executionTransitions,
708
+ active_stage: activation && activation.agent ? activation.agent : null,
709
+ next_stage: activation && activation.next ? activation.next : null,
710
+ handoff,
711
+ handoff_protocol: handoffProtocol,
712
+ parallel_guard: parallelGuard
238
713
  };
714
+
715
+ if (!options.json) {
716
+ logger.log('');
717
+ logger.log(`Workflow checkpoint stored at ${EXECUTION_STATE_RELATIVE_PATH}`);
718
+ logger.log(`Feature: ${slug}`);
719
+ logger.log(`Resumed: ${seeded.resumed ? 'yes' : 'no'}`);
720
+ }
721
+
722
+ return result;
239
723
  }
240
724
 
241
- module.exports = { runWorkflowExecute };
725
+ module.exports = {
726
+ EXECUTION_STATE_RELATIVE_PATH,
727
+ buildExecutionPlan,
728
+ seedFeatureWorkflowState,
729
+ runWorkflowExecute
730
+ };