akm-cli 0.9.0-rc.1 → 0.9.0-rc.13

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 (587) hide show
  1. package/CHANGELOG.md +1190 -52
  2. package/README.md +62 -37
  3. package/SECURITY.md +46 -31
  4. package/dist/akm +162 -38
  5. package/dist/akm-migrate +44 -0
  6. package/dist/assets/backends/schtasks-template.xml +2 -1
  7. package/dist/assets/hints/cli-hints-full.md +268 -118
  8. package/dist/assets/hints/cli-hints-short.md +87 -24
  9. package/dist/assets/{profiles → improve-strategies}/catchup.json +3 -1
  10. package/dist/assets/{profiles → improve-strategies}/consolidate.json +3 -1
  11. package/dist/assets/{profiles → improve-strategies}/default.json +6 -7
  12. package/dist/assets/improve-strategies/frequent.json +15 -0
  13. package/dist/assets/{profiles → improve-strategies}/graph-refresh.json +4 -2
  14. package/dist/assets/{profiles → improve-strategies}/memory-focus.json +4 -1
  15. package/dist/assets/{profiles → improve-strategies}/proactive-maintenance.json +5 -5
  16. package/dist/assets/{profiles → improve-strategies}/quick.json +4 -2
  17. package/dist/assets/improve-strategies/reflect-distill.json +30 -0
  18. package/dist/assets/{profiles → improve-strategies}/thorough.json +1 -1
  19. package/dist/assets/prompts/consolidate-system.md +5 -5
  20. package/dist/assets/prompts/extract-session.md +2 -6
  21. package/dist/assets/prompts/memory-infer-user.md +2 -3
  22. package/dist/assets/prompts/reflect-llm-framed-contract.md +11 -0
  23. package/dist/assets/prompts/reflect-llm-schema-contract.md +3 -0
  24. package/dist/assets/prompts/reflect-output-repair.md +3 -0
  25. package/dist/assets/stash-skeleton/README.md +38 -10
  26. package/dist/assets/stash-skeleton/facts/conventions/assets/agent.md +8 -0
  27. package/dist/assets/stash-skeleton/facts/conventions/assets/command.md +8 -0
  28. package/dist/assets/stash-skeleton/facts/conventions/assets/fact.md +14 -1
  29. package/dist/assets/stash-skeleton/facts/conventions/assets/knowledge.md +13 -1
  30. package/dist/assets/stash-skeleton/facts/conventions/assets/lesson.md +9 -1
  31. package/dist/assets/stash-skeleton/facts/conventions/assets/memory.md +11 -0
  32. package/dist/assets/stash-skeleton/facts/conventions/assets/script.md +9 -0
  33. package/dist/assets/stash-skeleton/facts/conventions/assets/skill.md +9 -0
  34. package/dist/assets/stash-skeleton/facts/conventions/assets/workflow.md +8 -0
  35. package/dist/assets/stash-skeleton/facts/conventions/backlinks.md +100 -0
  36. package/dist/assets/stash-skeleton/facts/conventions/domains.md +64 -0
  37. package/dist/assets/stash-skeleton/facts/conventions/organization.md +136 -0
  38. package/dist/assets/tasks/core/extract.yml +3 -2
  39. package/dist/assets/tasks/core/improve.yml +2 -1
  40. package/dist/assets/tasks/core/index-refresh.yml +1 -0
  41. package/dist/assets/tasks/core/sync.yml +1 -0
  42. package/dist/assets/tasks/core/version-check.yml +2 -1
  43. package/dist/assets/tasks/improve/akm-graph-refresh-weekly.yml +5 -0
  44. package/dist/assets/tasks/improve/akm-improve-catchup.yml +8 -0
  45. package/dist/assets/tasks/improve/akm-improve-consolidate.yml +5 -0
  46. package/dist/assets/tasks/improve/akm-improve-frequent.yml +5 -0
  47. package/dist/assets/tasks/improve/akm-improve-nightly.yml +5 -0
  48. package/dist/assets/templates/html/health.html +5 -4
  49. package/dist/assets/workflows/workflow-template.md +31 -15
  50. package/dist/cli/invocation.js +279 -0
  51. package/dist/cli/parse-args.js +5 -90
  52. package/dist/cli/retired-commands.js +78 -0
  53. package/dist/cli/shared.js +158 -48
  54. package/dist/cli-node.mjs +2 -1
  55. package/dist/cli.js +747 -293
  56. package/dist/commands/agent/agent-dispatch.js +19 -18
  57. package/dist/commands/agent/agent-support.js +0 -24
  58. package/dist/commands/agent/contribute-cli.js +43 -97
  59. package/dist/commands/completions.js +80 -23
  60. package/dist/commands/config-cli.js +44 -281
  61. package/dist/commands/env/env-binding.js +13 -9
  62. package/dist/commands/env/env-cli.js +76 -159
  63. package/dist/commands/env/env.js +12 -163
  64. package/dist/commands/env/marker-path.js +6 -0
  65. package/dist/commands/env/secret-cli.js +45 -61
  66. package/dist/commands/env/secret.js +32 -62
  67. package/dist/commands/feedback-cli.js +179 -85
  68. package/dist/commands/health/accept-rate.js +58 -0
  69. package/dist/commands/health/advisories.js +7 -8
  70. package/dist/commands/health/checks.js +279 -94
  71. package/dist/commands/health/html-report.js +197 -578
  72. package/dist/commands/health/improve-metrics.js +277 -246
  73. package/dist/commands/health/llm-usage.js +19 -19
  74. package/dist/commands/health/md-report.js +16 -7
  75. package/dist/commands/health/metrics.js +67 -32
  76. package/dist/commands/health/renderers.js +47 -0
  77. package/dist/commands/health/report-view-model.js +508 -0
  78. package/dist/commands/health/stash-exposure.js +1 -1
  79. package/dist/commands/health/surfaces.js +16 -56
  80. package/dist/commands/health/task-runs.js +3 -67
  81. package/dist/{migrate-storage-node.mjs → commands/health/types-checks.js} +1 -5
  82. package/dist/commands/health/types-improve.js +29 -0
  83. package/dist/{output/text/save.js → commands/health/types-metrics.js} +1 -2
  84. package/dist/commands/health/types-result.js +7 -0
  85. package/dist/commands/health/types-runs.js +4 -0
  86. package/dist/commands/health/types-session-log.js +4 -0
  87. package/dist/commands/health/types-windows.js +4 -0
  88. package/dist/commands/health/types.js +26 -21
  89. package/dist/commands/health/windows.js +2 -3
  90. package/dist/commands/health.js +296 -167
  91. package/dist/commands/improve/anti-collapse.js +5 -5
  92. package/dist/commands/improve/autonomy-gate.js +68 -0
  93. package/dist/commands/improve/collapse-detector.js +65 -52
  94. package/dist/commands/improve/consolidate/chunking.js +9 -7
  95. package/dist/commands/improve/consolidate/eligibility.js +1 -23
  96. package/dist/commands/improve/consolidate/merge.js +4 -0
  97. package/dist/commands/improve/consolidate.js +454 -1354
  98. package/dist/commands/improve/content-hash.js +39 -0
  99. package/dist/commands/improve/distill/content-repair.js +4 -10
  100. package/dist/commands/improve/distill/promote-memory.js +89 -64
  101. package/dist/commands/improve/distill/quality-gate.js +118 -42
  102. package/dist/commands/improve/distill-guards.js +1 -1
  103. package/dist/commands/improve/distill-promotion-policy.js +33 -888
  104. package/dist/commands/improve/distill.js +607 -363
  105. package/dist/commands/improve/eligibility.js +165 -79
  106. package/dist/commands/improve/extract-cli.js +35 -126
  107. package/dist/commands/improve/extract-prompt.js +6 -35
  108. package/dist/commands/improve/extract.js +640 -391
  109. package/dist/commands/improve/feedback-valence.js +2 -12
  110. package/dist/commands/improve/improve-cli.js +134 -135
  111. package/dist/commands/improve/improve-result-file.js +30 -50
  112. package/dist/commands/improve/improve-run-types.js +4 -0
  113. package/dist/commands/improve/improve-strategies.js +135 -0
  114. package/dist/commands/improve/improve.js +904 -701
  115. package/dist/commands/improve/locks.js +64 -111
  116. package/dist/commands/improve/loop-stages.js +1110 -923
  117. package/dist/commands/improve/memory/derived-ref.js +124 -0
  118. package/dist/commands/improve/memory/memory-belief.js +79 -7
  119. package/dist/commands/improve/memory/memory-contradiction-detect.js +49 -52
  120. package/dist/commands/improve/memory/memory-improve.js +25 -37
  121. package/dist/commands/improve/outcome-loop.js +25 -88
  122. package/dist/commands/improve/preparation.js +1034 -813
  123. package/dist/commands/improve/proactive-maintenance.js +34 -9
  124. package/dist/commands/improve/proposal-envelope.js +31 -0
  125. package/dist/commands/improve/reflect.js +983 -794
  126. package/dist/commands/improve/run-context.js +119 -0
  127. package/dist/commands/improve/salience.js +24 -127
  128. package/dist/commands/improve/session-asset.js +7 -3
  129. package/dist/commands/improve/shared.js +14 -34
  130. package/dist/commands/improve/source-identity.js +28 -0
  131. package/dist/commands/improve/triage.js +20 -17
  132. package/dist/commands/lint/base-linter.js +340 -313
  133. package/dist/commands/lint/env-key-rules.js +31 -47
  134. package/dist/commands/lint/index.js +185 -30
  135. package/dist/commands/{events.js → log.js} +28 -38
  136. package/dist/commands/migrate-cli.js +54 -0
  137. package/dist/commands/migration-tool.js +55 -0
  138. package/dist/commands/observability-cli.js +70 -208
  139. package/dist/commands/proposal/diff-format.js +50 -0
  140. package/dist/commands/proposal/drain-policies.js +0 -6
  141. package/dist/commands/proposal/drain.js +91 -40
  142. package/dist/commands/proposal/proposal-cli.js +134 -132
  143. package/dist/commands/proposal/proposal-types.js +56 -0
  144. package/dist/commands/proposal/proposal.js +83 -65
  145. package/dist/commands/proposal/propose-cli.js +88 -0
  146. package/dist/commands/proposal/propose.js +105 -88
  147. package/dist/commands/proposal/repository.js +1303 -278
  148. package/dist/commands/proposal/validators/proposal-quality-validators.js +16 -6
  149. package/dist/commands/proposal/validators/proposal-validators.js +61 -12
  150. package/dist/commands/proposal/validators/proposals.js +6 -8
  151. package/dist/commands/read/curate.js +78 -73
  152. package/dist/commands/read/knowledge.js +510 -13
  153. package/dist/commands/read/registry-search.js +2 -2
  154. package/dist/commands/read/remember-cli.js +84 -15
  155. package/dist/commands/read/search-cli.js +203 -96
  156. package/dist/commands/read/search.js +126 -94
  157. package/dist/commands/read/show.js +226 -250
  158. package/dist/commands/registry-cli.js +34 -60
  159. package/dist/commands/remember.js +18 -57
  160. package/dist/commands/sources/add-cli.js +104 -49
  161. package/dist/commands/sources/bundle-cli.js +166 -0
  162. package/dist/commands/sources/bundle-config-ops.js +63 -0
  163. package/dist/commands/sources/info.js +27 -15
  164. package/dist/commands/sources/init.js +30 -40
  165. package/dist/commands/sources/installed-stashes.js +469 -172
  166. package/dist/commands/sources/schema-repair.js +10 -9
  167. package/dist/commands/sources/self-update.js +182 -121
  168. package/dist/commands/sources/source-add.js +169 -178
  169. package/dist/commands/sources/source-clone.js +144 -41
  170. package/dist/commands/sources/source-manage.js +94 -59
  171. package/dist/commands/sources/sources-cli.js +64 -205
  172. package/dist/commands/sources/stash-cli.js +91 -54
  173. package/dist/commands/sources/stash-skeleton.js +1 -1
  174. package/dist/commands/tasks/tasks-cli.js +106 -104
  175. package/dist/commands/tasks/tasks.js +445 -262
  176. package/dist/commands/workflow-cli.js +75 -228
  177. package/dist/core/action-contributors.js +1 -1
  178. package/dist/core/activation-policy.js +49 -0
  179. package/dist/core/adapter/adapters/agent-skills-adapter.js +181 -0
  180. package/dist/core/adapter/adapters/akm-adapter.js +528 -0
  181. package/dist/core/adapter/adapters/akm-lint.js +392 -0
  182. package/dist/core/adapter/adapters/akm-metadata.js +387 -0
  183. package/dist/core/adapter/adapters/akm-task-adapter.js +149 -0
  184. package/dist/core/adapter/adapters/akm-workflow-adapter.js +180 -0
  185. package/dist/core/adapter/adapters/claude-adapter.js +61 -0
  186. package/dist/core/adapter/adapters/dotenv-adapter.js +187 -0
  187. package/dist/core/adapter/adapters/generic-files-adapter.js +119 -0
  188. package/dist/core/adapter/adapters/index.js +80 -0
  189. package/dist/core/adapter/adapters/llm-wiki-adapter.js +419 -0
  190. package/dist/core/adapter/adapters/okf-adapter.js +391 -0
  191. package/dist/core/adapter/adapters/opencode-adapter.js +68 -0
  192. package/dist/core/adapter/adapters/shared.js +286 -0
  193. package/dist/core/adapter/adapters/tool-dir-shared.js +217 -0
  194. package/dist/core/adapter/adapters/website-snapshot-adapter.js +155 -0
  195. package/dist/core/adapter/bundle-adapter.js +4 -0
  196. package/dist/core/adapter/detect-adapter.js +17 -0
  197. package/dist/core/adapter/recognize-match.js +44 -0
  198. package/dist/core/adapter/registry.js +56 -0
  199. package/dist/core/adapter/types.js +4 -0
  200. package/dist/core/asset/akm-markdown.js +30 -0
  201. package/dist/core/asset/asset-placement.js +243 -0
  202. package/dist/core/asset/asset-ref.js +110 -79
  203. package/dist/core/asset/asset-serialize.js +20 -0
  204. package/dist/core/asset/frontmatter.js +28 -12
  205. package/dist/core/asset/markdown.js +40 -51
  206. package/dist/core/asset/resolve-ref.js +274 -0
  207. package/dist/core/asset/stash-meta.js +2 -2
  208. package/dist/core/bundle-id.js +51 -0
  209. package/dist/core/common.js +281 -86
  210. package/dist/core/config/config-io.js +42 -128
  211. package/dist/core/config/config-schema.js +233 -855
  212. package/dist/core/config/config-sources.js +162 -39
  213. package/dist/core/config/config-types.js +16 -11
  214. package/dist/core/config/config-version.js +29 -0
  215. package/dist/core/config/config-walker.js +126 -37
  216. package/dist/core/config/config.js +154 -331
  217. package/dist/core/config/deep-merge.js +41 -0
  218. package/dist/core/config/engine-semantics.js +28 -0
  219. package/dist/core/config/experimental.js +21 -0
  220. package/dist/core/config/schema/embedding.js +38 -0
  221. package/dist/core/config/schema/engines.js +116 -0
  222. package/dist/core/config/schema/experimental.js +47 -0
  223. package/dist/core/config/schema/feedback.js +31 -0
  224. package/dist/core/config/schema/improve-processes.js +389 -0
  225. package/dist/core/config/schema/improve.js +94 -0
  226. package/dist/core/config/schema/index-config.js +176 -0
  227. package/dist/core/config/schema/output.js +18 -0
  228. package/dist/core/config/schema/primitives.js +94 -0
  229. package/dist/core/config/schema/search.js +30 -0
  230. package/dist/core/config/schema/setup.js +18 -0
  231. package/dist/core/config/schema/sources-bundles.js +169 -0
  232. package/dist/core/config/schema/workflow.js +29 -0
  233. package/dist/core/env-secret-ref.js +155 -20
  234. package/dist/core/errors.js +17 -15
  235. package/dist/core/events-types.js +4 -0
  236. package/dist/core/events.js +46 -128
  237. package/dist/core/extra-params.js +62 -0
  238. package/dist/core/file-change.js +17 -0
  239. package/dist/core/file-lock.js +202 -57
  240. package/dist/core/fs-txn.js +392 -0
  241. package/dist/core/git-message.js +59 -0
  242. package/dist/core/improve-result.js +167 -0
  243. package/dist/core/lesson-lint.js +1 -17
  244. package/dist/core/logs-db.js +1 -1
  245. package/dist/core/maintenance-barrier.js +135 -0
  246. package/dist/core/migration-operation.js +44 -0
  247. package/dist/core/mutation-target.js +78 -0
  248. package/dist/core/paths.js +22 -25
  249. package/dist/core/platform.js +10 -0
  250. package/dist/core/recognition-util.js +128 -0
  251. package/dist/core/redaction.js +392 -0
  252. package/dist/core/standards/resolve-standards-context.js +36 -65
  253. package/dist/core/standards/resolve-stash-standards.js +2 -2
  254. package/dist/core/standards/resolve-type-conventions.js +5 -5
  255. package/dist/core/state/migrations.js +242 -11
  256. package/dist/core/state-db.js +98 -10
  257. package/dist/core/structured.js +1 -1
  258. package/dist/core/subprocess.js +303 -0
  259. package/dist/core/text-truncation.js +9 -5
  260. package/dist/core/time.js +20 -0
  261. package/dist/core/type-presentation.js +130 -0
  262. package/dist/core/warn.js +0 -3
  263. package/dist/core/write-source.js +834 -118
  264. package/dist/indexer/bundle-identity-guard.js +92 -0
  265. package/dist/indexer/db/graph-db.js +1 -25
  266. package/dist/indexer/db/llm-cache.js +1 -1
  267. package/dist/indexer/ensure-index.js +30 -9
  268. package/dist/indexer/graph/graph-boost.js +9 -30
  269. package/dist/indexer/graph/graph-extraction.js +41 -27
  270. package/dist/indexer/graph/graph-types.js +4 -0
  271. package/dist/indexer/index-writer-lock.js +93 -49
  272. package/dist/indexer/index-written-assets.js +100 -53
  273. package/dist/indexer/indexer.js +746 -329
  274. package/dist/indexer/init.js +18 -25
  275. package/dist/indexer/installations.js +142 -0
  276. package/dist/indexer/passes/dir-staleness.js +18 -10
  277. package/dist/indexer/passes/memory-inference.js +25 -15
  278. package/dist/indexer/passes/metadata.js +412 -243
  279. package/dist/indexer/scan/doc-to-entry.js +160 -0
  280. package/dist/indexer/scan/drain-dir.js +134 -0
  281. package/dist/indexer/search/db-search.js +292 -108
  282. package/dist/indexer/search/fts-query.js +64 -0
  283. package/dist/indexer/search/ranking-contributors.js +145 -25
  284. package/dist/indexer/search/ranking-types.js +4 -0
  285. package/dist/indexer/search/ranking.js +28 -71
  286. package/dist/indexer/search/search-attribution.js +67 -0
  287. package/dist/indexer/search/search-fields.js +18 -3
  288. package/dist/indexer/search/search-hit-enrichers.js +30 -40
  289. package/dist/indexer/search/search-source.js +157 -111
  290. package/dist/indexer/search/semantic-status.js +4 -1
  291. package/dist/indexer/usage/usage-events.js +10 -30
  292. package/dist/indexer/walk/file-context.js +3 -45
  293. package/dist/indexer/walk/matchers.js +42 -73
  294. package/dist/indexer/walk/path-resolver.js +11 -5
  295. package/dist/indexer/walk/walker.js +42 -14
  296. package/dist/integrations/agent/builder-shared.js +7 -0
  297. package/dist/integrations/agent/builders.js +5 -58
  298. package/dist/integrations/agent/config.js +3 -143
  299. package/dist/integrations/agent/detect.js +17 -2
  300. package/dist/integrations/agent/engine-resolution.js +231 -0
  301. package/dist/integrations/agent/index.js +1 -2
  302. package/dist/integrations/agent/model-aliases.js +8 -3
  303. package/dist/integrations/agent/profiles.js +6 -99
  304. package/dist/integrations/agent/prompts.js +46 -18
  305. package/dist/integrations/agent/runner-dispatch.js +78 -13
  306. package/dist/integrations/agent/runner.js +76 -208
  307. package/dist/integrations/agent/spawn.js +48 -279
  308. package/dist/integrations/harnesses/aider/agent-builder.js +9 -8
  309. package/dist/integrations/harnesses/aider/index.js +2 -12
  310. package/dist/integrations/harnesses/amazonq/agent-builder.js +10 -16
  311. package/dist/integrations/harnesses/amazonq/index.js +3 -17
  312. package/dist/integrations/harnesses/claude/agent-builder.js +2 -3
  313. package/dist/integrations/harnesses/claude/config-import.js +1 -3
  314. package/dist/integrations/harnesses/claude/index.js +1 -14
  315. package/dist/integrations/harnesses/claude/session-log.js +27 -75
  316. package/dist/integrations/harnesses/codex/agent-builder.js +8 -7
  317. package/dist/integrations/harnesses/codex/index.js +2 -13
  318. package/dist/integrations/harnesses/copilot/agent-builder.js +9 -9
  319. package/dist/integrations/harnesses/copilot/index.js +1 -13
  320. package/dist/integrations/harnesses/gemini/agent-builder.js +8 -9
  321. package/dist/integrations/harnesses/gemini/index.js +1 -13
  322. package/dist/integrations/harnesses/ids.js +24 -0
  323. package/dist/integrations/harnesses/index.js +31 -33
  324. package/dist/integrations/harnesses/opencode/agent-builder.js +23 -5
  325. package/dist/integrations/harnesses/opencode/config-import.js +1 -3
  326. package/dist/integrations/harnesses/opencode/index.js +1 -18
  327. package/dist/integrations/harnesses/opencode/session-log.js +67 -125
  328. package/dist/integrations/harnesses/opencode-sdk/harness.js +3 -17
  329. package/dist/integrations/harnesses/opencode-sdk/sdk-runner.js +274 -191
  330. package/dist/integrations/harnesses/openhands/agent-builder.js +12 -10
  331. package/dist/integrations/harnesses/openhands/index.js +2 -12
  332. package/dist/integrations/harnesses/pi/agent-builder.js +11 -18
  333. package/dist/integrations/harnesses/pi/index.js +3 -16
  334. package/dist/integrations/harnesses/shared.js +17 -0
  335. package/dist/integrations/harnesses/types.js +38 -34
  336. package/dist/integrations/lockfile.js +211 -24
  337. package/dist/integrations/session-logs/index.js +24 -40
  338. package/dist/integrations/session-logs/provider-base.js +113 -0
  339. package/dist/llm/client.js +182 -110
  340. package/dist/llm/embedders/deterministic.js +2 -2
  341. package/dist/llm/embedders/remote.js +21 -9
  342. package/dist/llm/feature-gate.js +17 -57
  343. package/dist/llm/graph-extract.js +12 -13
  344. package/dist/llm/index-passes.js +8 -42
  345. package/dist/llm/memory-infer.js +144 -1
  346. package/dist/llm/metadata-enhance.js +45 -30
  347. package/dist/llm/structured-call.js +16 -8
  348. package/dist/llm/usage-persist.js +30 -5
  349. package/dist/llm/usage-telemetry.js +59 -6
  350. package/dist/output/cli-hints.js +1 -2
  351. package/dist/output/command-registry.js +27 -0
  352. package/dist/output/context.js +22 -7
  353. package/dist/output/format-exempt.js +80 -0
  354. package/dist/output/generic-render.js +251 -0
  355. package/dist/output/html-render.js +11 -16
  356. package/dist/output/render-registry.js +57 -0
  357. package/dist/output/renderers.js +15 -281
  358. package/dist/output/shapes/curate.js +10 -1
  359. package/dist/output/shapes/events.js +12 -7
  360. package/dist/output/shapes/helpers.js +58 -84
  361. package/dist/output/shapes/passthrough.js +8 -40
  362. package/dist/output/shapes/proposal/producer.js +15 -7
  363. package/dist/output/shapes/registry.js +12 -6
  364. package/dist/output/shapes.js +0 -9
  365. package/dist/output/text/{init.js → bundle-create.js} +3 -1
  366. package/dist/output/text/bundle-show.js +7 -0
  367. package/dist/output/text/command-format.js +562 -0
  368. package/dist/output/text/env.js +1 -3
  369. package/dist/output/text/events.js +8 -7
  370. package/dist/output/text/helpers.js +15 -1375
  371. package/dist/output/text/proposal/producer.js +4 -2
  372. package/dist/output/text/proposal-format.js +202 -0
  373. package/dist/output/text/registry-commands.js +1 -2
  374. package/dist/output/text/registry.js +12 -6
  375. package/dist/output/text/show-directives.js +117 -0
  376. package/dist/output/text/show-format.js +103 -0
  377. package/dist/output/text/sync.js +5 -0
  378. package/dist/output/text/workflow-format.js +332 -0
  379. package/dist/output/text/workflow.js +1 -2
  380. package/dist/output/text.js +10 -19
  381. package/dist/registry/factory.js +4 -6
  382. package/dist/registry/origin-resolve.js +16 -27
  383. package/dist/registry/providers/skills-sh.js +3 -3
  384. package/dist/registry/providers/static-index.js +15 -25
  385. package/dist/registry/resolve.js +43 -94
  386. package/dist/registry/semver.js +43 -0
  387. package/dist/runtime.js +81 -12
  388. package/dist/scripts/akm-migrate.js +35529 -0
  389. package/dist/setup/detect.js +5 -7
  390. package/dist/setup/detected-engines.js +136 -0
  391. package/dist/setup/engine-config.js +100 -0
  392. package/dist/setup/registry-stash-loader.js +3 -3
  393. package/dist/setup/semantic-assets.js +12 -9
  394. package/dist/setup/setup.js +444 -208
  395. package/dist/setup/steps/connection-shared.js +120 -0
  396. package/dist/setup/steps/connection.js +108 -305
  397. package/dist/setup/steps/platforms.js +13 -12
  398. package/dist/setup/steps/semantic.js +15 -3
  399. package/dist/setup/steps/sources.js +21 -15
  400. package/dist/setup/steps/stashdir.js +6 -4
  401. package/dist/setup/steps/tasks.js +236 -119
  402. package/dist/setup/steps.js +3 -2
  403. package/dist/sources/freshness.js +39 -0
  404. package/dist/sources/provider-factory.js +11 -17
  405. package/dist/sources/providers/filesystem.js +2 -3
  406. package/dist/sources/providers/git-install.js +278 -34
  407. package/dist/sources/providers/git-provider.js +54 -56
  408. package/dist/sources/providers/git-stash.js +420 -91
  409. package/dist/sources/providers/git.js +2 -2
  410. package/dist/sources/providers/npm.js +16 -19
  411. package/dist/sources/providers/provider-utils.js +47 -22
  412. package/dist/sources/providers/sync-from-ref.js +3 -9
  413. package/dist/sources/providers/website.js +2 -2
  414. package/dist/sources/resolve.js +11 -10
  415. package/dist/sources/snapshot-fetchers/types.js +4 -0
  416. package/dist/sources/{website-ingest.js → snapshot-fetchers/website-ingest.js} +110 -41
  417. package/dist/storage/database.js +60 -4
  418. package/dist/storage/engines/sqlite-migrations.js +156 -5
  419. package/dist/storage/locations.js +1 -2
  420. package/dist/storage/repositories/canaries-repository.js +1 -1
  421. package/dist/storage/repositories/events-repository.js +51 -11
  422. package/dist/storage/repositories/improve-runs-repository.js +6 -32
  423. package/dist/storage/repositories/index-connection.js +79 -0
  424. package/dist/storage/repositories/index-db.js +4 -3
  425. package/dist/storage/repositories/index-entries-repository.js +863 -0
  426. package/dist/{indexer/db/entry-mapper.js → storage/repositories/index-entry-mapper.js} +19 -2
  427. package/dist/storage/repositories/index-entry-types.js +4 -0
  428. package/dist/storage/repositories/index-fts-repository.js +167 -0
  429. package/dist/storage/repositories/index-llm-cache-repository.js +108 -0
  430. package/dist/storage/repositories/index-meta-repository.js +49 -0
  431. package/dist/{indexer/db/schema.js → storage/repositories/index-schema.js} +226 -100
  432. package/dist/storage/repositories/index-sql.js +12 -0
  433. package/dist/storage/repositories/index-utility-repository.js +356 -0
  434. package/dist/storage/repositories/index-vec-repository.js +250 -0
  435. package/dist/storage/repositories/outcome-repository.js +119 -0
  436. package/dist/storage/repositories/proposals-repository.js +317 -75
  437. package/dist/storage/repositories/registry-cache.js +1 -1
  438. package/dist/storage/repositories/salience-repository.js +172 -0
  439. package/dist/storage/repositories/task-history-repository.js +110 -3
  440. package/dist/storage/repositories/workflow-runs-repository.js +68 -35
  441. package/dist/tasks/backends/cron.js +169 -46
  442. package/dist/tasks/backends/exec-utils.js +76 -3
  443. package/dist/tasks/backends/index.js +6 -9
  444. package/dist/tasks/backends/launchd.js +292 -55
  445. package/dist/tasks/backends/schtasks.js +557 -70
  446. package/dist/tasks/backends/types.js +4 -0
  447. package/dist/tasks/command-executable.js +93 -0
  448. package/dist/tasks/embedded.js +56 -38
  449. package/dist/tasks/parser.js +156 -64
  450. package/dist/tasks/resolve-akm-bin.js +144 -51
  451. package/dist/tasks/runner.js +377 -209
  452. package/dist/tasks/schedule.js +108 -19
  453. package/dist/tasks/scheduler-invocation.js +296 -0
  454. package/dist/tasks/schema.js +1 -1
  455. package/dist/tasks/task-id.js +35 -0
  456. package/dist/tasks/validator.js +30 -16
  457. package/dist/workflows/authoring/authoring.js +96 -148
  458. package/dist/workflows/authoring/scope-key.js +1 -1
  459. package/dist/workflows/cli.js +0 -20
  460. package/dist/workflows/concurrency-policy.js +15 -0
  461. package/dist/workflows/exec/brief.js +25 -59
  462. package/dist/workflows/exec/frozen-judge.js +47 -0
  463. package/dist/workflows/exec/native-executor.js +157 -94
  464. package/dist/workflows/exec/report.js +365 -200
  465. package/dist/workflows/exec/run-workflow.js +46 -40
  466. package/dist/workflows/exec/scheduler.js +12 -41
  467. package/dist/workflows/exec/step-work.js +239 -205
  468. package/dist/workflows/exec/workflow-engine-gate.js +67 -0
  469. package/dist/workflows/ir/compile.js +141 -283
  470. package/dist/workflows/ir/freeze.js +233 -0
  471. package/dist/workflows/ir/plan-hash.js +40 -5
  472. package/dist/workflows/ir/schema.js +537 -1
  473. package/dist/workflows/parser.js +878 -306
  474. package/dist/workflows/program/expressions.js +20 -208
  475. package/dist/workflows/program/schema.js +7 -10
  476. package/dist/workflows/renderer.js +99 -121
  477. package/dist/workflows/resource-limits.js +22 -0
  478. package/dist/workflows/runtime/checkin.js +1 -1
  479. package/dist/workflows/runtime/plan-classifier.js +131 -0
  480. package/dist/workflows/runtime/runs.js +200 -113
  481. package/dist/workflows/runtime/unit-checkin.js +1 -1
  482. package/dist/workflows/runtime/unit-phases.js +20 -0
  483. package/dist/workflows/runtime/workflow-asset-loader.js +235 -97
  484. package/dist/workflows/schema.js +1 -11
  485. package/dist/workflows/validate-summary.js +4 -26
  486. package/dist/workflows/validator.js +52 -30
  487. package/docs/README.md +42 -78
  488. package/docs/migration/README.md +8 -0
  489. package/docs/migration/release-notes/0.6.0.md +1 -1
  490. package/docs/migration/release-notes/0.7.0.md +9 -8
  491. package/docs/migration/release-notes/0.9.0.md +158 -14
  492. package/docs/migration/v0.7-to-v0.8.md +46 -47
  493. package/docs/migration/v0.8-to-v0.9.md +844 -0
  494. package/docs/reference/README.md +12 -0
  495. package/docs/reference/data-and-telemetry.md +333 -0
  496. package/package.json +21 -17
  497. package/schemas/akm-asset-envelope.json +93 -0
  498. package/schemas/akm-config.json +4636 -0
  499. package/schemas/akm-task.json +87 -0
  500. package/{dist/schemas → schemas}/akm-workflow.json +127 -82
  501. package/dist/akm-migrate-storage +0 -38
  502. package/dist/assets/help/help-accept.md +0 -12
  503. package/dist/assets/help/help-improve.md +0 -84
  504. package/dist/assets/help/help-proposals.md +0 -17
  505. package/dist/assets/help/help-propose.md +0 -17
  506. package/dist/assets/help/help-reject.md +0 -11
  507. package/dist/assets/profiles/frequent.json +0 -13
  508. package/dist/assets/profiles/recombine-only.json +0 -21
  509. package/dist/assets/profiles/reflect-distill.json +0 -30
  510. package/dist/assets/profiles/synthesize.json +0 -15
  511. package/dist/assets/prompts/procedural-system.md +0 -44
  512. package/dist/assets/prompts/recombine-system.md +0 -40
  513. package/dist/assets/prompts/staleness-detect-system.md +0 -6
  514. package/dist/assets/tasks/core/backup.yml +0 -4
  515. package/dist/assets/tasks/graph-refresh-weekly.yml +0 -10
  516. package/dist/assets/templates/html/default.html +0 -78
  517. package/dist/assets/templates/html/vendor/echarts.min.js +0 -45
  518. package/dist/assets/wiki/index-template.md +0 -12
  519. package/dist/assets/wiki/ingest-workflow-template.md +0 -83
  520. package/dist/assets/wiki/log-template.md +0 -8
  521. package/dist/assets/wiki/schema-template.md +0 -61
  522. package/dist/cli/config-migrate.js +0 -150
  523. package/dist/cli/config-validate.js +0 -39
  524. package/dist/commands/graph/graph-cli.js +0 -124
  525. package/dist/commands/graph/graph.js +0 -487
  526. package/dist/commands/improve/calibration.js +0 -161
  527. package/dist/commands/improve/dedup.js +0 -482
  528. package/dist/commands/improve/extract-watch.js +0 -140
  529. package/dist/commands/improve/hot-probation.js +0 -45
  530. package/dist/commands/improve/improve-auto-accept.js +0 -276
  531. package/dist/commands/improve/improve-profiles.js +0 -168
  532. package/dist/commands/improve/procedural.js +0 -398
  533. package/dist/commands/improve/recombine.js +0 -818
  534. package/dist/commands/improve/schema-similarity-gate.js +0 -168
  535. package/dist/commands/lint/agent-linter.js +0 -44
  536. package/dist/commands/lint/command-linter.js +0 -44
  537. package/dist/commands/lint/default-linter.js +0 -16
  538. package/dist/commands/lint/fact-linter.js +0 -39
  539. package/dist/commands/lint/knowledge-linter.js +0 -16
  540. package/dist/commands/lint/memory-linter.js +0 -61
  541. package/dist/commands/lint/registry.js +0 -41
  542. package/dist/commands/lint/skill-linter.js +0 -45
  543. package/dist/commands/lint/task-linter.js +0 -50
  544. package/dist/commands/lint/workflow-linter.js +0 -81
  545. package/dist/commands/proposal/legacy-import.js +0 -115
  546. package/dist/commands/sources/history.js +0 -196
  547. package/dist/commands/tasks/default-tasks.js +0 -186
  548. package/dist/commands/wiki-cli.js +0 -292
  549. package/dist/core/asset/asset-registry.js +0 -76
  550. package/dist/core/asset/asset-spec.js +0 -316
  551. package/dist/core/config/config-migration.js +0 -602
  552. package/dist/core/deep-merge.js +0 -38
  553. package/dist/core/eval/rank-metrics.js +0 -113
  554. package/dist/core/ripgrep/install.js +0 -163
  555. package/dist/core/ripgrep/resolve.js +0 -81
  556. package/dist/indexer/db/db.js +0 -1414
  557. package/dist/indexer/manifest.js +0 -170
  558. package/dist/indexer/passes/metadata-contributors.js +0 -31
  559. package/dist/indexer/usage/unmigrated-vaults-guard.js +0 -94
  560. package/dist/integrations/harnesses/opencode-sdk/index.js +0 -25
  561. package/dist/llm/call-ai.js +0 -62
  562. package/dist/llm/memory-infer-impl.js +0 -138
  563. package/dist/output/shapes/distill.js +0 -14
  564. package/dist/output/shapes/history.js +0 -11
  565. package/dist/output/text/distill.js +0 -6
  566. package/dist/output/text/enable-disable.js +0 -8
  567. package/dist/output/text/history.js +0 -6
  568. package/dist/output/text/wiki.js +0 -16
  569. package/dist/registry/build-index.js +0 -386
  570. package/dist/schemas/akm-config.json +0 -14225
  571. package/dist/scripts/migrate-storage.js +0 -13169
  572. package/dist/scripts/migrations/import-fs-improve-runs-to-db.js +0 -10169
  573. package/dist/scripts/migrations/v16-to-v17.js +0 -141
  574. package/dist/setup/legacy-config.js +0 -106
  575. package/dist/storage/repositories/consolidation-repository.js +0 -38
  576. package/dist/storage/repositories/recombine-repository.js +0 -213
  577. package/dist/wiki/wiki-templates.js +0 -15
  578. package/dist/wiki/wiki.js +0 -1012
  579. package/dist/workflows/authoring/workflow-program-template.yaml +0 -31
  580. package/dist/workflows/db.js +0 -350
  581. package/dist/workflows/exec/watch.js +0 -116
  582. package/dist/workflows/program/parser.js +0 -760
  583. package/dist/workflows/program/project.js +0 -105
  584. package/docs/data-and-telemetry.md +0 -227
  585. package/docs/migration/release-notes/0.9.0-beta.60.md +0 -19
  586. /package/dist/sources/{wiki-fetchers → snapshot-fetchers}/registry.js +0 -0
  587. /package/dist/sources/{wiki-fetchers → snapshot-fetchers}/youtube.js +0 -0
