nlm-memory 0.20.1 → 0.21.12

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 (475) hide show
  1. package/README.md +69 -12
  2. package/assets/replay-eval-dark.svg +26 -0
  3. package/assets/replay-eval-light.svg +26 -0
  4. package/dist/cli/digest.js +69 -4
  5. package/dist/cli/digest.js.map +1 -1
  6. package/dist/cli/nlm.d.ts +14 -0
  7. package/dist/cli/nlm.js +556 -71
  8. package/dist/cli/nlm.js.map +1 -1
  9. package/dist/cli/reprocess-job-adapters.d.ts +35 -0
  10. package/dist/cli/reprocess-job-adapters.js +80 -0
  11. package/dist/cli/reprocess-job-adapters.js.map +1 -0
  12. package/dist/cli/scope-backfill.d.ts +34 -0
  13. package/dist/cli/scope-backfill.js +237 -0
  14. package/dist/cli/scope-backfill.js.map +1 -0
  15. package/dist/cli/scope-coverage.d.ts +44 -0
  16. package/dist/cli/scope-coverage.js +208 -0
  17. package/dist/cli/scope-coverage.js.map +1 -0
  18. package/dist/cli/supersede.js +8 -7
  19. package/dist/cli/supersede.js.map +1 -1
  20. package/dist/core/actions/actions-log.d.ts +65 -8
  21. package/dist/core/actions/actions-log.js +134 -17
  22. package/dist/core/actions/actions-log.js.map +1 -1
  23. package/dist/core/actions/overlay.d.ts +11 -2
  24. package/dist/core/actions/overlay.js +18 -6
  25. package/dist/core/actions/overlay.js.map +1 -1
  26. package/dist/core/adapters/claude-code.d.ts +14 -0
  27. package/dist/core/adapters/claude-code.js +30 -0
  28. package/dist/core/adapters/claude-code.js.map +1 -1
  29. package/dist/core/adapters/from-source.js +11 -3
  30. package/dist/core/adapters/from-source.js.map +1 -1
  31. package/dist/core/adapters/fs-wiki-writer.d.ts +44 -0
  32. package/dist/core/adapters/fs-wiki-writer.js +132 -0
  33. package/dist/core/adapters/fs-wiki-writer.js.map +1 -0
  34. package/dist/core/adapters/hermes-agent.d.ts +15 -2
  35. package/dist/core/adapters/hermes-agent.js +57 -11
  36. package/dist/core/adapters/hermes-agent.js.map +1 -1
  37. package/dist/core/adapters/memory-wiki-writer.d.ts +8 -0
  38. package/dist/core/adapters/memory-wiki-writer.js +16 -0
  39. package/dist/core/adapters/memory-wiki-writer.js.map +1 -0
  40. package/dist/core/adapters/muse.d.ts +51 -0
  41. package/dist/core/adapters/muse.js +271 -0
  42. package/dist/core/adapters/muse.js.map +1 -0
  43. package/dist/core/adapters/opencode.d.ts +11 -4
  44. package/dist/core/adapters/opencode.js +41 -7
  45. package/dist/core/adapters/opencode.js.map +1 -1
  46. package/dist/core/alerts/alert-state.d.ts +17 -0
  47. package/dist/core/alerts/alert-state.js +45 -0
  48. package/dist/core/alerts/alert-state.js.map +1 -0
  49. package/dist/core/alerts/check-and-alert.d.ts +28 -0
  50. package/dist/core/alerts/check-and-alert.js +53 -0
  51. package/dist/core/alerts/check-and-alert.js.map +1 -0
  52. package/dist/core/alerts/drift-transition.d.ts +27 -0
  53. package/dist/core/alerts/drift-transition.js +56 -0
  54. package/dist/core/alerts/drift-transition.js.map +1 -0
  55. package/dist/core/alerts/embedder-transition.d.ts +23 -0
  56. package/dist/core/alerts/embedder-transition.js +40 -0
  57. package/dist/core/alerts/embedder-transition.js.map +1 -0
  58. package/dist/core/alerts/fire-alert.d.ts +24 -0
  59. package/dist/core/alerts/fire-alert.js +72 -0
  60. package/dist/core/alerts/fire-alert.js.map +1 -0
  61. package/dist/core/alerts/job-alert.d.ts +12 -0
  62. package/dist/core/alerts/job-alert.js +37 -0
  63. package/dist/core/alerts/job-alert.js.map +1 -0
  64. package/dist/core/alerts/types.d.ts +104 -0
  65. package/dist/core/alerts/types.js +11 -0
  66. package/dist/core/alerts/types.js.map +1 -0
  67. package/dist/core/alerts/wiki-alert.d.ts +15 -0
  68. package/dist/core/alerts/wiki-alert.js +31 -0
  69. package/dist/core/alerts/wiki-alert.js.map +1 -0
  70. package/dist/core/classifier/prompt.d.ts +13 -0
  71. package/dist/core/classifier/prompt.js +52 -2
  72. package/dist/core/classifier/prompt.js.map +1 -1
  73. package/dist/core/dataset/build-dataset.d.ts +16 -1
  74. package/dist/core/dataset/build-dataset.js +46 -13
  75. package/dist/core/dataset/build-dataset.js.map +1 -1
  76. package/dist/core/digest/compose.d.ts +11 -3
  77. package/dist/core/digest/compose.js +70 -17
  78. package/dist/core/digest/compose.js.map +1 -1
  79. package/dist/core/digest/hook-injection.d.ts +43 -0
  80. package/dist/core/digest/hook-injection.js +87 -0
  81. package/dist/core/digest/hook-injection.js.map +1 -0
  82. package/dist/core/digest/hook-version-parity.d.ts +31 -0
  83. package/dist/core/digest/hook-version-parity.js +56 -0
  84. package/dist/core/digest/hook-version-parity.js.map +1 -0
  85. package/dist/core/embedding/pg-embed-backfill.js +1 -1
  86. package/dist/core/embedding/pg-embed-backfill.js.map +1 -1
  87. package/dist/core/exemplars/capture-from-session.d.ts +2 -1
  88. package/dist/core/exemplars/capture-from-session.js +4 -4
  89. package/dist/core/exemplars/capture-from-session.js.map +1 -1
  90. package/dist/core/exemplars/embed-backfill.d.ts +9 -0
  91. package/dist/core/exemplars/embed-backfill.js +9 -1
  92. package/dist/core/exemplars/embed-backfill.js.map +1 -1
  93. package/dist/core/exemplars/extract-exemplar.d.ts +2 -0
  94. package/dist/core/exemplars/extract-exemplar.js +7 -1
  95. package/dist/core/exemplars/extract-exemplar.js.map +1 -1
  96. package/dist/core/exemplars/ingest-exemplar.d.ts +1 -0
  97. package/dist/core/exemplars/ingest-exemplar.js +1 -0
  98. package/dist/core/exemplars/ingest-exemplar.js.map +1 -1
  99. package/dist/core/exemplars/recall-code.d.ts +1 -1
  100. package/dist/core/exemplars/recall-code.js +2 -2
  101. package/dist/core/exemplars/recall-code.js.map +1 -1
  102. package/dist/core/facts/backfill-facts.d.ts +1 -1
  103. package/dist/core/facts/backfill-facts.js +4 -4
  104. package/dist/core/facts/backfill-facts.js.map +1 -1
  105. package/dist/core/facts/embed-backfill.d.ts +54 -0
  106. package/dist/core/facts/embed-backfill.js +109 -0
  107. package/dist/core/facts/embed-backfill.js.map +1 -0
  108. package/dist/core/facts/reconcile-facts.d.ts +42 -0
  109. package/dist/core/facts/reconcile-facts.js +133 -0
  110. package/dist/core/facts/reconcile-facts.js.map +1 -0
  111. package/dist/core/health/embed-failure-state.d.ts +4 -0
  112. package/dist/core/health/embed-failure-state.js +12 -0
  113. package/dist/core/health/embed-failure-state.js.map +1 -0
  114. package/dist/core/health/warmup-retry.d.ts +27 -0
  115. package/dist/core/health/warmup-retry.js +53 -0
  116. package/dist/core/health/warmup-retry.js.map +1 -0
  117. package/dist/core/health/warmup-state.d.ts +15 -0
  118. package/dist/core/health/warmup-state.js +15 -1
  119. package/dist/core/health/warmup-state.js.map +1 -1
  120. package/dist/core/hook/cite-memo.d.ts +11 -7
  121. package/dist/core/hook/cite-memo.js +25 -17
  122. package/dist/core/hook/cite-memo.js.map +1 -1
  123. package/dist/core/hook/claude-settings.d.ts +1 -1
  124. package/dist/core/hook/claude-settings.js +0 -1
  125. package/dist/core/hook/claude-settings.js.map +1 -1
  126. package/dist/core/hook/hook-log.d.ts +13 -2
  127. package/dist/core/hook/hook-log.js +16 -8
  128. package/dist/core/hook/hook-log.js.map +1 -1
  129. package/dist/core/hook/memo.d.ts +10 -6
  130. package/dist/core/hook/memo.js +25 -17
  131. package/dist/core/hook/memo.js.map +1 -1
  132. package/dist/core/hook/pointer-block.d.ts +8 -1
  133. package/dist/core/hook/pointer-block.js +17 -4
  134. package/dist/core/hook/pointer-block.js.map +1 -1
  135. package/dist/core/hook/resolve-conversation-by-query.d.ts +6 -5
  136. package/dist/core/hook/resolve-conversation-by-query.js +24 -12
  137. package/dist/core/hook/resolve-conversation-by-query.js.map +1 -1
  138. package/dist/core/ingest/backfill-derivables.d.ts +92 -0
  139. package/dist/core/ingest/backfill-derivables.js +175 -0
  140. package/dist/core/ingest/backfill-derivables.js.map +1 -0
  141. package/dist/core/ingest/ingest-session.d.ts +1 -1
  142. package/dist/core/ingest/ingest-session.js +23 -3
  143. package/dist/core/ingest/ingest-session.js.map +1 -1
  144. package/dist/core/ingest/reclassify-oversized.d.ts +1 -1
  145. package/dist/core/ingest/reclassify-oversized.js +8 -2
  146. package/dist/core/ingest/reclassify-oversized.js.map +1 -1
  147. package/dist/core/ingest/reprocess.d.ts +1 -1
  148. package/dist/core/ingest/reprocess.js +7 -2
  149. package/dist/core/ingest/reprocess.js.map +1 -1
  150. package/dist/core/ingest/transcript-derivables.d.ts +27 -0
  151. package/dist/core/ingest/transcript-derivables.js +138 -0
  152. package/dist/core/ingest/transcript-derivables.js.map +1 -0
  153. package/dist/core/jobs/job-supervisor.d.ts +168 -0
  154. package/dist/core/jobs/job-supervisor.js +335 -0
  155. package/dist/core/jobs/job-supervisor.js.map +1 -0
  156. package/dist/core/learner/model.d.ts +63 -0
  157. package/dist/core/learner/model.js +30 -0
  158. package/dist/core/learner/model.js.map +1 -0
  159. package/dist/core/learner/service.d.ts +42 -0
  160. package/dist/core/learner/service.js +74 -0
  161. package/dist/core/learner/service.js.map +1 -0
  162. package/dist/core/learner/summary.d.ts +28 -0
  163. package/dist/core/learner/summary.js +70 -0
  164. package/dist/core/learner/summary.js.map +1 -0
  165. package/dist/core/learner/validate.d.ts +18 -0
  166. package/dist/core/learner/validate.js +95 -0
  167. package/dist/core/learner/validate.js.map +1 -0
  168. package/dist/core/metrics/re-derivation.d.ts +31 -2
  169. package/dist/core/metrics/re-derivation.js +36 -4
  170. package/dist/core/metrics/re-derivation.js.map +1 -1
  171. package/dist/core/outcome/coverage.d.ts +33 -0
  172. package/dist/core/outcome/coverage.js +46 -0
  173. package/dist/core/outcome/coverage.js.map +1 -0
  174. package/dist/core/outcome/rollup.d.ts +33 -0
  175. package/dist/core/outcome/rollup.js +113 -0
  176. package/dist/core/outcome/rollup.js.map +1 -0
  177. package/dist/core/providers/provider-registry.d.ts +40 -23
  178. package/dist/core/providers/provider-registry.js +99 -81
  179. package/dist/core/providers/provider-registry.js.map +1 -1
  180. package/dist/core/recall/citation-log.d.ts +10 -5
  181. package/dist/core/recall/citation-log.js +21 -10
  182. package/dist/core/recall/citation-log.js.map +1 -1
  183. package/dist/core/recall/hook-recall-log.d.ts +7 -4
  184. package/dist/core/recall/hook-recall-log.js +14 -8
  185. package/dist/core/recall/hook-recall-log.js.map +1 -1
  186. package/dist/core/recall/miss-log.d.ts +7 -4
  187. package/dist/core/recall/miss-log.js +18 -11
  188. package/dist/core/recall/miss-log.js.map +1 -1
  189. package/dist/core/recall/query-log.d.ts +8 -5
  190. package/dist/core/recall/query-log.js +16 -9
  191. package/dist/core/recall/query-log.js.map +1 -1
  192. package/dist/core/recall/recall-service.d.ts +10 -1
  193. package/dist/core/recall/recall-service.js +31 -12
  194. package/dist/core/recall/recall-service.js.map +1 -1
  195. package/dist/core/recall/recent-log.d.ts +6 -1
  196. package/dist/core/recall/recent-log.js +13 -5
  197. package/dist/core/recall/recent-log.js.map +1 -1
  198. package/dist/core/recall/related-concepts.d.ts +29 -0
  199. package/dist/core/recall/related-concepts.js +67 -0
  200. package/dist/core/recall/related-concepts.js.map +1 -0
  201. package/dist/core/recall/related-exemplars.d.ts +1 -1
  202. package/dist/core/recall/related-exemplars.js +2 -2
  203. package/dist/core/recall/related-exemplars.js.map +1 -1
  204. package/dist/core/recall/related-facts.d.ts +1 -1
  205. package/dist/core/recall/related-facts.js +3 -3
  206. package/dist/core/recall/related-facts.js.map +1 -1
  207. package/dist/core/recall-facts/fact-query-log.d.ts +8 -4
  208. package/dist/core/recall-facts/fact-query-log.js +16 -8
  209. package/dist/core/recall-facts/fact-query-log.js.map +1 -1
  210. package/dist/core/recall-facts/fact-recall-service.d.ts +2 -2
  211. package/dist/core/recall-facts/fact-recall-service.js +13 -12
  212. package/dist/core/recall-facts/fact-recall-service.js.map +1 -1
  213. package/dist/core/scheduler/scan-once.js +15 -12
  214. package/dist/core/scheduler/scan-once.js.map +1 -1
  215. package/dist/core/scheduler/scheduler.d.ts +3 -0
  216. package/dist/core/scheduler/scheduler.js +45 -10
  217. package/dist/core/scheduler/scheduler.js.map +1 -1
  218. package/dist/core/scope/alias-map.d.ts +10 -0
  219. package/dist/core/scope/alias-map.js +41 -0
  220. package/dist/core/scope/alias-map.js.map +1 -0
  221. package/dist/core/scope/derive-scope.d.ts +8 -0
  222. package/dist/core/scope/derive-scope.js +54 -0
  223. package/dist/core/scope/derive-scope.js.map +1 -0
  224. package/dist/core/scope/scope-clause.d.ts +16 -0
  225. package/dist/core/scope/scope-clause.js +21 -0
  226. package/dist/core/scope/scope-clause.js.map +1 -0
  227. package/dist/core/scope/stamp-flag.d.ts +1 -0
  228. package/dist/core/scope/stamp-flag.js +4 -0
  229. package/dist/core/scope/stamp-flag.js.map +1 -0
  230. package/dist/core/signals/code-signal.d.ts +1 -0
  231. package/dist/core/signals/code-signal.js +1 -0
  232. package/dist/core/signals/code-signal.js.map +1 -1
  233. package/dist/core/signals/failure-mode-recall.d.ts +1 -1
  234. package/dist/core/signals/failure-mode-recall.js +2 -2
  235. package/dist/core/signals/failure-mode-recall.js.map +1 -1
  236. package/dist/core/signals/ingest-signal.d.ts +1 -1
  237. package/dist/core/signals/ingest-signal.js +3 -1
  238. package/dist/core/signals/ingest-signal.js.map +1 -1
  239. package/dist/core/signals/stamp-scope.d.ts +18 -0
  240. package/dist/core/signals/stamp-scope.js +28 -0
  241. package/dist/core/signals/stamp-scope.js.map +1 -0
  242. package/dist/core/sources/source-registry.d.ts +49 -28
  243. package/dist/core/sources/source-registry.js +113 -70
  244. package/dist/core/sources/source-registry.js.map +1 -1
  245. package/dist/core/storage/pg-code-exemplar-store.d.ts +19 -10
  246. package/dist/core/storage/pg-code-exemplar-store.js +62 -27
  247. package/dist/core/storage/pg-code-exemplar-store.js.map +1 -1
  248. package/dist/core/storage/pg-entity-store.d.ts +6 -1
  249. package/dist/core/storage/pg-entity-store.js +33 -18
  250. package/dist/core/storage/pg-entity-store.js.map +1 -1
  251. package/dist/core/storage/pg-fact-ingest.d.ts +1 -1
  252. package/dist/core/storage/pg-fact-ingest.js +10 -7
  253. package/dist/core/storage/pg-fact-ingest.js.map +1 -1
  254. package/dist/core/storage/pg-fact-store.d.ts +29 -17
  255. package/dist/core/storage/pg-fact-store.js +99 -46
  256. package/dist/core/storage/pg-fact-store.js.map +1 -1
  257. package/dist/core/storage/pg-learner-store.d.ts +27 -0
  258. package/dist/core/storage/pg-learner-store.js +174 -0
  259. package/dist/core/storage/pg-learner-store.js.map +1 -0
  260. package/dist/core/storage/pg-session-store.d.ts +25 -21
  261. package/dist/core/storage/pg-session-store.js +186 -114
  262. package/dist/core/storage/pg-session-store.js.map +1 -1
  263. package/dist/core/storage/pg-signal-store.d.ts +10 -5
  264. package/dist/core/storage/pg-signal-store.js +26 -13
  265. package/dist/core/storage/pg-signal-store.js.map +1 -1
  266. package/dist/core/storage/pg-storage.d.ts +4 -0
  267. package/dist/core/storage/pg-storage.js +6 -0
  268. package/dist/core/storage/pg-storage.js.map +1 -1
  269. package/dist/core/storage/pg-workstream-store.d.ts +17 -11
  270. package/dist/core/storage/pg-workstream-store.js +47 -29
  271. package/dist/core/storage/pg-workstream-store.js.map +1 -1
  272. package/dist/core/storage/sqlite-code-exemplar-store.d.ts +24 -10
  273. package/dist/core/storage/sqlite-code-exemplar-store.js +86 -40
  274. package/dist/core/storage/sqlite-code-exemplar-store.js.map +1 -1
  275. package/dist/core/storage/sqlite-entity-store.d.ts +8 -1
  276. package/dist/core/storage/sqlite-entity-store.js +46 -27
  277. package/dist/core/storage/sqlite-entity-store.js.map +1 -1
  278. package/dist/core/storage/sqlite-fact-store.d.ts +45 -19
  279. package/dist/core/storage/sqlite-fact-store.js +175 -64
  280. package/dist/core/storage/sqlite-fact-store.js.map +1 -1
  281. package/dist/core/storage/sqlite-learner-store.d.ts +33 -0
  282. package/dist/core/storage/sqlite-learner-store.js +178 -0
  283. package/dist/core/storage/sqlite-learner-store.js.map +1 -0
  284. package/dist/core/storage/sqlite-outcome-store.d.ts +104 -0
  285. package/dist/core/storage/sqlite-outcome-store.js +211 -0
  286. package/dist/core/storage/sqlite-outcome-store.js.map +1 -0
  287. package/dist/core/storage/sqlite-session-store.d.ts +50 -21
  288. package/dist/core/storage/sqlite-session-store.js +233 -149
  289. package/dist/core/storage/sqlite-session-store.js.map +1 -1
  290. package/dist/core/storage/sqlite-signal-store.d.ts +12 -5
  291. package/dist/core/storage/sqlite-signal-store.js +29 -15
  292. package/dist/core/storage/sqlite-signal-store.js.map +1 -1
  293. package/dist/core/storage/sqlite-storage.d.ts +4 -0
  294. package/dist/core/storage/sqlite-storage.js +10 -2
  295. package/dist/core/storage/sqlite-storage.js.map +1 -1
  296. package/dist/core/storage/sqlite-workstream-store.d.ts +17 -11
  297. package/dist/core/storage/sqlite-workstream-store.js +53 -31
  298. package/dist/core/storage/sqlite-workstream-store.js.map +1 -1
  299. package/dist/core/storage/supersedence-log.d.ts +10 -7
  300. package/dist/core/storage/supersedence-log.js +21 -14
  301. package/dist/core/storage/supersedence-log.js.map +1 -1
  302. package/dist/core/telemetry/probe-filter.d.ts +35 -0
  303. package/dist/core/telemetry/probe-filter.js +56 -0
  304. package/dist/core/telemetry/probe-filter.js.map +1 -0
  305. package/dist/core/tenancy/default-team.d.ts +6 -0
  306. package/dist/core/tenancy/default-team.js +7 -0
  307. package/dist/core/tenancy/default-team.js.map +1 -0
  308. package/dist/core/tenancy/hosted-mode.d.ts +9 -0
  309. package/dist/core/tenancy/hosted-mode.js +12 -0
  310. package/dist/core/tenancy/hosted-mode.js.map +1 -0
  311. package/dist/core/tenancy/team-auth.d.ts +16 -0
  312. package/dist/core/tenancy/team-auth.js +22 -0
  313. package/dist/core/tenancy/team-auth.js.map +1 -0
  314. package/dist/core/tenancy/team-token-store.d.ts +45 -0
  315. package/dist/core/tenancy/team-token-store.js +52 -0
  316. package/dist/core/tenancy/team-token-store.js.map +1 -0
  317. package/dist/core/tenancy/tenant-clause.d.ts +37 -0
  318. package/dist/core/tenancy/tenant-clause.js +11 -0
  319. package/dist/core/tenancy/tenant-clause.js.map +1 -0
  320. package/dist/core/tenancy/tenant-state-path.d.ts +28 -0
  321. package/dist/core/tenancy/tenant-state-path.js +49 -0
  322. package/dist/core/tenancy/tenant-state-path.js.map +1 -0
  323. package/dist/core/update-check/check.d.ts +6 -0
  324. package/dist/core/update-check/check.js +35 -0
  325. package/dist/core/update-check/check.js.map +1 -1
  326. package/dist/core/wiki/project.d.ts +17 -0
  327. package/dist/core/wiki/project.js +37 -0
  328. package/dist/core/wiki/project.js.map +1 -0
  329. package/dist/core/wiki/reconcile.d.ts +15 -0
  330. package/dist/core/wiki/reconcile.js +14 -0
  331. package/dist/core/wiki/reconcile.js.map +1 -0
  332. package/dist/core/wiki/render.d.ts +5 -0
  333. package/dist/core/wiki/render.js +84 -0
  334. package/dist/core/wiki/render.js.map +1 -0
  335. package/dist/core/wiki/rollup.d.ts +28 -0
  336. package/dist/core/wiki/rollup.js +91 -0
  337. package/dist/core/wiki/rollup.js.map +1 -0
  338. package/dist/core/wiki/select.d.ts +8 -0
  339. package/dist/core/wiki/select.js +7 -0
  340. package/dist/core/wiki/select.js.map +1 -0
  341. package/dist/core/wiki/slug.d.ts +36 -0
  342. package/dist/core/wiki/slug.js +71 -0
  343. package/dist/core/wiki/slug.js.map +1 -0
  344. package/dist/core/wiki/types.d.ts +37 -0
  345. package/dist/core/wiki/types.js +2 -0
  346. package/dist/core/wiki/types.js.map +1 -0
  347. package/dist/core/work-digest/build-work-digest.d.ts +1 -1
  348. package/dist/core/work-digest/build-work-digest.js +3 -3
  349. package/dist/core/work-digest/build-work-digest.js.map +1 -1
  350. package/dist/core/workstream/bind.d.ts +3 -2
  351. package/dist/core/workstream/bind.js +29 -10
  352. package/dist/core/workstream/bind.js.map +1 -1
  353. package/dist/core/workstream/model.d.ts +1 -0
  354. package/dist/core/workstream/model.js.map +1 -1
  355. package/dist/core/workstream/rollup.d.ts +1 -1
  356. package/dist/core/workstream/rollup.js +6 -6
  357. package/dist/core/workstream/rollup.js.map +1 -1
  358. package/dist/hook/hook-helpers.d.ts +14 -0
  359. package/dist/hook/hook-helpers.js +29 -2
  360. package/dist/hook/hook-helpers.js.map +1 -1
  361. package/dist/hook/pre-compact-hook.js +8 -5
  362. package/dist/hook/pre-compact-hook.js.map +1 -1
  363. package/dist/hook/prompt-recall-hook.d.ts +7 -3
  364. package/dist/hook/prompt-recall-hook.js +35 -20
  365. package/dist/hook/prompt-recall-hook.js.map +1 -1
  366. package/dist/hook/recall-over-http.d.ts +28 -3
  367. package/dist/hook/recall-over-http.js +58 -12
  368. package/dist/hook/recall-over-http.js.map +1 -1
  369. package/dist/hook/session-end-hook.js +7 -5
  370. package/dist/hook/session-end-hook.js.map +1 -1
  371. package/dist/hook/session-start-hook.d.ts +14 -1
  372. package/dist/hook/session-start-hook.js +57 -16
  373. package/dist/hook/session-start-hook.js.map +1 -1
  374. package/dist/hook/stop-hook.js +11 -8
  375. package/dist/hook/stop-hook.js.map +1 -1
  376. package/dist/http/app.d.ts +47 -3
  377. package/dist/http/app.js +379 -132
  378. package/dist/http/app.js.map +1 -1
  379. package/dist/install/claude-code.d.ts +17 -0
  380. package/dist/install/claude-code.js +44 -5
  381. package/dist/install/claude-code.js.map +1 -1
  382. package/dist/install/codex.d.ts +23 -2
  383. package/dist/install/codex.js +111 -14
  384. package/dist/install/codex.js.map +1 -1
  385. package/dist/install/cursor.d.ts +2 -2
  386. package/dist/install/cursor.js +7 -7
  387. package/dist/install/cursor.js.map +1 -1
  388. package/dist/install/hermes.d.ts +8 -0
  389. package/dist/install/hermes.js +28 -5
  390. package/dist/install/hermes.js.map +1 -1
  391. package/dist/install/local-source.d.ts +20 -0
  392. package/dist/install/local-source.js +28 -0
  393. package/dist/install/local-source.js.map +1 -0
  394. package/dist/install/mcp-block.d.ts +77 -0
  395. package/dist/install/mcp-block.js +99 -0
  396. package/dist/install/mcp-block.js.map +1 -0
  397. package/dist/install/pi.d.ts +26 -0
  398. package/dist/install/pi.js +43 -0
  399. package/dist/install/pi.js.map +1 -1
  400. package/dist/install/setup.js +6 -0
  401. package/dist/install/setup.js.map +1 -1
  402. package/dist/install/windsurf.d.ts +2 -2
  403. package/dist/install/windsurf.js +7 -7
  404. package/dist/install/windsurf.js.map +1 -1
  405. package/dist/llm/classifier-box.d.ts +5 -0
  406. package/dist/llm/classifier-box.js +5 -0
  407. package/dist/llm/classifier-box.js.map +1 -1
  408. package/dist/mcp/server.d.ts +94 -15
  409. package/dist/mcp/server.js +402 -79
  410. package/dist/mcp/server.js.map +1 -1
  411. package/dist/ports/clock.d.ts +12 -0
  412. package/dist/ports/clock.js +10 -0
  413. package/dist/ports/clock.js.map +1 -0
  414. package/dist/ports/code-exemplar-store.d.ts +13 -13
  415. package/dist/ports/entity-store.d.ts +5 -1
  416. package/dist/ports/fact-store.d.ts +0 -0
  417. package/dist/ports/fact-store.js +0 -0
  418. package/dist/ports/fact-store.js.map +1 -1
  419. package/dist/ports/learner-store.d.ts +80 -0
  420. package/dist/ports/learner-store.js +19 -0
  421. package/dist/ports/learner-store.js.map +1 -0
  422. package/dist/ports/outcome.d.ts +85 -0
  423. package/dist/ports/outcome.js +11 -0
  424. package/dist/ports/outcome.js.map +1 -0
  425. package/dist/ports/session-store.d.ts +20 -20
  426. package/dist/ports/session-store.js +5 -0
  427. package/dist/ports/session-store.js.map +1 -1
  428. package/dist/ports/signal-store.d.ts +12 -8
  429. package/dist/ports/spawn-child.d.ts +14 -0
  430. package/dist/ports/spawn-child.js +10 -0
  431. package/dist/ports/spawn-child.js.map +1 -0
  432. package/dist/ports/storage.d.ts +6 -0
  433. package/dist/ports/transcript-adapter.d.ts +11 -0
  434. package/dist/ports/wiki-writer.d.ts +19 -0
  435. package/dist/ports/wiki-writer.js +12 -0
  436. package/dist/ports/wiki-writer.js.map +1 -0
  437. package/dist/ports/workstream-store.d.ts +20 -12
  438. package/dist/shared/net.d.ts +3 -0
  439. package/dist/shared/net.js +4 -0
  440. package/dist/shared/net.js.map +1 -0
  441. package/dist/shared/types.d.ts +55 -0
  442. package/dist/shared/types.js +4 -1
  443. package/dist/shared/types.js.map +1 -1
  444. package/dist/shared/version.d.ts +9 -0
  445. package/dist/shared/version.js +11 -0
  446. package/dist/shared/version.js.map +1 -0
  447. package/dist/ui/assets/index-D6F3xAis.js +11 -0
  448. package/dist/ui/index.html +1 -1
  449. package/migrations/029_project_scope.sql +21 -0
  450. package/migrations/032_session_derivables.sql +11 -0
  451. package/migrations/033_actions_kind_check.sql +58 -0
  452. package/migrations/034_tenancy_teams_and_stamps.sql +40 -0
  453. package/migrations/035_tenancy_entity_rekey.sql +75 -0
  454. package/migrations/036_tenant_name_uniqueness.sql +59 -0
  455. package/migrations/037_sessions_covering_index.sql +25 -0
  456. package/migrations/038_sources_muse.sql +33 -0
  457. package/migrations/039_learner_evidence.sql +51 -0
  458. package/migrations/pg/030_project_scope.sql +23 -0
  459. package/migrations/pg/031_widen_session_edges_kind.sql +11 -0
  460. package/migrations/pg/032_session_derivables.sql +17 -0
  461. package/migrations/pg/033_actions_kind_check.sql +17 -0
  462. package/migrations/pg/034_tenancy.sql +77 -0
  463. package/migrations/pg/035_tenant_name_uniqueness.sql +15 -0
  464. package/migrations/pg/036_sources_muse.sql +12 -0
  465. package/migrations/pg/037_learner_evidence.sql +55 -0
  466. package/nlm/index.js +258 -59
  467. package/package.json +10 -5
  468. package/plugin/.codex-plugin/plugin.json +1 -1
  469. package/plugin/scripts/prompt-recall-hook.mjs +256 -58
  470. package/plugin/scripts/session-start-hook.mjs +283 -55
  471. package/plugin/scripts/stop-hook.mjs +199 -38
  472. package/dist/hook/subagent-start-hook.d.ts +0 -28
  473. package/dist/hook/subagent-start-hook.js +0 -81
  474. package/dist/hook/subagent-start-hook.js.map +0 -1
  475. package/dist/ui/assets/index-CMpQkbQy.js +0 -11
