akm-cli 0.9.30 → 0.10.261001-beta

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 (384) hide show
  1. package/CHANGELOG.md +438 -0
  2. package/README.md +10 -10
  3. package/ROADMAP.md +112 -0
  4. package/STABILITY.md +99 -57
  5. package/dist/api-node.mjs +20 -0
  6. package/dist/api.d.ts +23 -0
  7. package/dist/api.js +45 -0
  8. package/dist/assets/hints/cli-hints-full.md +15 -29
  9. package/dist/assets/hints/cli-hints-short.md +2 -2
  10. package/dist/assets/improve-strategies/default.json +3 -3
  11. package/dist/assets/prompts/consolidate-pair.md +9 -7
  12. package/dist/assets/stash-skeleton/README.md +1 -1
  13. package/dist/assets/tasks/improve/akm-improve-consolidate.yml +1 -1
  14. package/dist/cli/shared.js +31 -48
  15. package/dist/cli/unknown-flags.js +6 -43
  16. package/dist/cli.js +8 -34
  17. package/dist/commands/agent/contribute-cli.js +1 -1
  18. package/dist/commands/completions.js +1 -2
  19. package/dist/commands/config-cli.js +5 -28
  20. package/dist/commands/env/env-cli.js +5 -5
  21. package/dist/commands/env/secret-cli.js +2 -2
  22. package/dist/commands/feedback-cli.js +75 -49
  23. package/dist/commands/health/checks.js +41 -16
  24. package/dist/commands/health/plugin-staleness.js +52 -22
  25. package/dist/commands/improve/autonomy-gate.js +5 -3
  26. package/dist/commands/improve/consolidate/chunking.js +3 -10
  27. package/dist/commands/improve/consolidate/continuity-check.js +4 -4
  28. package/dist/commands/improve/consolidate/pair-pass.js +29 -10
  29. package/dist/commands/improve/consolidate.js +10 -65
  30. package/dist/commands/improve/distill/lesson-update.js +91 -0
  31. package/dist/commands/improve/distill-guards.js +1 -43
  32. package/dist/commands/improve/distill.js +148 -21
  33. package/dist/commands/improve/eligibility.js +14 -1
  34. package/dist/commands/improve/extract-cli.js +1 -1
  35. package/dist/commands/improve/extract-prompt.js +17 -7
  36. package/dist/commands/improve/extract.js +5 -7
  37. package/dist/commands/improve/improve-cli.js +125 -118
  38. package/dist/commands/improve/improve-strategies.js +8 -12
  39. package/dist/commands/improve/improve.js +134 -52
  40. package/dist/commands/improve/loop-stages.js +18 -5
  41. package/dist/commands/improve/planner.js +0 -1
  42. package/dist/commands/improve/preparation.js +40 -99
  43. package/dist/commands/improve/proactive-maintenance.js +2 -2
  44. package/dist/commands/improve/reflect-noise.js +3 -55
  45. package/dist/commands/improve/reflect.js +29 -34
  46. package/dist/commands/improve/retrieval-queries.js +37 -0
  47. package/dist/commands/improve/retrieval-scope.js +2 -2
  48. package/dist/commands/improve/salience.js +2 -9
  49. package/dist/commands/improve/session-asset.js +4 -1
  50. package/dist/commands/improve/stage.js +23 -12
  51. package/dist/commands/lint/index.js +5 -20
  52. package/dist/commands/observability-cli.js +3 -9
  53. package/dist/commands/proposal/drain.js +43 -6
  54. package/dist/commands/proposal/proposal-cli.js +11 -31
  55. package/dist/commands/proposal/repository.js +20 -14
  56. package/dist/commands/proposal/validators/proposal-quality-validators.js +0 -3
  57. package/dist/commands/read/knowledge.js +3 -3
  58. package/dist/commands/read/remember-cli.js +0 -13
  59. package/dist/commands/read/search-cli.js +29 -97
  60. package/dist/commands/read/search.js +0 -11
  61. package/dist/commands/read/show.js +0 -19
  62. package/dist/commands/sources/plugin-upgrade.js +164 -101
  63. package/dist/commands/sources/sources-cli.js +1 -15
  64. package/dist/commands/sources/stash-cli.js +6 -14
  65. package/dist/commands/tasks/tasks-cli.js +4 -115
  66. package/dist/commands/workflow/plan.js +11 -33
  67. package/dist/commands/workflow-cli.js +2 -7
  68. package/dist/core/adapter/adapter-ids.js +1 -2
  69. package/dist/core/adapter/adapters/agent-skills-adapter.js +0 -4
  70. package/dist/core/adapter/adapters/akm-adapter.js +9 -48
  71. package/dist/core/adapter/adapters/akm-lint.js +10 -26
  72. package/dist/core/adapter/adapters/akm-metadata.js +2 -72
  73. package/dist/core/adapter/adapters/akm-task-adapter.js +0 -5
  74. package/dist/core/adapter/adapters/akm-workflow-adapter.js +9 -28
  75. package/dist/core/adapter/adapters/dotenv-adapter.js +1 -20
  76. package/dist/core/adapter/adapters/generic-files-adapter.js +0 -10
  77. package/dist/core/adapter/adapters/llm-wiki-adapter.js +0 -4
  78. package/dist/core/adapter/adapters/tool-dir-shared.js +0 -24
  79. package/dist/core/adapter/adapters/website-snapshot-adapter.js +4 -4
  80. package/dist/core/adapter/recognize-match.js +3 -4
  81. package/dist/core/common.js +18 -2
  82. package/dist/core/config/config-schema.js +12 -15
  83. package/dist/core/config/config-types.js +6 -15
  84. package/dist/core/config/config-walker.js +6 -23
  85. package/dist/core/config/config.js +17 -80
  86. package/dist/core/config/engine-semantics.js +7 -3
  87. package/dist/core/config/schema/engines.js +7 -7
  88. package/dist/core/config/schema/improve-processes.js +10 -63
  89. package/dist/core/config/schema/improve.js +2 -21
  90. package/dist/core/config/schema/index-config.js +6 -39
  91. package/dist/core/env-secret-ref.js +2 -45
  92. package/dist/core/errors.js +1 -2
  93. package/dist/core/extra-params.js +2 -86
  94. package/dist/core/file-lock.js +12 -7
  95. package/dist/core/improve-result.js +13 -1
  96. package/dist/core/mutation-target.js +2 -2
  97. package/dist/core/paths.js +4 -0
  98. package/dist/core/recognition-util.js +4 -5
  99. package/dist/core/run-lock.js +1 -1
  100. package/dist/core/subprocess.js +49 -0
  101. package/dist/core/warn.js +21 -4
  102. package/dist/core/write-source.js +3 -3
  103. package/dist/execution/target-ref.js +1 -2
  104. package/dist/indexer/indexer.js +15 -6
  105. package/dist/indexer/passes/memory-inference.js +15 -6
  106. package/dist/indexer/search/db-search.js +49 -36
  107. package/dist/indexer/search/fts-query.js +0 -19
  108. package/dist/indexer/search/ranking.js +29 -1
  109. package/dist/indexer/usage/usage-events.js +21 -16
  110. package/dist/integrations/agent/engine-resolution.js +5 -2
  111. package/dist/integrations/agent/index.js +1 -1
  112. package/dist/integrations/agent/profiles.js +41 -98
  113. package/dist/integrations/agent/request-lowering.js +3 -3
  114. package/dist/integrations/harnesses/aider/index.js +5 -0
  115. package/dist/integrations/harnesses/amazonq/index.js +1 -0
  116. package/dist/integrations/harnesses/claude/config-import.js +2 -3
  117. package/dist/integrations/harnesses/claude/index.js +5 -0
  118. package/dist/integrations/harnesses/codex/index.js +1 -0
  119. package/dist/integrations/harnesses/copilot/index.js +1 -0
  120. package/dist/integrations/harnesses/gemini/index.js +1 -0
  121. package/dist/integrations/harnesses/index.js +18 -39
  122. package/dist/integrations/harnesses/opencode/agent-builder.js +60 -35
  123. package/dist/integrations/harnesses/opencode/config-import.js +121 -52
  124. package/dist/integrations/harnesses/opencode/index.js +22 -0
  125. package/dist/integrations/harnesses/opencode/plugin-layout.js +68 -0
  126. package/dist/integrations/harnesses/opencode/session-log-types.js +12 -0
  127. package/dist/integrations/harnesses/opencode/session-log-v1.js +72 -0
  128. package/dist/integrations/harnesses/opencode/session-log-v2.js +140 -0
  129. package/dist/integrations/harnesses/opencode/session-log.js +104 -115
  130. package/dist/integrations/harnesses/opencode/version.js +98 -0
  131. package/dist/integrations/harnesses/opencode-sdk/{harness.js → index.js} +5 -17
  132. package/dist/integrations/harnesses/opencode-sdk/sdk-runner.js +105 -206
  133. package/dist/integrations/harnesses/opencode-sdk/v1-adapter.js +199 -0
  134. package/dist/integrations/harnesses/opencode-sdk/v2-adapter.js +254 -0
  135. package/dist/integrations/harnesses/opencode-sdk/wire.js +66 -0
  136. package/dist/integrations/harnesses/openhands/index.js +1 -0
  137. package/dist/integrations/harnesses/pi/index.js +1 -0
  138. package/dist/integrations/harnesses/shared.js +2 -0
  139. package/dist/integrations/harnesses/types.js +2 -0
  140. package/dist/llm/client.js +74 -14
  141. package/dist/output/cli-hints.js +1 -1
  142. package/dist/output/context.js +10 -19
  143. package/dist/output/format-exempt.js +5 -8
  144. package/dist/output/shapes/helpers.js +1 -22
  145. package/dist/output/shapes/passthrough.js +0 -1
  146. package/dist/output/shapes.js +3 -31
  147. package/dist/output/stdout.js +5 -1
  148. package/dist/output/text/command-format.js +6 -1
  149. package/dist/output/text/workflow-format.js +4 -22
  150. package/dist/scripts/akm-migrate-node.js +15769 -16731
  151. package/dist/scripts/akm-migrate.js +16339 -17297
  152. package/dist/setup/detect.js +10 -4
  153. package/dist/setup/harness-config-import.js +5 -14
  154. package/dist/setup/setup.js +1 -1
  155. package/dist/setup/steps/tasks.js +12 -13
  156. package/dist/sources/providers/git-stash.js +94 -13
  157. package/dist/storage/repositories/index-utility-repository.js +2 -32
  158. package/dist/storage/repositories/index-vec-repository.js +4 -0
  159. package/dist/storage/repositories/task-history-repository.js +0 -5
  160. package/dist/storage/repositories/workflow-runs-repository.js +5 -15
  161. package/dist/tasks/embedded.js +2 -1
  162. package/dist/tasks/run/run-command-task.js +9 -1
  163. package/dist/tasks/run/run-workflow-task.js +4 -3
  164. package/dist/tasks/run/task-history.js +0 -2
  165. package/dist/tasks/run/task-log.js +38 -1
  166. package/dist/tasks/schedule-gates.js +39 -0
  167. package/dist/tasks/scheduler-binding.js +0 -16
  168. package/dist/tasks/scheduler-sync.js +3 -97
  169. package/dist/tasks/source/bounded-document.js +1 -1
  170. package/dist/tasks/source/task-source-v4.js +2 -12
  171. package/dist/tasks/task-run-reserved-flags.js +2 -31
  172. package/dist/workflows/authoring/authoring.js +6 -6
  173. package/dist/workflows/compile.js +8 -65
  174. package/dist/workflows/exec/child-workflow.js +22 -3
  175. package/dist/workflows/exec/native-executor.js +12 -147
  176. package/dist/workflows/exec/run-workflow.js +31 -103
  177. package/dist/workflows/exec/step-work.js +9 -178
  178. package/dist/workflows/exec/unit-dispatch.js +0 -10
  179. package/dist/workflows/freeze/environment.js +3 -44
  180. package/dist/workflows/freeze/freeze.js +8 -41
  181. package/dist/workflows/freeze/targets/child-workflow.js +27 -63
  182. package/dist/workflows/freeze/targets/command.js +2 -16
  183. package/dist/workflows/freeze/targets/shell.js +0 -2
  184. package/dist/workflows/freeze/task-bindings.js +2 -28
  185. package/dist/workflows/ir/params.js +12 -2
  186. package/dist/workflows/parser.js +82 -232
  187. package/dist/workflows/plan.js +1 -1
  188. package/dist/workflows/renderer.js +10 -19
  189. package/dist/workflows/runtime/run-plan.js +11 -53
  190. package/dist/workflows/runtime/runs.js +4 -27
  191. package/dist/workflows/source-files.js +12 -16
  192. package/dist/workflows/source-semantics.js +1 -93
  193. package/docs/README.md +43 -42
  194. package/docs/agents/README.md +15 -0
  195. package/docs/agents/agent-install.md +14 -0
  196. package/docs/architecture/0.10-process-rules.md +827 -0
  197. package/docs/architecture/README.md +67 -0
  198. package/docs/architecture/adapters.md +258 -0
  199. package/docs/architecture/akm-architecture-decision-history.md +2055 -0
  200. package/docs/architecture/akm-core-principles.md +126 -0
  201. package/docs/architecture/architecture.md +578 -0
  202. package/docs/architecture/comparisons/claude-code-vs-akm-workflows-full.md +550 -0
  203. package/docs/architecture/decisions/0001-no-interpolation-attached-structured-context.md +72 -0
  204. package/docs/architecture/decisions/0002-unit-reuse-and-input-hash-scope.md +142 -0
  205. package/docs/architecture/decisions/0003-child-env-allowlist-and-provenance.md +189 -0
  206. package/docs/architecture/decisions/0004-task-input-contract-and-flag-coercion.md +97 -0
  207. package/docs/architecture/decisions/0005-task-result-vocabulary-and-legacy-read-mapping.md +108 -0
  208. package/docs/architecture/decisions/0006-task-source-version-routing.md +124 -0
  209. package/docs/architecture/decisions/0007-workflow-composition-bounds.md +83 -0
  210. package/docs/architecture/decisions/0008-task-binding-normalization.md +88 -0
  211. package/docs/architecture/decisions/0009-child-run-publication-column-parity.md +80 -0
  212. package/docs/architecture/decisions/0010-driver-protocol-cut.md +36 -0
  213. package/docs/architecture/decisions/0011-engine-run-loop-invariants.md +125 -0
  214. package/docs/architecture/decisions/README.md +62 -0
  215. package/docs/architecture/improvement.md +479 -0
  216. package/docs/architecture/internals/classification.md +154 -0
  217. package/docs/architecture/internals/fresh-host-rebuild-runbook.md +40 -0
  218. package/docs/architecture/internals/functional-contract-patterns.md +340 -0
  219. package/docs/architecture/internals/health-advisories.md +110 -0
  220. package/docs/architecture/internals/improve-workflow.md +719 -0
  221. package/docs/architecture/internals/indexing.md +498 -0
  222. package/docs/architecture/internals/registry-network-boundary.md +57 -0
  223. package/docs/architecture/internals/search.md +248 -0
  224. package/docs/architecture/internals/storage-locations.md +943 -0
  225. package/docs/architecture/persisted-data-compat.md +68 -0
  226. package/docs/architecture/reviews/env-secret-access.md +319 -0
  227. package/docs/architecture/runtime-boundary-design.md +153 -0
  228. package/docs/architecture/specs/0.9.0-close-out-plan.md +361 -0
  229. package/docs/architecture/specs/0.9.0-decisions.md +532 -0
  230. package/docs/architecture/specs/0.9.0-docs-code-drift-register.md +745 -0
  231. package/docs/architecture/specs/0.9.0-open-items-register.md +135 -0
  232. package/docs/architecture/specs/0.9.0-public-api-issue-backlog.md +740 -0
  233. package/docs/architecture/specs/0.9.0-release-surface-review.md +636 -0
  234. package/docs/architecture/specs/agent-command-engine-model-design.md +513 -0
  235. package/docs/architecture/specs/akm-0.9.0-bundle-adapter-spec.md +501 -0
  236. package/docs/architecture/specs/akm-0.9.0-ref-grammar-decision.md +291 -0
  237. package/docs/architecture/specs/akm-format-neutral-bundle-workspace-spec.md +2059 -0
  238. package/docs/architecture/specs/di-seams-plan.md +539 -0
  239. package/docs/architecture/specs/driver-protocol-keep-or-cut.md +275 -0
  240. package/docs/architecture/specs/fact-asset-type.md +142 -0
  241. package/docs/architecture/specs/improve-collapse-churn-detector-design.md +634 -0
  242. package/docs/architecture/specs/okf-support.md +148 -0
  243. package/docs/architecture/specs/ref.md +329 -0
  244. package/docs/architecture/specs/reviews/task-workflow-unification/README.md +72 -0
  245. package/docs/architecture/specs/reviews/task-workflow-unification/findings-consolidated.md +152 -0
  246. package/docs/architecture/specs/reviews/task-workflow-unification/library-eval-alternatives.md +352 -0
  247. package/docs/architecture/specs/reviews/task-workflow-unification/library-eval-bunqueue.md +300 -0
  248. package/docs/architecture/specs/reviews/task-workflow-unification/library-eval-openworkflow.md +402 -0
  249. package/docs/architecture/specs/reviews/task-workflow-unification/opus-review-1.md +758 -0
  250. package/docs/architecture/specs/reviews/task-workflow-unification/opus-review-2.md +645 -0
  251. package/docs/architecture/specs/reviews/task-workflow-unification/opus-review-3.md +602 -0
  252. package/docs/architecture/specs/reviews/task-workflow-unification/panel-r1-adversarial.md +27 -0
  253. package/docs/architecture/specs/reviews/task-workflow-unification/panel-r1-architecture.md +27 -0
  254. package/docs/architecture/specs/reviews/task-workflow-unification/panel-r1-coverage.md +74 -0
  255. package/docs/architecture/specs/reviews/task-workflow-unification/panel-r1-security.md +15 -0
  256. package/docs/architecture/specs/reviews/task-workflow-unification/panel-r2-adversarial.md +132 -0
  257. package/docs/architecture/specs/reviews/task-workflow-unification/panel-r2-verification.md +147 -0
  258. package/docs/architecture/specs/stash-conventions-code-spec.md +275 -0
  259. package/docs/architecture/specs/stash-organization-conventions.md +377 -0
  260. package/docs/architecture/specs/task-workflow-format-unification.md +721 -0
  261. package/docs/architecture/specs/workflow-engine-buy-vs-build.md +231 -0
  262. package/docs/architecture/specs/workflow-format-unification.md +432 -0
  263. package/docs/architecture/testing/manual-testing-checklist.md +3411 -0
  264. package/docs/architecture/testing/okf-v0.2-conformance-runbook.md +924 -0
  265. package/docs/architecture/testing/task-workflow-manual-tests.md +1720 -0
  266. package/docs/architecture/testing/testing-workflow.md +446 -0
  267. package/docs/architecture/workflow-engine.md +223 -0
  268. package/docs/guides/README.md +33 -0
  269. package/docs/guides/author-bundles.md +310 -0
  270. package/docs/guides/author-workflows.md +490 -0
  271. package/docs/guides/bundles.md +323 -0
  272. package/docs/guides/capture-knowledge.md +136 -0
  273. package/docs/guides/claude-code-vs-akm-workflows.md +29 -0
  274. package/docs/guides/concepts.md +93 -0
  275. package/docs/guides/discover-and-load.md +158 -0
  276. package/docs/guides/getting-started.md +240 -0
  277. package/docs/guides/improve-the-library.md +247 -0
  278. package/docs/guides/knowledge-management.md +18 -0
  279. package/docs/guides/recipes/headless-install.md +97 -0
  280. package/docs/guides/recipes/website-source.md +28 -0
  281. package/docs/guides/run-workflows.md +279 -0
  282. package/docs/guides/scheduling.md +131 -0
  283. package/docs/guides/use-with-any-agent.md +174 -0
  284. package/docs/guides/wikis.md +81 -0
  285. package/docs/integration/bundling-akm.md +7 -6
  286. package/docs/maintainers/README.md +19 -0
  287. package/docs/maintainers/curate-workmap.md +335 -0
  288. package/docs/maintainers/eval.md +3 -0
  289. package/docs/maintainers/local-development.md +108 -0
  290. package/docs/maintainers/release-checklist.md +135 -0
  291. package/docs/migration/README.md +4 -2
  292. package/docs/migration/release-notes/0.0.13.md +1 -1
  293. package/docs/migration/release-notes/0.1.0.md +1 -1
  294. package/docs/migration/release-notes/0.10.0.md +201 -0
  295. package/docs/migration/release-notes/0.2.0.md +1 -1
  296. package/docs/migration/release-notes/0.3.0.md +1 -1
  297. package/docs/migration/release-notes/0.5.0.md +1 -1
  298. package/docs/migration/release-notes/0.6.0.md +1 -1
  299. package/docs/migration/release-notes/0.7.0.md +1 -1
  300. package/docs/migration/release-notes/0.7.3.md +2 -2
  301. package/docs/migration/release-notes/0.7.4.md +1 -1
  302. package/docs/migration/release-notes/0.7.5.md +1 -1
  303. package/docs/migration/release-notes/0.8.0.md +1 -1
  304. package/docs/migration/release-notes/0.9.0.md +1 -1
  305. package/docs/migration/release-notes/0.9.14.md +1 -1
  306. package/docs/migration/release-notes/0.9.15.md +1 -1
  307. package/docs/migration/release-notes/0.9.16.md +1 -1
  308. package/docs/migration/release-notes/0.9.17.md +1 -1
  309. package/docs/migration/release-notes/0.9.19.md +1 -1
  310. package/docs/migration/release-notes/0.9.2.md +1 -1
  311. package/docs/migration/release-notes/README.md +28 -31
  312. package/docs/migration/v0.5-to-v0.6.md +759 -0
  313. package/docs/migration/v0.8-to-v0.9.md +1 -1
  314. package/docs/migration/v0.9-to-v0.10.md +507 -0
  315. package/docs/plans/0.9.2-agent-command-workflow-plan.md +423 -0
  316. package/docs/posts/README.md +30 -0
  317. package/docs/posts/akm-command-tour.md +495 -0
  318. package/docs/posts/akm-logo-sized.webp +0 -0
  319. package/docs/posts/belief-aware-memory-12.md +139 -0
  320. package/docs/posts/config-v2-lessons-16.md +191 -0
  321. package/docs/posts/improve-loop-autonomous-10.md +225 -0
  322. package/docs/posts/improve-pipeline-debugging-0803.md +179 -0
  323. package/docs/posts/intro-part-01.md +76 -0
  324. package/docs/posts/intro-part-02.md +221 -0
  325. package/docs/posts/intro-part-03.md +190 -0
  326. package/docs/posts/intro-part-04.md +221 -0
  327. package/docs/posts/llm-mode-reflect-13.md +166 -0
  328. package/docs/posts/openpalm-built-on-akm.md +86 -0
  329. package/docs/posts/progressive-disclosure-06.md +129 -0
  330. package/docs/posts/proposal-safety-net-15.md +112 -0
  331. package/docs/posts/release-0.5.0.md +247 -0
  332. package/docs/posts/release-0.6.0.md +117 -0
  333. package/docs/posts/release-0.7.0.md +159 -0
  334. package/docs/posts/release-0.8.0.md +332 -0
  335. package/docs/posts/scattered-skills-05.md +100 -0
  336. package/docs/posts/task-assets-persistent-workflows-11.md +222 -0
  337. package/docs/posts/team-skills-07.md +198 -0
  338. package/docs/posts/wiki-agent-knowledge-08.md +223 -0
  339. package/docs/posts/workflows-vaults-09.md +321 -0
  340. package/docs/product-surface.md +54 -0
  341. package/docs/reference/README.md +2 -2
  342. package/docs/reference/api.md +65 -0
  343. package/docs/reference/asset-types.md +166 -0
  344. package/docs/reference/bundle-types.md +2 -4
  345. package/docs/reference/cli.md +163 -192
  346. package/docs/reference/configuration.md +101 -20
  347. package/docs/reference/data-and-telemetry.md +2 -2
  348. package/docs/reference/env-and-secrets.md +126 -0
  349. package/docs/reference/memory.md +124 -0
  350. package/docs/reference/refs.md +156 -0
  351. package/docs/reference/registry.md +489 -0
  352. package/docs/reference/supported-formats.md +3 -4
  353. package/docs/reference/tasks.md +12 -19
  354. package/docs/reference/website-sources.md +141 -0
  355. package/docs/reference/workflow-schema.md +89 -317
  356. package/docs/reference/workflows.md +20 -48
  357. package/package.json +23 -16
  358. package/schemas/akm-config.json +2 -243
  359. package/schemas/akm-task.json +2 -3
  360. package/schemas/akm-workflow.json +47 -84
  361. package/dist/assets/improve-strategies/catchup.json +0 -41
  362. package/dist/assets/improve-strategies/proactive-maintenance.json +0 -24
  363. package/dist/assets/improve-strategies/quick.json +0 -17
  364. package/dist/assets/improve-strategies/reflect-distill.json +0 -29
  365. package/dist/assets/improve-strategies/thorough.json +0 -49
  366. package/dist/assets/prompts/retrieval-relevance-judge.md +0 -6
  367. package/dist/assets/tasks/improve/akm-improve-catchup.yml +0 -6
  368. package/dist/assets/tasks/improve/akm-improve-frequent.yml +0 -4
  369. package/dist/assets/tasks/improve/akm-improve-nightly.yml +0 -4
  370. package/dist/cli/retired-commands.js +0 -118
  371. package/dist/commands/improve/retrieval-gate.js +0 -132
  372. package/dist/commands/tasks/validate.js +0 -176
  373. package/dist/core/config/legacy-source-shape-shim.js +0 -117
  374. package/dist/indexer/feedback/utility-policy.js +0 -75
  375. package/dist/integrations/harnesses/ids.js +0 -28
  376. package/dist/tasks/source/task-source-v3-frozen.js +0 -424
  377. package/dist/tasks/source/task-to-v4.js +0 -863
  378. package/dist/workflows/exec/worktree.js +0 -372
  379. package/dist/workflows/freeze/child-output-references.js +0 -83
  380. package/dist/workflows/freeze/identity.js +0 -22
  381. package/dist/workflows/freeze/targets/script.js +0 -50
  382. package/dist/workflows/freeze/targets/task.js +0 -124
  383. package/dist/workflows/github-yaml.js +0 -506
  384. package/dist/workflows/runtime/run-outputs.js +0 -80