@@ -2,21 +2,27 @@
2
2
  // License, v. 2.0. If a copy of the MPL was not distributed with this
3
3
  // file, You can obtain one at https://mozilla.org/MPL/2.0/.
4
4
  /**
5
- * R5 — Longitudinal collapse/churn detector
6
- * (docs/design/improve-collapse-churn-detector-design.md).
5
+ * R5 — Longitudinal collapse detector
6
+ * (docs/architecture/specs/improve-collapse-churn-detector-design.md).
7
7
  *
8
- * Detects the two measured failure modes of LLM-consolidated memory stores:
8
+ * Detects the measured collapse failure mode of LLM-consolidated memory
9
+ * stores: repeated merges destroy information — canary retrieval recall
10
+ * downtrends, distinct-content entropy downtrends, or the store shrinks
11
+ * while generation counts rise.
9
12
  *
10
- * COLLAPSE — repeated merges destroy information: canary retrieval recall
11
- * downtrends, distinct-content entropy downtrends, or the store shrinks
12
- * while generation counts rise.
13
- * CHURN — real accepted-change volume with zero retrieval-visible or
14
- * shape-visible movement (LLM budget burned rewriting to no effect).
13
+ * The CHURN alert class described in the design doc was removed: production
14
+ * never threaded a real accepted-change-volume signal in (the value was a
15
+ * hardcoded 0 from the 0.9.0 confidence-gate deletion onward), so the alert
16
+ * could never fire. See the design doc's status note for the removal
17
+ * rationale. `improve_cycle_metrics.accepted_actions` stays in the schema and
18
+ * is written as 0: its migration body is released, and 0.8 ships `state.db`,
19
+ * so a deployed ledger may already have sealed that body's checksum. Editing
20
+ * it would fail those installs closed.
15
21
  *
16
22
  * Hard invariants: deterministic only (FTS BM25 + hashing — never an LLM,
17
23
  * never an embedding model); bounded storage (< 2 KB per qualifying cycle,
18
24
  * 365-day retention); fail-open (an error warns and skips, never breaks an
19
- * improve run); runs only on cycles where consolidate/recombine did work.
25
+ * improve run); runs only on cycles where consolidate did work.
20
26
  *
21
27
  * Observe-only in v1: alerts land in `improve_cycle_metrics.alerts_json`, the
22
28
  * events log (`collapse_detector_alert`), and the `akm health` advisory —
@@ -25,13 +31,16 @@
25
31
  * @module collapse-detector
26
32
  */