@@ -0,0 +1,80 @@
1
+ /**
2
+ * Real (non-core, side-effectful) adapters for JobSupervisor's reprocess
3
+ * job — the daemon composition root (`nlm start`, src/cli/nlm.ts) wires
4
+ * these; core/jobs/job-supervisor.ts only ever sees the ports (@ports/
5
+ * clock.js, @ports/spawn-child.js). Thin and unremarkable by design (Task 1
6
+ * report): no logic worth unit-testing beyond what job-supervisor.test.ts
7
+ * already covers against fakes of these same shapes.
8
+ */
9
+ import { spawn } from "node:child_process";
10
+ /** Date.now() + a ref'd setInterval — JobSupervisor's stall-check interval
11
+ * is meant to live for the whole daemon process, so it is not unref'd. */
12
+ export const realClock = {
13
+ now: () => Date.now(),
14
+ setInterval: (fn, ms) => {
15
+ setInterval(fn, ms);
16
+ },
17
+ };
18
+ /**
19
+ * Spawns `node <nlm.js> reprocess -v <args>` and line-buffers stdout+stderr
20
+ * into a single onLine stream (reprocess's -v progress lines go to stderr
21
+ * per the `reprocess` command's own onProgress wiring in nlm.ts; combining
22
+ * both means JobSupervisor never needs to care which fd a future output
23
+ * change lands on).
24
+ *
25
+ * Args are always passed as separate argv entries to child_process.spawn,
26
+ * never through a shell — a caller-supplied arg containing shell
27
+ * metacharacters is just one literal argv element to the child, nothing it
28
+ * can escape into.
29
+ */
30
+ export function createReprocessSpawnChild(opts) {
31
+ return (args) => {
32
+ const child = spawn(opts.execPath, [opts.nlmScriptPath, "reprocess", "-v", ...args], {
33
+ stdio: ["ignore", "pipe", "pipe"],
34
+ });
35
+ let lineCb = null;
36
+ let exitCb = null;
37
+ // Separate buffers per stream: stdout and stderr are independent byte
38
+ // streams that can each deliver a partial (no-newline-yet) chunk in
39
+ // either order. A single shared buffer would let an in-flight partial
40
+ // line on one fd get spliced together with an unrelated chunk that
41
+ // lands on the other fd before the first line's newline arrives.
42
+ const makeFeed = (buf) => (chunk) => {
43
+ buf.s += chunk.toString("utf8");
44
+ let idx;
45
+ while ((idx = buf.s.indexOf("\n")) !== -1) {
46
+ const line = buf.s.slice(0, idx);
47
+ buf.s = buf.s.slice(idx + 1);
48
+ lineCb?.(line);
49
+ }
50
+ };
51
+ child.stdout?.on("data", makeFeed({ s: "" }));
52
+ child.stderr?.on("data", makeFeed({ s: "" }));
53
+ // A spawn-level error (e.g. ENOENT on a bad execPath/script path) may
54
+ // fire "error" without a normal "exit" ever following — without
55
+ // surfacing it as an exit, JobSupervisor would sit in "running" forever
56
+ // instead of applying its restart/exhaust policy. Node's own docs say
57
+ // "exit" can still follow "error" in some cases, so this can call
58
+ // exitCb twice; that's harmless because job-supervisor.ts's
59
+ // spawnAndWire nulls out `this.child` after the first exit and its
60
+ // identity guard drops every callback after that.
61
+ child.on("exit", (code) => {
62
+ exitCb?.(code);
63
+ });
64
+ child.on("error", () => {
65
+ exitCb?.(1);
66
+ });
67
+ return {
68
+ onLine: (cb) => {
69
+ lineCb = cb;
70
+ },
71
+ onExit: (cb) => {
72
+ exitCb = cb;
73
+ },
74
+ kill: () => {
75
+ child.kill();
76
+ },
77
+ };
78
+ };
79
+ }
80
+ //# sourceMappingURL=reprocess-job-adapters.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"reprocess-job-adapters.js","sourceRoot":"","sources":["../../src/cli/reprocess-job-adapters.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,OAAO,EAAE,KAAK,EAAE,MAAM,oBAAoB,CAAC;AAI3C;2EAC2E;AAC3E,MAAM,CAAC,MAAM,SAAS,GAAU;IAC9B,GAAG,EAAE,GAAG,EAAE,CAAC,IAAI,CAAC,GAAG,EAAE;IACrB,WAAW,EAAE,CAAC,EAAE,EAAE,EAAE,EAAE,EAAE;QACtB,WAAW,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC;IACtB,CAAC;CACF,CAAC;AAYF;;;;;;;;;;;GAWG;AACH,MAAM,UAAU,yBAAyB,CAAC,IAA2B;IACnE,OAAO,CAAC,IAAc,EAAe,EAAE;QACrC,MAAM,KAAK,GAAG,KAAK,CAAC,IAAI,CAAC,QAAQ,EAAE,CAAC,IAAI,CAAC,aAAa,EAAE,WAAW,EAAE,IAAI,EAAE,GAAG,IAAI,CAAC,EAAE;YACnF,KAAK,EAAE,CAAC,QAAQ,EAAE,MAAM,EAAE,MAAM,CAAC;SAClC,CAAC,CAAC;QAEH,IAAI,MAAM,GAAoC,IAAI,CAAC;QACnD,IAAI,MAAM,GAA2C,IAAI,CAAC;QAC1D,sEAAsE;QACtE,oEAAoE;QACpE,sEAAsE;QACtE,mEAAmE;QACnE,iEAAiE;QACjE,MAAM,QAAQ,GAAG,CAAC,GAAkB,EAAE,EAAE,CAAC,CAAC,KAAa,EAAQ,EAAE;YAC/D,GAAG,CAAC,CAAC,IAAI,KAAK,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAC;YAChC,IAAI,GAAW,CAAC;YAChB,OAAO,CAAC,GAAG,GAAG,GAAG,CAAC,CAAC,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC;gBAC1C,MAAM,IAAI,GAAG,GAAG,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,EAAE,GAAG,CAAC,CAAC;gBACjC,GAAG,CAAC,CAAC,GAAG,GAAG,CAAC,CAAC,CAAC,KAAK,CAAC,GAAG,GAAG,CAAC,CAAC,CAAC;gBAC7B,MAAM,EAAE,CAAC,IAAI,CAAC,CAAC;YACjB,CAAC;QACH,CAAC,CAAC;QACF,KAAK,CAAC,MAAM,EAAE,EAAE,CAAC,MAAM,EAAE,QAAQ,CAAC,EAAE,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC;QAC9C,KAAK,CAAC,MAAM,EAAE,EAAE,CAAC,MAAM,EAAE,QAAQ,CAAC,EAAE,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC;QAE9C,sEAAsE;QACtE,gEAAgE;QAChE,wEAAwE;QACxE,sEAAsE;QACtE,kEAAkE;QAClE,4DAA4D;QAC5D,mEAAmE;QACnE,kDAAkD;QAClD,KAAK,CAAC,EAAE,CAAC,MAAM,EAAE,CAAC,IAAI,EAAE,EAAE;YACxB,MAAM,EAAE,CAAC,IAAI,CAAC,CAAC;QACjB,CAAC,CAAC,CAAC;QACH,KAAK,CAAC,EAAE,CAAC,OAAO,EAAE,GAAG,EAAE;YACrB,MAAM,EAAE,CAAC,CAAC,CAAC,CAAC;QACd,CAAC,CAAC,CAAC;QAEH,OAAO;YACL,MAAM,EAAE,CAAC,EAAE,EAAE,EAAE;gBACb,MAAM,GAAG,EAAE,CAAC;YACd,CAAC;YACD,MAAM,EAAE,CAAC,EAAE,EAAE,EAAE;gBACb,MAAM,GAAG,EAAE,CAAC;YACd,CAAC;YACD,IAAI,EAAE,GAAG,EAAE;gBACT,KAAK,CAAC,IAAI,EAAE,CAAC;YACf,CAAC;SACF,CAAC;IACJ,CAAC,CAAC;AACJ,CAAC"}
@@ -0,0 +1,34 @@
1
+ /**
2
+ * `nlm scope backfill`: derive and stamp scope on legacy corpus rows.
3
+ *
4
+ * Cascade order: sessions -> facts -> exemplars -> signals -> workstreams.
5
+ * --dry-run (default): computes would-change counts and writes nothing.
6
+ * --apply: writes; only fills scope IS NULL rows; idempotent.
7
+ */
8
+ import Database from "better-sqlite3";
9
+ import type { AliasMap } from "../core/scope/alias-map.js";
10
+ type ScopeCount = Record<string, number>;
11
+ export interface BackfillTableResult {
12
+ total: number;
13
+ byScope: ScopeCount;
14
+ }
15
+ export interface BackfillResult {
16
+ dryRun: boolean;
17
+ sessions: BackfillTableResult;
18
+ facts: BackfillTableResult;
19
+ exemplars: BackfillTableResult;
20
+ signals: BackfillTableResult;
21
+ workstreams: BackfillTableResult;
22
+ skipped: {
23
+ missingTranscript: number;
24
+ malformed: number;
25
+ noCwdFound: number;
26
+ };
27
+ }
28
+ export declare function runScopeBackfill(opts: {
29
+ db: Database.Database;
30
+ apply: boolean;
31
+ aliasMap: AliasMap;
32
+ }): Promise<BackfillResult>;
33
+ export declare function formatBackfillResult(result: BackfillResult, write: (s: string) => void): void;
34
+ export {};
@@ -0,0 +1,237 @@
1
+ /**
2
+ * `nlm scope backfill`: derive and stamp scope on legacy corpus rows.
3
+ *
4
+ * Cascade order: sessions -> facts -> exemplars -> signals -> workstreams.
5
+ * --dry-run (default): computes would-change counts and writes nothing.
6
+ * --apply: writes; only fills scope IS NULL rows; idempotent.
7
+ */
8
+ import { open } from "node:fs/promises";
9
+ import Database from "better-sqlite3";
10
+ import { deriveScope } from "../core/scope/derive-scope.js";
11
+ /** Read at most this many bytes from the head of a transcript to find cwd. */
12
+ const HEAD_BYTES = 8_192;
13
+ /**
14
+ * Bounded head-read that matches the claude-code adapter's cwd extraction
15
+ * exactly (src/core/adapters/claude-code.ts:144):
16
+ * if (!projectDir && typeof evt["cwd"] === "string") projectDir = evt["cwd"];
17
+ *
18
+ * Also covers pi-runtime JSONL: the pi adapter reads cwd from the
19
+ * `type: "session"` event on line 1 (src/core/adapters/pi.ts:124-126);
20
+ * taking the first `cwd` field on any line subsumes that shape.
21
+ *
22
+ * Reads at most HEAD_BYTES from the file start, splits into lines, parses
23
+ * each as JSON, and returns the value of the first "cwd" string field found.
24
+ * A first line longer than HEAD_BYTES arrives truncated, fails JSON.parse,
25
+ * and is skipped: fail-closed to NULL, never a mis-parse.
26
+ */
27
+ async function readCwdFromTranscript(transcriptPath) {
28
+ let fd;
29
+ try {
30
+ fd = await open(transcriptPath, "r");
31
+ const buf = Buffer.alloc(HEAD_BYTES);
32
+ const { bytesRead } = await fd.read(buf, 0, HEAD_BYTES, 0);
33
+ const head = buf.toString("utf8", 0, bytesRead);
34
+ for (const line of head.split("\n")) {
35
+ const trimmed = line.trim();
36
+ if (!trimmed)
37
+ continue;
38
+ let evt;
39
+ try {
40
+ evt = JSON.parse(trimmed);
41
+ }
42
+ catch {
43
+ continue;
44
+ }
45
+ if (typeof evt["cwd"] === "string" && evt["cwd"]) {
46
+ return { cwd: evt["cwd"] };
47
+ }
48
+ }
49
+ return { cwd: null };
50
+ }
51
+ catch (err) {
52
+ const code = err.code;
53
+ const skipReason = code === "ENOENT" || code === "EACCES" || code === "EPERM"
54
+ ? "missing"
55
+ : "malformed";
56
+ return { cwd: null, skipReason };
57
+ }
58
+ finally {
59
+ await fd?.close().catch(() => { });
60
+ }
61
+ }
62
+ function inc(counter, scope) {
63
+ counter[scope] = (counter[scope] ?? 0) + 1;
64
+ }
65
+ function emptyTable() {
66
+ return { total: 0, byScope: {} };
67
+ }
68
+ export async function runScopeBackfill(opts) {
69
+ const { db, apply, aliasMap } = opts;
70
+ const sessionRows = db
71
+ .prepare("SELECT id, transcript_path FROM sessions WHERE scope IS NULL AND transcript_path IS NOT NULL")
72
+ .all();
73
+ const derivedScopes = new Map();
74
+ let missingCount = 0;
75
+ let malformedCount = 0;
76
+ let noCwdCount = 0;
77
+ for (const row of sessionRows) {
78
+ const { cwd, skipReason } = await readCwdFromTranscript(row.transcript_path);
79
+ if (skipReason === "missing") {
80
+ missingCount++;
81
+ continue;
82
+ }
83
+ if (skipReason === "malformed") {
84
+ malformedCount++;
85
+ continue;
86
+ }
87
+ if (!cwd) {
88
+ noCwdCount++;
89
+ continue;
90
+ }
91
+ const scope = deriveScope(cwd, aliasMap);
92
+ if (scope === null)
93
+ continue;
94
+ derivedScopes.set(row.id, scope);
95
+ }
96
+ const result = {
97
+ dryRun: !apply,
98
+ sessions: emptyTable(),
99
+ facts: emptyTable(),
100
+ exemplars: emptyTable(),
101
+ signals: emptyTable(),
102
+ workstreams: emptyTable(),
103
+ skipped: { missingTranscript: missingCount, malformed: malformedCount, noCwdFound: noCwdCount },
104
+ };
105
+ for (const scope of derivedScopes.values()) {
106
+ result.sessions.total++;
107
+ inc(result.sessions.byScope, scope);
108
+ }
109
+ const performUpdates = () => {
110
+ const updateSession = db.prepare("UPDATE sessions SET scope = ? WHERE id = ? AND scope IS NULL");
111
+ for (const [id, scope] of derivedScopes) {
112
+ updateSession.run(scope, id);
113
+ }
114
+ const factRows = db
115
+ .prepare(`
116
+ SELECT s.scope, COUNT(f.id) AS n
117
+ FROM facts f
118
+ JOIN sessions s ON f.source_session_id = s.id
119
+ WHERE f.scope IS NULL AND s.scope IS NOT NULL
120
+ GROUP BY s.scope
121
+ `)
122
+ .all();
123
+ for (const { scope, n } of factRows) {
124
+ result.facts.total += n;
125
+ inc(result.facts.byScope, scope);
126
+ }
127
+ db.prepare(`
128
+ UPDATE facts
129
+ SET scope = (SELECT s.scope FROM sessions s WHERE s.id = facts.source_session_id)
130
+ WHERE scope IS NULL
131
+ AND source_session_id IN (SELECT id FROM sessions WHERE scope IS NOT NULL)
132
+ `).run();
133
+ const exemplarRows = db
134
+ .prepare(`
135
+ SELECT s.scope, COUNT(e.id) AS n
136
+ FROM code_exemplars e
137
+ JOIN sessions s ON e.session_id = s.id
138
+ WHERE e.scope IS NULL AND s.scope IS NOT NULL
139
+ GROUP BY s.scope
140
+ `)
141
+ .all();
142
+ for (const { scope, n } of exemplarRows) {
143
+ result.exemplars.total += n;
144
+ inc(result.exemplars.byScope, scope);
145
+ }
146
+ db.prepare(`
147
+ UPDATE code_exemplars
148
+ SET scope = (SELECT s.scope FROM sessions s WHERE s.id = code_exemplars.session_id)
149
+ WHERE scope IS NULL
150
+ AND session_id IN (SELECT id FROM sessions WHERE scope IS NOT NULL)
151
+ `).run();
152
+ const signalRows = db
153
+ .prepare(`
154
+ SELECT s.scope, COUNT(sig.id) AS n
155
+ FROM signals sig
156
+ JOIN sessions s ON sig.session_id = s.id
157
+ WHERE sig.scope IS NULL AND s.scope IS NOT NULL AND s.scope != 'global'
158
+ GROUP BY s.scope
159
+ `)
160
+ .all();
161
+ for (const { scope, n } of signalRows) {
162
+ result.signals.total += n;
163
+ inc(result.signals.byScope, scope);
164
+ }
165
+ db.prepare(`
166
+ UPDATE signals
167
+ SET scope = (SELECT s.scope FROM sessions s WHERE s.id = signals.session_id)
168
+ WHERE scope IS NULL
169
+ AND session_id IS NOT NULL
170
+ AND session_id IN (
171
+ SELECT id FROM sessions WHERE scope IS NOT NULL AND scope != 'global'
172
+ )
173
+ `).run();
174
+ const pendingWorkstreams = db
175
+ .prepare("SELECT id FROM workstreams WHERE scope IS NULL")
176
+ .all();
177
+ const getMemberScopes = db.prepare("SELECT scope FROM sessions WHERE workstream_id = ?");
178
+ const updateWs = db.prepare("UPDATE workstreams SET scope = ? WHERE id = ? AND scope IS NULL");
179
+ for (const ws of pendingWorkstreams) {
180
+ const members = getMemberScopes.all(ws.id);
181
+ if (members.length === 0)
182
+ continue;
183
+ if (members.some((m) => m.scope === null))
184
+ continue;
185
+ const unique = new Set(members.map((m) => m.scope));
186
+ if (unique.size !== 1)
187
+ continue;
188
+ const wsScope = [...unique][0];
189
+ result.workstreams.total++;
190
+ inc(result.workstreams.byScope, wsScope);
191
+ updateWs.run(wsScope, ws.id);
192
+ }
193
+ };
194
+ if (apply) {
195
+ db.transaction(performUpdates)();
196
+ }
197
+ else {
198
+ db.exec("BEGIN");
199
+ try {
200
+ performUpdates();
201
+ }
202
+ finally {
203
+ db.exec("ROLLBACK");
204
+ }
205
+ }
206
+ return result;
207
+ }
208
+ export function formatBackfillResult(result, write) {
209
+ const heading = result.dryRun
210
+ ? "scope backfill (dry run -- no writes):"
211
+ : "scope backfill applied:";
212
+ write(`${heading}\n`);
213
+ const rows = [
214
+ ["sessions", result.dryRun ? "would change" : "stamped", result.sessions],
215
+ ["facts", result.dryRun ? "would cascade" : "cascaded", result.facts],
216
+ ["exemplars", result.dryRun ? "would cascade" : "cascaded", result.exemplars],
217
+ ["signals", result.dryRun ? "would cascade" : "cascaded", result.signals],
218
+ ["workstreams", result.dryRun ? "would cascade" : "cascaded", result.workstreams],
219
+ ];
220
+ for (const [table, verb, data] of rows) {
221
+ const entries = Object.entries(data.byScope);
222
+ const breakdown = entries.length > 0
223
+ ? ` [${entries.map(([s, c]) => `${s}: ${c}`).join(", ")}]`
224
+ : "";
225
+ write(` ${table.padEnd(12)}${String(data.total).padStart(4)} ${verb}${breakdown}\n`);
226
+ }
227
+ const { missingTranscript, malformed, noCwdFound } = result.skipped;
228
+ const skipTotal = missingTranscript + malformed + noCwdFound;
229
+ if (skipTotal > 0) {
230
+ write(` skipped: ${skipTotal}` +
231
+ ` (missing transcript: ${missingTranscript}, malformed: ${malformed}, no cwd found: ${noCwdFound})\n`);
232
+ }
233
+ else {
234
+ write(` skipped: 0\n`);
235
+ }
236
+ }
237
+ //# sourceMappingURL=scope-backfill.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"scope-backfill.js","sourceRoot":"","sources":["../../src/cli/scope-backfill.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,44 @@
1
+ /**
2
+ * `nlm scope coverage`: per-table and recall-weighted scope coverage fractions.
3
+ *
4
+ * READ-ONLY: opens the DB with { readonly: true }; never writes.
5
+ * No env flags consulted. No recall behavior change.
6
+ */
7
+ export interface TableCoverage {
8
+ total: number;
9
+ stamped: number;
10
+ unstamped: number;
11
+ stamped_fraction: number;
12
+ byScope: Record<string, number>;
13
+ }
14
+ export interface OverallCoverage {
15
+ total: number;
16
+ stamped: number;
17
+ unstamped: number;
18
+ stamped_fraction: number;
19
+ }
20
+ export interface RecallWeightedStats {
21
+ distinctReturnedIds: number;
22
+ foundInDb: number;
23
+ scoped: number;
24
+ fraction: number;
25
+ }
26
+ export interface RecallWeightedCoverage extends RecallWeightedStats {
27
+ bySurface: Record<string, RecallWeightedStats>;
28
+ }
29
+ export interface CoverageResult {
30
+ sessions: TableCoverage;
31
+ facts: TableCoverage;
32
+ code_exemplars: TableCoverage;
33
+ signals: TableCoverage;
34
+ workstreams: TableCoverage;
35
+ overall: OverallCoverage;
36
+ recallWeighted: RecallWeightedCoverage | null;
37
+ queryLogNote: string | null;
38
+ }
39
+ export declare function runScopeCoverage(opts: {
40
+ dbPath: string;
41
+ queryLogPath?: string;
42
+ window?: number;
43
+ }): Promise<CoverageResult>;
44
+ export declare function formatCoverageResult(result: CoverageResult, write: (s: string) => void): void;
@@ -0,0 +1,208 @@
1
+ /**
2
+ * `nlm scope coverage`: per-table and recall-weighted scope coverage fractions.
3
+ *
4
+ * READ-ONLY: opens the DB with { readonly: true }; never writes.
5
+ * No env flags consulted. No recall behavior change.
6
+ */
7
+ import Database from "better-sqlite3";
8
+ import { existsSync } from "node:fs";
9
+ import { homedir } from "node:os";
10
+ import { join } from "node:path";
11
+ import { recentQueryLog } from "../core/recall/recent-log.js";
12
+ import { DEFAULT_TEAM_ID } from "../core/tenancy/default-team.js";
13
+ function overallOf(tables) {
14
+ let total = 0;
15
+ let stamped = 0;
16
+ for (const t of tables) {
17
+ total += t.total;
18
+ stamped += t.stamped;
19
+ }
20
+ return {
21
+ total,
22
+ stamped,
23
+ unstamped: total - stamped,
24
+ stamped_fraction: total === 0 ? 0 : stamped / total,
25
+ };
26
+ }
27
+ function tableStats(db, table) {
28
+ const agg = db
29
+ .prepare(`SELECT COUNT(*) AS total, SUM(CASE WHEN scope IS NOT NULL THEN 1 ELSE 0 END) AS scoped FROM "${table}"`)
30
+ .get();
31
+ const total = agg.total;
32
+ const scoped = agg.scoped ?? 0;
33
+ const rows = db
34
+ .prepare(`SELECT scope, COUNT(*) AS n FROM "${table}" WHERE scope IS NOT NULL GROUP BY scope`)
35
+ .all();
36
+ const byScope = {};
37
+ for (const { scope, n } of rows) {
38
+ byScope[scope] = n;
39
+ }
40
+ return {
41
+ total,
42
+ stamped: scoped,
43
+ unstamped: total - scoped,
44
+ stamped_fraction: total === 0 ? 0 : scoped / total,
45
+ byScope,
46
+ };
47
+ }
48
+ function defaultQueryLogPath() {
49
+ return process.env["NLM_QUERY_LOG"] ?? join(homedir(), ".nlm", "query_log.jsonl");
50
+ }
51
+ const CHUNK_SIZE = 999;
52
+ export async function runScopeCoverage(opts) {
53
+ const entryWindow = opts.window ?? 200;
54
+ if (!Number.isFinite(entryWindow) || entryWindow <= 0) {
55
+ throw new Error(`invalid --window: ${String(opts.window)} (expected a positive integer)`);
56
+ }
57
+ const db = new Database(opts.dbPath, { readonly: true });
58
+ try {
59
+ const sessions = tableStats(db, "sessions");
60
+ const facts = tableStats(db, "facts");
61
+ const code_exemplars = tableStats(db, "code_exemplars");
62
+ const signals = tableStats(db, "signals");
63
+ const workstreams = tableStats(db, "workstreams");
64
+ const overall = overallOf([sessions, facts, code_exemplars, signals, workstreams]);
65
+ const logPath = opts.queryLogPath ?? defaultQueryLogPath();
66
+ if (!existsSync(logPath)) {
67
+ return {
68
+ sessions,
69
+ facts,
70
+ code_exemplars,
71
+ signals,
72
+ workstreams,
73
+ overall,
74
+ recallWeighted: null,
75
+ queryLogNote: `query log not found at ${logPath}`,
76
+ };
77
+ }
78
+ // `nlm scope coverage` is a local CLI tool (single-tenant, no per-tenant
79
+ // CLI concept) — DEFAULT_TEAM_ID is its real identity, not a placeholder.
80
+ const entries = recentQueryLog(DEFAULT_TEAM_ID, entryWindow, logPath);
81
+ const idSet = new Set();
82
+ const idsBySurface = new Map();
83
+ for (const entry of entries) {
84
+ let surfaceIds = idsBySurface.get(entry.source);
85
+ if (!surfaceIds) {
86
+ surfaceIds = new Set();
87
+ idsBySurface.set(entry.source, surfaceIds);
88
+ }
89
+ for (const id of entry.returnedIds) {
90
+ idSet.add(id);
91
+ surfaceIds.add(id);
92
+ }
93
+ }
94
+ if (idSet.size === 0) {
95
+ return {
96
+ sessions,
97
+ facts,
98
+ code_exemplars,
99
+ signals,
100
+ workstreams,
101
+ overall,
102
+ recallWeighted: { distinctReturnedIds: 0, foundInDb: 0, scoped: 0, fraction: 0, bySurface: {} },
103
+ queryLogNote: null,
104
+ };
105
+ }
106
+ // Recalled ids span the corpus tables (session recall returns session
107
+ // ids, fact recall fact ids, code recall exemplar ids); resolve each id
108
+ // to its scope across all three, first match wins.
109
+ const scopeById = new Map();
110
+ const ids = [...idSet];
111
+ for (const table of ["sessions", "facts", "code_exemplars"]) {
112
+ for (let i = 0; i < ids.length; i += CHUNK_SIZE) {
113
+ const chunk = ids.slice(i, i + CHUNK_SIZE).filter((id) => !scopeById.has(id));
114
+ if (chunk.length === 0)
115
+ continue;
116
+ const placeholders = chunk.map(() => "?").join(", ");
117
+ const rows = db
118
+ .prepare(`SELECT id, scope FROM "${table}" WHERE id IN (${placeholders})`)
119
+ .all(...chunk);
120
+ for (const row of rows) {
121
+ if (!scopeById.has(row.id))
122
+ scopeById.set(row.id, row.scope);
123
+ }
124
+ }
125
+ }
126
+ const statsFor = (set) => {
127
+ let foundInDb = 0;
128
+ let scoped = 0;
129
+ for (const id of set) {
130
+ const scope = scopeById.get(id);
131
+ if (scope === undefined)
132
+ continue;
133
+ foundInDb++;
134
+ if (scope !== null)
135
+ scoped++;
136
+ }
137
+ return {
138
+ distinctReturnedIds: set.size,
139
+ foundInDb,
140
+ scoped,
141
+ fraction: foundInDb === 0 ? 0 : scoped / foundInDb,
142
+ };
143
+ };
144
+ const bySurface = {};
145
+ for (const [source, surfaceIds] of idsBySurface) {
146
+ if (surfaceIds.size > 0)
147
+ bySurface[source] = statsFor(surfaceIds);
148
+ }
149
+ return {
150
+ sessions,
151
+ facts,
152
+ code_exemplars,
153
+ signals,
154
+ workstreams,
155
+ overall,
156
+ recallWeighted: { ...statsFor(idSet), bySurface },
157
+ queryLogNote: null,
158
+ };
159
+ }
160
+ finally {
161
+ db.close();
162
+ }
163
+ }
164
+ export function formatCoverageResult(result, write) {
165
+ write("scope coverage:\n\n");
166
+ write(" per-table:\n");
167
+ const tables = [
168
+ ["sessions", result.sessions],
169
+ ["facts", result.facts],
170
+ ["code_exemplars", result.code_exemplars],
171
+ ["signals", result.signals],
172
+ ["workstreams", result.workstreams],
173
+ ];
174
+ for (const [name, cov] of tables) {
175
+ const pct = `${(cov.stamped_fraction * 100).toFixed(1)}%`;
176
+ const counts = `${cov.stamped}/${cov.total} stamped (${pct})`;
177
+ const entries = Object.entries(cov.byScope);
178
+ const breakdown = entries.length > 0
179
+ ? ` [${entries.map(([s, c]) => `${s}: ${c}`).join(", ")}]`
180
+ : "";
181
+ write(` ${name.padEnd(15)} ${counts}${breakdown}\n`);
182
+ }
183
+ const o = result.overall;
184
+ const overallPct = `${(o.stamped_fraction * 100).toFixed(1)}%`;
185
+ write(` ${"overall".padEnd(15)} ${o.stamped}/${o.total} stamped (${overallPct})\n`);
186
+ write("\n");
187
+ if (result.queryLogNote !== null) {
188
+ write(` recall-weighted: skipped -- ${result.queryLogNote}\n`);
189
+ }
190
+ else if (result.recallWeighted !== null) {
191
+ const rw = result.recallWeighted;
192
+ const pct = `${(rw.fraction * 100).toFixed(1)}%`;
193
+ write(` recall-weighted (recalled ids from last window):\n`);
194
+ write(` distinct ids: ${rw.distinctReturnedIds}\n`);
195
+ write(` found in db: ${rw.foundInDb}\n`);
196
+ write(` scoped: ${rw.scoped}\n`);
197
+ write(` fraction: ${pct}\n`);
198
+ const surfaces = Object.entries(rw.bySurface);
199
+ if (surfaces.length > 0) {
200
+ write(` per-surface:\n`);
201
+ for (const [source, s] of surfaces) {
202
+ const sPct = `${(s.fraction * 100).toFixed(1)}%`;
203
+ write(` ${source.padEnd(15)} ${s.scoped}/${s.foundInDb} scoped (${sPct}, ${s.distinctReturnedIds} ids)\n`);
204
+ }
205
+ }
206
+ }
207
+ }
208
+ //# sourceMappingURL=scope-coverage.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"scope-coverage.js","sourceRoot":"","sources":["../../src/cli/scope-coverage.ts"],"names":[],"mappings":"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"}