@@ -1,506 +0,0 @@
1
- // This Source Code Form is subject to the terms of the Mozilla Public
2
- // License, v. 2.0. If a copy of the MPL was not distributed with this
3
- // file, You can obtain one at https://mozilla.org/MPL/2.0/.
4
- /**
5
- * The GitHub-shaped YAML workflow grammar: a strict `name`/`on`/`jobs`
6
- * document with exactly one job, compiled straight to a {@link WorkflowPlan}.
7
- * It is an AKM workflow format executed by AKM's own engine, not GitHub
8
- * Actions: no expressions, no service events, `runs-on: [self-hosted]` only.
9
- */
10
- import { isAlias, isMap, isScalar, isSeq, LineCounter, parseDocument } from "yaml";
11
- import { WORKFLOW_PLAN_VERSION, } from "./plan.js";
12
- import { utf8Bytes, WORKFLOW_MAX_SOURCE_BYTES } from "./resource-limits.js";
13
- import { canonicalizeWorkflowCron, canonicalizeWorkflowRun, canonicalizeWorkflowWorkingDirectory, classifyWorkflowStepUses, validateWorkflowBuiltinCommand, WorkflowSourceSemanticError, workflowShellCommand, } from "./source-semantics.js";
14
- /** A located compile failure; `compile.ts` turns it into a `WorkflowSourceError`. */
15
- export class WorkflowSourceFailure extends Error {
16
- error;
17
- constructor(code, message, source) {
18
- super(message);
19
- this.name = "WorkflowSourceFailure";
20
- this.error = { code, message, path: source.path, line: source.start };
21
- }
22
- }
23
- const ROOT_KEYS = ["name", "on", "jobs"];
24
- const TRIGGER_KEYS = ["schedule", "workflow_dispatch"];
25
- const SCHEDULE_KEYS = ["cron"];
26
- const JOB_KEYS = ["name", "needs", "runs-on", "steps"];
27
- const STEP_KEYS = ["id", "name", "uses", "run", "with", "env", "shell", "working-directory"];
28
- const UNSAFE_KEYS = new Set(["__proto__", "prototype", "constructor"]);
29
- const HOST_SHELLS = new Set(["bash", "sh", "zsh", "pwsh", "powershell", "cmd"]);
30
- const SOURCE_ID = /^[A-Za-z_][A-Za-z0-9_-]{0,127}$/;
31
- const INPUT_KEY = /^[A-Za-z_][A-Za-z0-9_.-]{0,127}$/;
32
- const ENV_KEY = /^[A-Za-z_][A-Za-z0-9_]*$/;
33
- const MAX_YAML_DEPTH = 32;
34
- const MAX_YAML_NODES = 20_000;
35
- const MAX_STEPS_PER_JOB = 256;
36
- /** A bounded, non-expanding ownership probe. Validation belongs to compilation. */
37
- export function looksLikeGithubWorkflowSource(source) {
38
- if (utf8Bytes(source) > WORKFLOW_MAX_SOURCE_BYTES)
39
- return false;
40
- let doc;
41
- try {
42
- doc = parseDocument(source, { strict: true, uniqueKeys: true, version: "1.2" });
43
- }
44
- catch {
45
- return false;
46
- }
47
- if (!isMap(doc.contents))
48
- return false;
49
- const keys = new Set();
50
- for (const pair of doc.contents.items) {
51
- if (isScalar(pair.key) && typeof pair.key.value === "string")
52
- keys.add(pair.key.value);
53
- }
54
- return keys.has("on") && keys.has("jobs");
55
- }
56
- export function parseGithubWorkflowSource(source, options) {
57
- const documentSource = wholeSourceSpan(source, options.path);
58
- if (utf8Bytes(source) > WORKFLOW_MAX_SOURCE_BYTES) {
59
- throw new WorkflowSourceFailure("source-size-limit", "Workflow source exceeds the 1 MiB limit.", documentSource);
60
- }
61
- const lineCounter = new LineCounter();
62
- let doc;
63
- try {
64
- doc = parseDocument(source, {
65
- lineCounter,
66
- strict: true,
67
- uniqueKeys: true,
68
- version: "1.2",
69
- });
70
- }
71
- catch {
72
- throw new WorkflowSourceFailure("invalid-yaml", "Workflow YAML could not be parsed.", documentSource);
73
- }
74
- if (doc.errors.length > 0) {
75
- const problem = doc.errors[0];
76
- if (!problem)
77
- throw new WorkflowSourceFailure("invalid-yaml", "Invalid YAML.", documentSource);
78
- const offset = Array.isArray(problem.pos) ? problem.pos[0] : 0;
79
- const errorSource = spanAtOffset(options.path, lineCounter, offset);
80
- const code = /Map keys must be unique/i.test(problem.message) ? "duplicate-key" : "invalid-yaml";
81
- throw new WorkflowSourceFailure(code, cleanYamlMessage(problem.message), errorSource);
82
- }
83
- const firstWarning = doc.warnings[0];
84
- if (firstWarning && /tag/i.test(firstWarning.message)) {
85
- throw new WorkflowSourceFailure("yaml-custom-tag", cleanYamlMessage(firstWarning.message), documentSource);
86
- }
87
- const rootNode = doc.contents;
88
- if (!isMap(rootNode)) {
89
- throw new WorkflowSourceFailure("mapping-root-required", "GitHub workflow YAML root must be a mapping.", documentSource);
90
- }
91
- const parsedRoot = rootNode;
92
- const reader = new StrictYamlReader(options.path, lineCounter);
93
- reader.rejectAliases(parsedRoot);
94
- reader.checkTree(parsedRoot);
95
- const root = reader.fields(parsedRoot, ROOT_KEYS, "workflow");
96
- reader.requiredString(root, "name", "workflow");
97
- const schedules = parseTriggers(reader, reader.required(root, "on", "workflow"));
98
- const steps = parseJob(reader, reader.required(root, "jobs", "workflow"), options);
99
- return { irVersion: WORKFLOW_PLAN_VERSION, title: options.title, schedules, steps };
100
- }
101
- class StrictYamlReader {
102
- filePath;
103
- lineCounter;
104
- nodes = 0;
105
- constructor(filePath, lineCounter) {
106
- this.filePath = filePath;
107
- this.lineCounter = lineCounter;
108
- }
109
- span(node) {
110
- const range = node?.range;
111
- if (!range)
112
- return { path: this.filePath, start: 1, end: 1 };
113
- const start = this.lineCounter.linePos(range[0]).line;
114
- const end = this.lineCounter.linePos(Math.max(range[0], range[1] - 1)).line;
115
- return { path: this.filePath, start, end: Math.max(start, end) };
116
- }
117
- rejectAliases(root) {
118
- const pending = [{ node: root, depth: 0 }];
119
- let nodes = 0;
120
- while (pending.length > 0) {
121
- const current = pending.pop();
122
- if (!current)
123
- break;
124
- nodes++;
125
- if (nodes > MAX_YAML_NODES)
126
- this.fail("yaml-node-limit", "YAML exceeds the node limit.", current.node);
127
- if (current.depth > MAX_YAML_DEPTH) {
128
- this.fail("yaml-depth-limit", "YAML exceeds the depth limit.", current.node);
129
- }
130
- if (isAlias(current.node))
131
- this.fail("yaml-alias", "YAML aliases are not supported.", current.node);
132
- if (isSeq(current.node)) {
133
- for (const item of current.node.items) {
134
- if (item)
135
- pending.push({ node: item, depth: current.depth + 1 });
136
- }
137
- }
138
- else if (isMap(current.node)) {
139
- for (const pair of current.node.items) {
140
- if (pair.key)
141
- pending.push({ node: pair.key, depth: current.depth + 1 });
142
- if (pair.value)
143
- pending.push({ node: pair.value, depth: current.depth + 1 });
144
- }
145
- }
146
- }
147
- }
148
- checkTree(node, depth = 0) {
149
- this.nodes++;
150
- if (this.nodes > MAX_YAML_NODES)
151
- this.fail("yaml-node-limit", "YAML exceeds the node limit.", node);
152
- if (depth > MAX_YAML_DEPTH)
153
- this.fail("yaml-depth-limit", "YAML exceeds the depth limit.", node);
154
- if (isAlias(node))
155
- this.fail("yaml-alias", "YAML aliases are not supported.", node);
156
- if ("anchor" in node && typeof node.anchor === "string" && node.anchor !== "") {
157
- this.fail("yaml-anchor", "YAML anchors are not supported.", node);
158
- }
159
- if (node.tag !== undefined)
160
- this.fail("yaml-custom-tag", "Explicit YAML tags are not supported.", node);
161
- if (isScalar(node)) {
162
- if (typeof node.value === "string" && node.value.includes("${{")) {
163
- this.fail("unsupported-github-expression", "GitHub expressions and contexts are not supported.", node);
164
- }
165
- return;
166
- }
167
- if (isSeq(node)) {
168
- for (const item of node.items)
169
- if (item)
170
- this.checkTree(item, depth + 1);
171
- return;
172
- }
173
- if (isMap(node)) {
174
- for (const pair of node.items) {
175
- if (pair.key)
176
- this.checkTree(pair.key, depth + 1);
177
- if (pair.value)
178
- this.checkTree(pair.value, depth + 1);
179
- }
180
- }
181
- }
182
- fields(node, allowed, context) {
183
- if (!isMap(node))
184
- this.fail("mapping-required", `${context} must be a mapping.`, node);
185
- const accepted = new Set(allowed);
186
- const out = new Map();
187
- for (const pair of node.items) {
188
- if (!isScalar(pair.key) || typeof pair.key.value !== "string" || pair.key.value.trim() === "") {
189
- this.fail("string-key-required", `${context} keys must be non-empty strings.`, pair.key);
190
- }
191
- const key = pair.key.value;
192
- if (UNSAFE_KEYS.has(key))
193
- this.fail("unsafe-key", `${context} contains unsafe key ${JSON.stringify(key)}.`, pair.key);
194
- if (!accepted.has(key))
195
- this.fail("unknown-key", `${context} contains unknown key ${JSON.stringify(key)}.`, pair.key);
196
- out.set(key, pair);
197
- }
198
- return out;
199
- }
200
- arbitraryFields(node, context) {
201
- if (!isMap(node))
202
- this.fail("mapping-required", `${context} must be a mapping.`, node);
203
- const out = new Map();
204
- for (const pair of node.items) {
205
- if (!isScalar(pair.key) || typeof pair.key.value !== "string" || pair.key.value.trim() === "") {
206
- this.fail("string-key-required", `${context} keys must be non-empty strings.`, pair.key);
207
- }
208
- const key = pair.key.value;
209
- if (UNSAFE_KEYS.has(key))
210
- this.fail("unsafe-key", `${context} contains unsafe key ${JSON.stringify(key)}.`, pair.key);
211
- out.set(key, pair);
212
- }
213
- return out;
214
- }
215
- plain(node, context) {
216
- if (node === null)
217
- return null;
218
- if (isScalar(node))
219
- return node.value;
220
- if (isSeq(node)) {
221
- return node.items.map((item) => {
222
- if (!item)
223
- this.fail("sparse-yaml-sequence", `${context} may not contain empty entries.`, node);
224
- return this.plain(item, context);
225
- });
226
- }
227
- if (isMap(node)) {
228
- const out = {};
229
- for (const [key, pair] of this.arbitraryFields(node, context)) {
230
- out[key] = this.plain(pair.value, `${context}.${key}`);
231
- }
232
- return out;
233
- }
234
- this.fail("invalid-yaml-node", `${context} contains an unsupported YAML node.`, node);
235
- }
236
- required(fields, key, context) {
237
- const pair = fields.get(key);
238
- if (!pair)
239
- this.fail("missing-key", `${context} is missing required key ${JSON.stringify(key)}.`, undefined);
240
- return pair.value;
241
- }
242
- requiredString(fields, key, context) {
243
- return this.string(this.required(fields, key, context), `${context}.${key}`);
244
- }
245
- optionalString(fields, key, context) {
246
- const pair = fields.get(key);
247
- return pair ? this.string(pair.value, `${context}.${key}`) : undefined;
248
- }
249
- string(node, context) {
250
- if (!isScalar(node) || typeof node.value !== "string" || node.value.trim() === "") {
251
- this.fail("string-required", `${context} must be a non-empty string.`, node);
252
- }
253
- return node.value;
254
- }
255
- scalar(node, context, allowNull) {
256
- if (node === null || (isScalar(node) && node.value === null)) {
257
- if (allowNull)
258
- return null;
259
- this.fail("scalar-required", `${context} may not be null.`, node);
260
- }
261
- if (!isScalar(node))
262
- this.fail("scalar-required", `${context} must be a scalar.`, node);
263
- const value = node.value;
264
- if (typeof value !== "string" && typeof value !== "number" && typeof value !== "boolean") {
265
- this.fail("scalar-required", `${context} must be a string, number, or boolean.`, node);
266
- }
267
- if (typeof value === "number" && !Number.isFinite(value)) {
268
- this.fail("scalar-required", `${context} must be a finite number.`, node);
269
- }
270
- return value;
271
- }
272
- sequence(node, context, max, allowEmpty = false) {
273
- if (!isSeq(node) || (!allowEmpty && node.items.length === 0)) {
274
- this.fail("sequence-required", `${context} must be ${allowEmpty ? "an" : "a non-empty"} list.`, node);
275
- }
276
- if (node.items.length > max)
277
- this.fail("step-count-limit", `${context} exceeds ${max} entries.`, node);
278
- return node.items.map((item) => {
279
- if (!item)
280
- this.fail("sparse-yaml-sequence", `${context} may not contain empty entries.`, node);
281
- return item;
282
- });
283
- }
284
- fail(code, message, node) {
285
- throw new WorkflowSourceFailure(code, message, this.span(node));
286
- }
287
- }
288
- function parseTriggers(reader, node) {
289
- const fields = reader.arbitraryFields(node, "workflow.on");
290
- for (const [key, pair] of fields) {
291
- if (!TRIGGER_KEYS.includes(key)) {
292
- reader.fail("unsupported-service-event", `GitHub service event ${JSON.stringify(key)} is unsupported for local execution.`, pair.key);
293
- }
294
- }
295
- if (fields.size === 0)
296
- reader.fail("trigger-required", "workflow.on must declare schedule or workflow_dispatch.", node);
297
- const schedules = [];
298
- const schedule = fields.get("schedule");
299
- if (schedule) {
300
- const records = reader.sequence(schedule.value, "workflow.on.schedule", 64);
301
- for (const [ordinal, record] of records.entries()) {
302
- const scheduleFields = reader.fields(record, SCHEDULE_KEYS, `workflow.on.schedule[${ordinal}]`);
303
- const cronNode = reader.required(scheduleFields, "cron", `workflow.on.schedule[${ordinal}]`);
304
- const cron = validateCron(reader, reader.string(cronNode, `workflow.on.schedule[${ordinal}].cron`), cronNode);
305
- schedules.push({ cron, ordinal, line: reader.span(cronNode).start });
306
- }
307
- }
308
- const manual = fields.get("workflow_dispatch");
309
- if (manual) {
310
- const nullValue = manual.value === null || (isScalar(manual.value) && manual.value.value === null);
311
- if (!nullValue) {
312
- if (!isMap(manual.value)) {
313
- reader.fail("workflow-dispatch-inputs-unsupported", "workflow_dispatch must be null or an empty mapping; inputs are unsupported.", manual.value);
314
- }
315
- if (manual.value.items.length > 0) {
316
- reader.fail("workflow-dispatch-inputs-unsupported", "workflow_dispatch inputs are not supported for local execution.", manual.value.items[0]?.key);
317
- }
318
- }
319
- }
320
- return schedules;
321
- }
322
- function validateCron(reader, cron, node) {
323
- try {
324
- return canonicalizeWorkflowCron(cron);
325
- }
326
- catch (cause) {
327
- semanticReaderFail(reader, cause, node);
328
- }
329
- }
330
- /**
331
- * Exactly one job: AKM's YAML is an AKM workflow format executed by AKM's
332
- * native engine, not a GitHub Actions job graph.
333
- */
334
- function parseJob(reader, node, options) {
335
- const jobs = reader.arbitraryFields(node, "workflow.jobs");
336
- const [first, second] = [...jobs];
337
- if (jobs.size !== 1 || !first) {
338
- reader.fail("multi-job-unsupported", `AKM workflow YAML requires exactly one job; this document declares ${jobs.size}. AKM's YAML is an AKM workflow format executed by AKM's native engine, not GitHub Actions — split the jobs into separate workflows.`, second ? second[1].key : node);
339
- }
340
- const [id, pair] = first;
341
- const jobNode = pair.value;
342
- if (!SOURCE_ID.test(id))
343
- reader.fail("invalid-job-id", `Invalid job id ${JSON.stringify(id)}.`, jobNode);
344
- const fields = reader.fields(jobNode, JOB_KEYS, `workflow.jobs.${id}`);
345
- const runner = reader.required(fields, "runs-on", `workflow.jobs.${id}`);
346
- if (!isSeq(runner) ||
347
- runner.items.length !== 1 ||
348
- !isScalar(runner.items[0]) ||
349
- runner.items[0].value !== "self-hosted") {
350
- reader.fail("unsupported-runner", `Job ${JSON.stringify(id)} must declare exactly runs-on: [self-hosted].`, runner);
351
- }
352
- const needs = fields.get("needs");
353
- if (needs) {
354
- const values = isSeq(needs.value)
355
- ? reader
356
- .sequence(needs.value, `workflow.jobs.${id}.needs`, 256)
357
- .map((item) => reader.string(item, `workflow.jobs.${id}.needs`))
358
- : [reader.string(needs.value, `workflow.jobs.${id}.needs`)];
359
- for (const need of values)
360
- if (!SOURCE_ID.test(need))
361
- reader.fail("invalid-job-id", `Invalid needs id ${need}.`, needs.value);
362
- if (values.length > 0) {
363
- reader.fail("multi-job-unsupported", `Job ${id} declares needs, but an AKM workflow has exactly one job; remove needs.`, pair.key);
364
- }
365
- }
366
- reader.optionalString(fields, "name", `workflow.jobs.${id}`);
367
- const stepNodes = reader.sequence(reader.required(fields, "steps", `workflow.jobs.${id}`), `workflow.jobs.${id}.steps`, MAX_STEPS_PER_JOB);
368
- const stepIds = new Set();
369
- return stepNodes.map((step, index) => parseStep(reader, step, id, index, stepIds, options));
370
- }
371
- function parseStep(reader, node, jobId, index, stepIds, options) {
372
- const context = `workflow.jobs.${jobId}.steps[${index}]`;
373
- const fields = reader.fields(node, STEP_KEYS, context);
374
- const id = reader.requiredString(fields, "id", context);
375
- if (!SOURCE_ID.test(id))
376
- reader.fail("invalid-step-id", `Invalid step id ${JSON.stringify(id)}.`, fields.get("id")?.value);
377
- if (stepIds.has(id))
378
- reader.fail("duplicate-step-id", `Job ${jobId} has duplicate step id ${id}.`, fields.get("id")?.value);
379
- stepIds.add(id);
380
- const usesPair = fields.get("uses");
381
- const runPair = fields.get("run");
382
- if ((usesPair === undefined) === (runPair === undefined)) {
383
- reader.fail("step-target-xor", `${context} must declare exactly one of uses or run.`, node);
384
- }
385
- reader.optionalString(fields, "name", context);
386
- const env = parseScalarMap(reader, fields.get("env"), `${context}.env`, ENV_KEY, false);
387
- const target = usesPair
388
- ? parseUsesStep(reader, usesPair, fields)
389
- : parseRunStep(reader, runPair, fields, options);
390
- const spec = { ...target, ...(env ? { env } : {}), source: reader.span(node) };
391
- return {
392
- stepId: id,
393
- title: id,
394
- sequenceIndex: index,
395
- spec,
396
- gate: { kind: "gate", id: `${id}.gate`, stepId: id, criteria: [], maxLoops: 1, frozenJudge: null },
397
- };
398
- }
399
- function parseUsesStep(reader, usesPair, fields) {
400
- if (fields.has("shell") || fields.has("working-directory")) {
401
- reader.fail("uses-field-conflict", "shell and working-directory are legal only with run.", usesPair.value);
402
- }
403
- const uses = reader.string(usesPair.value, "step.uses");
404
- let target;
405
- try {
406
- target = classifyWorkflowStepUses(uses);
407
- }
408
- catch (cause) {
409
- semanticReaderFail(reader, cause, usesPair.value);
410
- }
411
- // A tasks/<ref> or workflows/<ref> step's with: may bind any JSON value the
412
- // composed target's declared input/param needs (an object/array literal, or
413
- // a {from: "..."} reference); every other target keeps the scalar grammar.
414
- const withValues = target.kind === "task" || target.kind === "workflow"
415
- ? parsePlainMap(reader, fields.get("with"), "step.with", INPUT_KEY)
416
- : parseScalarMap(reader, fields.get("with"), "step.with", INPUT_KEY, true);
417
- const commandMode = target.kind === "builtin-command"
418
- ? validateBuiltinCommand(reader, withValues, fields.get("with")?.value ?? usesPair.value)
419
- : undefined;
420
- return {
421
- uses,
422
- ...(commandMode ? { commandMode } : {}),
423
- ...(withValues ? { with: withValues } : {}),
424
- };
425
- }
426
- function validateBuiltinCommand(reader, values, node) {
427
- try {
428
- const action = validateWorkflowBuiltinCommand(values);
429
- if (action.kind === "stored")
430
- return "stored-ref";
431
- return action.arguments !== undefined || action.content.includes("$ARGUMENTS") ? "portable-template" : "literal";
432
- }
433
- catch (cause) {
434
- semanticReaderFail(reader, cause, node);
435
- }
436
- }
437
- /** A `run:` step lowers to its shell's argv now; `instructions` keeps the authored command for display. */
438
- function parseRunStep(reader, runPair, fields, options) {
439
- if (fields.has("with"))
440
- reader.fail("run-field-conflict", "with is legal only with uses.", fields.get("with")?.value);
441
- let run;
442
- try {
443
- run = canonicalizeWorkflowRun(reader.string(runPair.value, "step.run"));
444
- }
445
- catch (cause) {
446
- semanticReaderFail(reader, cause, runPair.value);
447
- }
448
- const shell = fields.has("shell") ? reader.requiredString(fields, "shell", "step") : undefined;
449
- if (shell !== undefined && !HOST_SHELLS.has(shell))
450
- reader.fail("unsupported-shell", `Unsupported shell ${shell}.`, fields.get("shell")?.value);
451
- let workingDirectory = fields.has("working-directory")
452
- ? reader.requiredString(fields, "working-directory", "step")
453
- : undefined;
454
- if (workingDirectory !== undefined) {
455
- try {
456
- workingDirectory = canonicalizeWorkflowWorkingDirectory(workingDirectory, options.workspaceRoot);
457
- }
458
- catch (cause) {
459
- semanticReaderFail(reader, cause, fields.get("working-directory")?.value);
460
- }
461
- }
462
- return {
463
- exec: { command: workflowShellCommand(shell ?? "sh", run), ...(workingDirectory ? { cwd: workingDirectory } : {}) },
464
- instructions: `Run ${run}.`,
465
- };
466
- }
467
- function parseScalarMap(reader, pair, context, keyPattern, allowNull) {
468
- if (!pair)
469
- return undefined;
470
- const fields = reader.arbitraryFields(pair.value, context);
471
- const out = {};
472
- for (const [key, valuePair] of fields) {
473
- if (!keyPattern.test(key))
474
- reader.fail("invalid-mapping-key", `${context} has invalid key ${JSON.stringify(key)}.`, valuePair.key);
475
- out[key] = reader.scalar(valuePair.value, `${context}.${key}`, allowNull);
476
- }
477
- return out;
478
- }
479
- /** Like {@link parseScalarMap} but any JSON value per key (bounded document-wide by `checkTree`). */
480
- function parsePlainMap(reader, pair, context, keyPattern) {
481
- if (!pair)
482
- return undefined;
483
- const fields = reader.arbitraryFields(pair.value, context);
484
- const out = {};
485
- for (const [key, valuePair] of fields) {
486
- if (!keyPattern.test(key))
487
- reader.fail("invalid-mapping-key", `${context} has invalid key ${JSON.stringify(key)}.`, valuePair.key);
488
- out[key] = reader.plain(valuePair.value, `${context}.${key}`);
489
- }
490
- return out;
491
- }
492
- function wholeSourceSpan(source, filePath) {
493
- return { path: filePath, start: 1, end: Math.max(1, source.split(/\r?\n/).length) };
494
- }
495
- function spanAtOffset(filePath, counter, offset) {
496
- const line = counter.linePos(Math.max(0, offset)).line;
497
- return { path: filePath, start: line, end: line };
498
- }
499
- function cleanYamlMessage(message) {
500
- return message.replace(/\s+at line \d+, column \d+:[\s\S]*$/i, "").trim();
501
- }
502
- function semanticReaderFail(reader, cause, node) {
503
- if (cause instanceof WorkflowSourceSemanticError)
504
- reader.fail(cause.code, cause.message, node);
505
- reader.fail("invalid-workflow-source", cause instanceof Error ? cause.message : String(cause), node);
506
- }
@@ -1,80 +0,0 @@
1
- // This Source Code Form is subject to the terms of the Mozilla Public
2
- // License, v. 2.0. If a copy of the MPL was not distributed with this
3
- // file, You can obtain one at https://mozilla.org/MPL/2.0/.
4
- /**
5
- * Declared-output resolution and the exported result (P3b, spec
6
- * docs/plans/specs/p3b-child-executor.md §4.3, §4.4).
7
- *
8
- * Pure; no IO. `resolveWorkflowRunOutputs` reads PERSISTED step rows (never
9
- * live in-memory evidence — `completeWorkflowStep` sees only the current
10
- * step's; a resumed run has nothing else to rebuild the scope from, B-N12)
11
- * and fails loudly, by name, when a declared output's source artifact was
12
- * replaced by a truncation envelope at persistence.
13
- *
14
- * This module must stay IMPORT-CYCLE-FREE with `./runs.ts` (which imports
15
- * it): `WORKFLOW_EVIDENCE_TRUNCATED_MARKER`'s value is therefore reproduced
16
- * locally rather than imported.
17
- */
18
- import { validateJsonSchemaSubset } from "../../core/json-schema.js";
19
- import { parseReference, resolveReferenceString } from "../program/expressions.js";
20
- /** Project a step artifact out of its persisted evidence — mirrors `exec/step-work.ts`'s `projectStepOutput`. */
21
- function projectStepOutput(evidence) {
22
- return Object.hasOwn(evidence, "output") ? evidence.output : evidence;
23
- }
24
- /**
25
- * Resolve a plan's declared `outputs:` from a run's PERSISTED step rows, in
26
- * declaration order (compile sorts `outputs` keys by name). Every failure
27
- * mode is collected (not stopped-at-first) so a completion failure names
28
- * every offending output at once.
29
- */
30
- export function resolveWorkflowRunOutputs(plan, steps) {
31
- const stepOutputs = {};
32
- for (const row of steps) {
33
- if (!row.evidence_json)
34
- continue;
35
- let evidence;
36
- try {
37
- evidence = JSON.parse(row.evidence_json);
38
- }
39
- catch {
40
- continue;
41
- }
42
- stepOutputs[row.step_id] = projectStepOutput(evidence);
43
- }
44
- const scope = { params: {}, stepOutputs };
45
- const errors = [];
46
- const outputs = {};
47
- for (const [name, declaration] of Object.entries(plan.outputs ?? {})) {
48
- const parsed = parseReference(declaration.from);
49
- if (!parsed.ok || parsed.expr.kind !== "stepOutput") {
50
- errors.push(`output "${name}": "${declaration.from}" is not a valid step-output reference.`);
51
- continue;
52
- }
53
- const resolved = resolveReferenceString(declaration.from, scope);
54
- if (!resolved.ok) {
55
- errors.push(`output "${name}": ${resolved.error.message}`);
56
- continue;
57
- }
58
- if (declaration.schema) {
59
- const schemaErrors = validateJsonSchemaSubset(resolved.value, declaration.schema);
60
- if (schemaErrors.length > 0) {
61
- for (const schemaError of schemaErrors)
62
- errors.push(`output "${name}": ${schemaError}`);
63
- continue;
64
- }
65
- }
66
- outputs[name] = resolved.value;
67
- }
68
- return { outputs, errors };
69
- }
70
- /**
71
- * What a completed run EXPORTS: the resolved declared outputs, or
72
- * `{runId, status}` metadata when the plan declared none. The `{runId,
73
- * status}` form is synthesized on read and never stored.
74
- */
75
- export function workflowRunExportedResult(row) {
76
- if (row.outputs_json) {
77
- return JSON.parse(row.outputs_json);
78
- }
79
- return { runId: row.id, status: row.status };
80
- }