27
33
  import { randomBytes } from "node:crypto";
28
- import { makeAssetRef } from "../../core/asset/asset-ref.js";
34
+ import { parseBundleRef } from "../../core/asset/asset-ref.js";
35
+ import { conceptIdFromTypeName } from "../../core/asset/resolve-ref.js";
29
36
  import { getImproveProcessConfig } from "../../core/config/config.js";
30
37
  import { appendEvent } from "../../core/events.js";
31
38
  import { withStateDb } from "../../core/state-db.js";
32
39
  import { warn } from "../../core/warn.js";
33
- import { closeDatabase, getAllEntries, openExistingDatabase, searchFts, } from "../../indexer/db/db.js";
34
40
  import { deactivateCanarySet, getActiveCanaries, getCanariesBySetId, insertCanaries, insertCycleMetrics, listActiveCanarySetIds, queryRecentCycleMetrics, } from "../../storage/repositories/canaries-repository.js";
41
+ import { closeDatabase, openExistingDatabase } from "../../storage/repositories/index-connection.js";
42
+ import { getAllEntries } from "../../storage/repositories/index-entries-repository.js";
43
+ import { searchFts } from "../../storage/repositories/index-fts-repository.js";
35
44
  import { computeBigramDiversity, DEFAULT_MAX_GENERATION } from "./anti-collapse.js";
36
45
  import { getAllRankScores } from "./salience.js";
37
46
  // ── Defaults (mirrored in config-schema.ts ImproveCollapseDetectorSchema) ────
@@ -40,7 +49,6 @@ export const DEFAULT_CANARY_K = 10;
40
49
  export const DEFAULT_WINDOW_CYCLES = 5;
41
50
  export const DEFAULT_RECALL_DROP_THRESHOLD = 0.15;
42
51
  export const DEFAULT_ENTROPY_DROP_THRESHOLD = 0.05;
43
- export const DEFAULT_CHURN_MIN_ACCEPTED = 25;
44
52
  export const DEFAULT_RETENTION_DAYS = 365;
45
53
  /** Deterministic bigram-diversity sample cap (cost bound at 10k assets). */
46
54
  const DIVERSITY_SAMPLE_CAP = 2000;
@@ -66,12 +74,13 @@ function buildCanaryQuery(entry) {
66
74
  function buildMintList(stateDb, entries, cfg) {
67
75
  const canaryCount = cfg.canaryCount ?? DEFAULT_CANARY_COUNT;
68
76
  const rankScores = getAllRankScores(stateDb);
69
- // NOTE: entryKey is stash-prefixed ("<stashDir>:type:name"); asset_salience
70
- // and the canary scoring both key on the bare "type:name" ref.
77
+ // Chunk-8 WI-8.5c: the canary anchor + salience correlation both key on the
78
+ // SHORT conceptId (`<stash-subdir>/<name>`, D-R2) — the same spelling the
79
+ // improve candidate refs and content xrefs now carry (post WI-8.5a).
71
80
  const candidates = entries
72
81
  .filter((e) => LEARNING_TYPES.has(e.entry.type))
73
82
  .map((e) => {
74
- const ref = makeAssetRef(e.entry.type, e.entry.name);
83
+ const ref = conceptIdFromTypeName(e.entry.type, e.entry.name);
75
84
  return { e, ref, score: rankScores.get(ref) ?? 0 };
76
85
  })
77
86
  .sort((a, b) => b.score - a.score || (a.ref < b.ref ? -1 : 1));
@@ -114,9 +123,10 @@ function newCanarySetId() {
114
123
  * mean the trend window never fills and recall reads as a fake 0).
115
124
  *
116
125
  * NEVER auto-refreshes: once minted the set is frozen until an explicit
117
- * `akm improve canary --refresh` — silent re-baselining is how a slow collapse
118
- * hides. Rows are read back BY OUR OWN set id (never "newest active") so a
119
- * concurrent mint in another process cannot relabel this run's metrics.
126
+ * `bun scripts/refresh-canary-set.ts --refresh` — silent re-baselining is how
127
+ * a slow collapse hides. Rows are read back BY OUR OWN set id (never "newest
128
+ * active") so a concurrent mint in another process cannot relabel this run's
129
+ * metrics.
120
130
  */
121
131
  export function ensureCanarySet(stateDb, indexDb, cfg, preloadedEntries) {
122
132
  const existing = getActiveCanaries(stateDb);
@@ -131,11 +141,11 @@ export function ensureCanarySet(stateDb, indexDb, cfg, preloadedEntries) {
131
141
  return { canarySetId, canaries: getCanariesBySetId(stateDb, canarySetId) };
132
142
  }
133
143
  /**
134
- * Explicit canary re-mint (the ONLY refresh path — `akm improve canary
135
- * --refresh`). Mint-first, deactivate-after: when the index is empty or
136
- * unreadable the current baseline is left untouched instead of destroyed.
137
- * Deactivates ALL other active sets (not just the newest) so stragglers from
138
- * an interrupted refresh can never resurrect.
144
+ * Explicit canary re-mint (the ONLY refresh path —
145
+ * `bun scripts/refresh-canary-set.ts --refresh`). Mint-first, deactivate-after:
146
+ * when the index is empty or unreadable the current baseline is left untouched
147
+ * instead of destroyed. Deactivates ALL other active sets (not just the
148
+ * newest) so stragglers from an interrupted refresh can never resurrect.
139
149
  */
140
150
  export function refreshCanarySet(stateDb, indexDb, cfg) {
141
151
  const minted = buildMintList(stateDb, getAllEntries(indexDb), cfg);
@@ -175,24 +185,36 @@ export function normHash(text) {
175
185
  return hash.toString(16);
176
186
  }
177
187
  /**
178
- * Score one canary against the live index, merge-following via `source_refs`:
179
- * a hit is the anchor ref itself OR any returned entry whose `source_refs`
180
- * frontmatter contains the anchor (ONE level — provenance dropped on a
181
- * second-generation merge is a miss by design; that IS the information loss).
188
+ * Score one canary against the live index, merge-following via canonical
189
+ * `xrefs`. A hit is the anchor ref itself or any returned entry whose
190
+ * provenance contains the anchor.
182
191
  * Returns the 0-based rank of the first hit, or -1.
183
192
  */
184
193
  function scoreCanary(indexDb, canary, k) {
185
194
  const results = searchFts(indexDb, canary.query, k);
195
+ const anchorConceptId = canaryConceptId(canary.anchor_ref);
186
196
  for (let i = 0; i < Math.min(results.length, k); i++) {
187
197
  const r = results[i];
188
- const ref = makeAssetRef(r.entry.type, r.entry.name);
189
- if (ref === canary.anchor_ref)
198
+ // Persisted canaries may be fully qualified after a state migration while
199
+ // index refs and xrefs remain short conceptIds. Compare identity, not display
200
+ // spelling, so migration alone cannot collapse recall to zero.
201
+ const ref = conceptIdFromTypeName(r.entry.type, r.entry.name);
202
+ if (ref === anchorConceptId)
190
203
  return i;
191
- if (r.entry.sourceRefs?.includes(canary.anchor_ref))
204
+ const provenance = r.entry.xrefs ?? [];
205
+ if (provenance.some((sourceRef) => canaryConceptId(sourceRef) === anchorConceptId))
192
206
  return i;
193
207
  }
194
208
  return -1;
195
209
  }
210
+ function canaryConceptId(ref) {
211
+ try {
212
+ return parseBundleRef(ref).conceptId;
213
+ }
214
+ catch {
215
+ return ref;
216
+ }
217
+ }
196
218
  /**
197
219
  * Compute one qualifying cycle's store-health snapshot. One `entries` scan +
198
220
  * `canaryCount` FTS queries; no LLM, no embedding model, no filesystem reads.
@@ -266,13 +288,17 @@ export function computeCycleMetrics(stateDb, indexDb, args) {
266
288
  distinct_content_ratio: learningTotal === 0 ? 1 : contentHashes.size / learningTotal,
267
289
  mean_bigram_diversity: diversityCount === 0 ? 1 : diversitySum / diversityCount,
268
290
  over_generation_count: overGeneration,
269
- accepted_actions: args.acceptedActions,
291
+ // Always 0 — the CHURN alert this fed was removed. The column is NOT NULL
292
+ // in a released migration body, so it is written rather than dropped.
293
+ accepted_actions: 0,
270
294
  merge_floor_violations: args.mergeFloorViolations,
271
295
  alerts_json: "[]",
272
296
  };
273
297
  }
274
298
  // ── Alert evaluation (pure) ───────────────────────────────────────────────────
275
299
  function median(values) {
300
+ if (values.length === 0)
301
+ return Number.NaN;
276
302
  const sorted = [...values].sort((a, b) => a - b);
277
303
  const mid = Math.floor(sorted.length / 2);
278
304
  return sorted.length % 2 === 0 ? (sorted[mid - 1] + sorted[mid]) / 2 : sorted[mid];
@@ -299,9 +325,11 @@ export function evaluateCollapseAlerts(history, current, cfg) {
299
325
  const hist = history.slice(-W);
300
326
  if (hist.length < W)
301
327
  return alerts; // no baseline yet
328
+ // Window is non-empty here: `windowCycles` is schema-bounded to ≥2 (default 5),
329
+ // so `hist.length >= W >= 2`. `windowStart` is the oldest row in the window.
330
+ const windowStart = hist[0];
302
331
  const recallDrop = cfg.recallDropThreshold ?? DEFAULT_RECALL_DROP_THRESHOLD;
303
332
  const entropyDrop = cfg.entropyDropThreshold ?? DEFAULT_ENTROPY_DROP_THRESHOLD;
304
- const churnMin = cfg.churnMinAcceptedActions ?? DEFAULT_CHURN_MIN_ACCEPTED;
305
333
  // COLLAPSE 1 — canary recall drop vs window median (median, not previous
306
334
  // cycle, so one noisy cycle can neither fire nor mask the alert).
307
335
  const medianRecall = median(hist.map((h) => h.mean_recall));
@@ -315,13 +343,13 @@ export function evaluateCollapseAlerts(history, current, cfg) {
315
343
  // COLLAPSE 2 — monotonic distinct-content-ratio decline over the window.
316
344
  const series = [...hist.map((h) => h.distinct_content_ratio), current.distinct_content_ratio];
317
345
  const monotonicNonIncreasing = series.every((v, i) => i === 0 || v <= series[i - 1]);
318
- const totalDecline = hist[0].distinct_content_ratio - current.distinct_content_ratio;
346
+ const totalDecline = windowStart.distinct_content_ratio - current.distinct_content_ratio;
319
347
  if (monotonicNonIncreasing && totalDecline >= entropyDrop) {
320
348
  alerts.push({
321
349
  kind: "collapse-entropy",
322
350
  detail: `distinct-content ratio declined monotonically by ${totalDecline.toFixed(3)} (≥${entropyDrop}) over ${W} cycles — store content is converging`,
323
351
  metrics: {
324
- windowStart: hist[0].distinct_content_ratio,
352
+ windowStart: windowStart.distinct_content_ratio,
325
353
  current: current.distinct_content_ratio,
326
354
  decline: totalDecline,
327
355
  },
@@ -329,10 +357,10 @@ export function evaluateCollapseAlerts(history, current, cfg) {
329
357
  }
330
358
  // COLLAPSE 3 — store shrinking BECAUSE of re-merging (not deletion hygiene).
331
359
  const maxStore = Math.max(...hist.map((h) => h.store_total));
332
- if (current.store_total < 0.8 * maxStore && current.over_generation_count > hist[0].over_generation_count) {
360
+ if (current.store_total < 0.8 * maxStore && current.over_generation_count > windowStart.over_generation_count) {
333
361
  alerts.push({
334
362
  kind: "collapse-shrink",
335
- detail: `store shrank >20% (${current.store_total} vs window max ${maxStore}) while over-generation count rose (${hist[0].over_generation_count} → ${current.over_generation_count})`,
363
+ detail: `store shrank >20% (${current.store_total} vs window max ${maxStore}) while over-generation count rose (${windowStart.over_generation_count} → ${current.over_generation_count})`,
336
364
  metrics: {
337
365
  storeTotal: current.store_total,
338
366
  windowMax: maxStore,
@@ -340,20 +368,6 @@ export function evaluateCollapseAlerts(history, current, cfg) {
340
368
  },
341
369
  });
342
370
  }
343
- // CHURN — real write volume, zero retrieval- or shape-visible movement.
344
- // Flatness is measured against the window MEDIAN (consistent with the
345
- // recall rule): endpoint-only comparison would call a window that swung
346
- // wildly but happened to land near its start "flat".
347
- const acceptedSum = hist.reduce((a, h) => a + h.accepted_actions, 0);
348
- const scoreFlat = Math.abs(current.mean_ndcg - median(hist.map((h) => h.mean_ndcg))) < 0.02;
349
- const entropyFlat = Math.abs(current.distinct_content_ratio - median(hist.map((h) => h.distinct_content_ratio))) < 0.02;
350
- if (acceptedSum >= churnMin && scoreFlat && entropyFlat) {
351
- alerts.push({
352
- kind: "churn",
353
- detail: `${acceptedSum} accepted actions over ${W} cycles with flat canary score and flat entropy — write volume with no retrieval-visible effect`,
354
- metrics: { acceptedSum, ndcgDelta: current.mean_ndcg - hist[0].mean_ndcg },
355
- });
356
- }
357
371
  return alerts;
358
372
  }
359
373
  // ── Orchestrator ─────────────────────────────────────────────────────────────
@@ -375,13 +389,12 @@ export function runCollapseDetector(args) {
375
389
  const db = indexDb;
376
390
  // Over-generation threshold mirrors the guard actually in effect —
377
391
  // reading the same config key keeps the two aligned when tuned.
378
- const antiCollapse = getImproveProcessConfig(args.config, "consolidate", args.improveProfile)?.antiCollapse;
392
+ const antiCollapse = getImproveProcessConfig("consolidate", args.improveProfile)?.antiCollapse;
379
393
  const maxGeneration = antiCollapse?.maxGeneration ?? DEFAULT_MAX_GENERATION;
380
394
  return withStateDb((stateDb) => {
381
395
  const row = computeCycleMetrics(stateDb, db, {
382
396
  runId: args.runId,
383
397
  pass: args.pass,
384
- acceptedActions: args.acceptedActions,
385
398
  mergeFloorViolations: args.mergeFloorViolations,
386
399
  cfg,
387
400
  maxGeneration,
@@ -6,7 +6,7 @@
6
6
  // no orchestrator coupling.
7
7
  import fs from "node:fs";
8
8
  import { parseFrontmatter } from "../../../core/asset/frontmatter.js";
9
- import { cacheHash } from "../dedup.js";
9
+ import { cacheHash } from "../content-hash.js";
10
10
  /**
11
11
  * Conservative chars-per-token estimate used when computing prompt budgets.
12
12
  * English text averages roughly 4 chars/token for most LLM tokenizers. We use
@@ -33,9 +33,9 @@ const PROMPT_OVERHEAD_TOKENS = 2_000;
33
33
  * chunk content.
34
34
  * - When the HTTP path is used (an LLM profile is selected), only the akm
35
35
  * system prompt and user prompt are sent, so the budget can be set to the
36
- * model's actual context length via profiles.llm[defaults.llm].contextLength.
36
+ * model's actual context length via the selected LLM engine's contextLength.
37
37
  *
38
- * Set profiles.llm[defaults.llm].contextLength in your config file to the
38
+ * Set the selected LLM engine's contextLength in your config file to the
39
39
  * model's actual context window to allow larger chunks on the HTTP path.
40
40
  */
41
41
  export const DEFAULT_CONTEXT_LENGTH_TOKENS = 4_096;
@@ -78,8 +78,9 @@ export function computeSafeChunkSize(contextLength, bodyTruncation, maxChunkSize
78
78
  * so the cost stays O(memories) inside the chunk loop.
79
79
  */
80
80
  export function buildChunkPrompt(sourceName, memories, chunkIndex, totalChunks, bodyTruncation, pendingProposalBodyHashes = new Set(), standardsContext = "") {
81
- const start = memories[0] ? `memory:${memories[0].name}` : "";
82
- const end = memories[memories.length - 1] ? `memory:${memories[memories.length - 1].name}` : "";
81
+ const start = memories[0] ? `memories/${memories[0].name}` : "";
82
+ const lastMemory = memories[memories.length - 1];
83
+ const end = lastMemory ? `memories/${lastMemory.name}` : "";
83
84
  const annotationsByIndex = [];
84
85
  const hotRefs = [];
85
86
  for (const m of memories) {
@@ -98,7 +99,7 @@ export function buildChunkPrompt(sourceName, memories, chunkIndex, totalChunks,
98
99
  const isAlreadyQueued = pendingProposalBodyHashes.has(bodyHash);
99
100
  annotationsByIndex.push({ isHot, isAlreadyQueued, body });
100
101
  if (isHot)
101
- hotRefs.push(`memory:${m.name}`);
102
+ hotRefs.push(`memories/${m.name}`);
102
103
  }
103
104
  const lines = [
104
105
  `Source: ${sourceName}`,
@@ -123,6 +124,7 @@ export function buildChunkPrompt(sourceName, memories, chunkIndex, totalChunks,
123
124
  }
124
125
  for (let i = 0; i < memories.length; i++) {
125
126
  const m = memories[i];
127
+ // `annotationsByIndex` has exactly one entry per memory (built in the loop above).
126
128
  const { isHot, isAlreadyQueued, body } = annotationsByIndex[i];
127
129
  const annotations = [];
128
130
  if (isHot)
@@ -130,7 +132,7 @@ export function buildChunkPrompt(sourceName, memories, chunkIndex, totalChunks,
130
132
  if (isAlreadyQueued)
131
133
  annotations.push("already queued");
132
134
  const annotationSuffix = annotations.length > 0 ? ` (${annotations.join("; ")})` : "";
133
- lines.push(`[${i + 1}] memory:${m.name}${annotationSuffix}`);
135
+ lines.push(`[${i + 1}] memories/${m.name}${annotationSuffix}`);
134
136
  lines.push(`Description: ${m.description || "(none)"}`);
135
137
  lines.push(`Tags: ${m.tags.length > 0 ? m.tags.join(", ") : "(none)"}`);
136
138
  lines.push("---");
@@ -22,7 +22,7 @@ export function isConsolidationEligibleMemoryName(name) {
22
22
  * consolidate flow already guards against unparseable memories elsewhere).
23
23
  *
24
24
  * Defends against four observed defect classes (see
25
- * `memory:akm-improve-critical-review-2026-05-20`):
25
+ * `memories/akm-improve-critical-review-2026-05-20`):
26
26
  * - LLM marks a memory contradicted then deletes (dangling contradictedBy)
27
27
  * - LLM merges two unrelated memories sharing a topic keyword
28
28
  * - LLM judges a recent durable design memo as "redundant"
@@ -40,25 +40,3 @@ export function isHotCapturedMemory(filePath) {
40
40
  return false;
41
41
  }
42
42
  }
43
- export function consolidateGuardStatus(filePath) {
44
- if (!fs.existsSync(filePath))
45
- return "missing";
46
- let content;
47
- try {
48
- content = fs.readFileSync(filePath, "utf8");
49
- }
50
- catch {
51
- return "unparseable";
52
- }
53
- let parsed;
54
- try {
55
- parsed = parseFrontmatter(content);
56
- }
57
- catch {
58
- return "unparseable";
59
- }
60
- const data = parsed.data;
61
- if (!data || Object.keys(data).length === 0)
62
- return "unparseable";
63
- return hasHotCaptureMode(data) ? "hot" : "safe";
64
- }
@@ -56,6 +56,10 @@ export function mergePlans(chunks, knownRefs) {
56
56
  mergeOp = { ...op, secondaries: filteredSecondaries };
57
57
  }
58
58
  }
59
+ if (mergeOp.secondaries.length > 1) {
60
+ warnings.push(`Merge: ${mergeOp.primary} proposed multiple secondaries; retaining one secondary for review.`);
61
+ mergeOp = { ...mergeOp, secondaries: mergeOp.secondaries.slice(0, 1) };
62
+ }
59
63
  // merge wins over delete
60
64
  if (deleteOps.has(mergeOp.primary)) {
61
65
  deleteOps.delete(mergeOp.primary);