hippo-memory 1.70.0 → 1.71.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (629) hide show
  1. package/README.md +1 -1
  2. package/dist/agent-memories/claude-code.d.ts +4 -2
  3. package/dist/agent-memories/claude-code.js +14 -5
  4. package/dist/agent-memories/files.js +23 -12
  5. package/dist/agent-memories/markdown.d.ts +1 -3
  6. package/dist/agent-memories/markdown.js +1 -3
  7. package/dist/agent-memories/report.js +2 -1
  8. package/dist/agent-memories/sync.d.ts +4 -2
  9. package/dist/agent-memories/sync.js +10 -5
  10. package/dist/api/assemble.d.ts +7 -44
  11. package/dist/api/assemble.js +2 -22
  12. package/dist/api/audit.d.ts +5 -1
  13. package/dist/api/audit.js +9 -1
  14. package/dist/api/auth.d.ts +13 -22
  15. package/dist/api/auth.js +34 -24
  16. package/dist/api/auto-sleep.js +2 -2
  17. package/dist/api/availability.d.ts +2 -15
  18. package/dist/api/availability.js +2 -15
  19. package/dist/api/context-select.js +3 -4
  20. package/dist/api/context-types.d.ts +10 -35
  21. package/dist/api/context.d.ts +5 -22
  22. package/dist/api/context.js +21 -38
  23. package/dist/api/dormant.d.ts +5 -21
  24. package/dist/api/dormant.js +7 -26
  25. package/dist/api/drill-down.d.ts +7 -46
  26. package/dist/api/drill-down.js +5 -26
  27. package/dist/api/forget.d.ts +5 -24
  28. package/dist/api/forget.js +5 -28
  29. package/dist/api/graph.d.ts +8 -0
  30. package/dist/api/graph.js +7 -0
  31. package/dist/api/index.d.ts +2 -0
  32. package/dist/api/index.js +2 -0
  33. package/dist/api/instruction-detect.js +16 -5
  34. package/dist/api/ledger-db.d.ts +2 -1
  35. package/dist/api/ledger-db.js +5 -3
  36. package/dist/api/memories.d.ts +5 -0
  37. package/dist/api/memories.js +7 -0
  38. package/dist/api/objects.d.ts +9 -0
  39. package/dist/api/objects.js +11 -0
  40. package/dist/api/on-store.js +5 -3
  41. package/dist/api/predictions.d.ts +9 -0
  42. package/dist/api/predictions.js +18 -0
  43. package/dist/api/promote.d.ts +13 -17
  44. package/dist/api/promote.js +11 -19
  45. package/dist/api/prompt-hook.d.ts +4 -4
  46. package/dist/api/prompt-hook.js +10 -9
  47. package/dist/api/recall-cli.d.ts +55 -0
  48. package/dist/api/recall-cli.js +94 -0
  49. package/dist/api/recall-core.js +14 -6
  50. package/dist/api/recall-finish.d.ts +53 -0
  51. package/dist/api/recall-finish.js +30 -0
  52. package/dist/api/recall-history.d.ts +17 -84
  53. package/dist/api/recall-history.js +15 -88
  54. package/dist/api/recall-pipeline.d.ts +2 -3
  55. package/dist/api/recall-pipeline.js +16 -9
  56. package/dist/api/recall-types.d.ts +64 -304
  57. package/dist/api/recall.d.ts +5 -33
  58. package/dist/api/recall.js +59 -60
  59. package/dist/api/refine.d.ts +7 -0
  60. package/dist/api/refine.js +10 -0
  61. package/dist/api/remember-local.d.ts +57 -0
  62. package/dist/api/remember-local.js +90 -0
  63. package/dist/api/remember.d.ts +18 -1
  64. package/dist/api/remember.js +13 -1
  65. package/dist/api/sleep-run.d.ts +1 -3
  66. package/dist/api/sleep-run.js +17 -21
  67. package/dist/api/sleep.d.ts +9 -28
  68. package/dist/api/tokens.d.ts +3 -10
  69. package/dist/api/tokens.js +3 -10
  70. package/dist/api/types.d.ts +6 -29
  71. package/dist/api/types.js +4 -22
  72. package/dist/capture/command.d.ts +4 -12
  73. package/dist/capture/command.js +6 -22
  74. package/dist/capture/compact.d.ts +4 -15
  75. package/dist/capture/compact.js +16 -25
  76. package/dist/capture/compaction-record.js +101 -69
  77. package/dist/capture/compaction-spool.d.ts +1 -1
  78. package/dist/capture/compaction-spool.js +1 -1
  79. package/dist/capture/session-digest.d.ts +1 -1
  80. package/dist/capture/session-digest.js +13 -7
  81. package/dist/capture/transcript.d.ts +2 -10
  82. package/dist/capture/transcript.js +4 -18
  83. package/dist/cli/api-context.d.ts +3 -0
  84. package/dist/cli/api-context.js +6 -0
  85. package/dist/cli/audit-prune.d.ts +6 -39
  86. package/dist/cli/audit-prune.js +6 -39
  87. package/dist/cli/audit.d.ts +1 -1
  88. package/dist/cli/audit.js +33 -34
  89. package/dist/cli/auth.d.ts +2 -2
  90. package/dist/cli/auth.js +57 -39
  91. package/dist/cli/briefs.d.ts +4 -4
  92. package/dist/cli/briefs.js +18 -22
  93. package/dist/cli/card.d.ts +2 -2
  94. package/dist/cli/card.js +31 -32
  95. package/dist/cli/client.d.ts +7 -27
  96. package/dist/cli/client.js +24 -43
  97. package/dist/cli/compact-resume-payload.js +3 -2
  98. package/dist/cli/context.d.ts +1 -2
  99. package/dist/cli/context.js +12 -8
  100. package/dist/cli/continuity.d.ts +6 -6
  101. package/dist/cli/continuity.js +62 -64
  102. package/dist/cli/correction-latency.d.ts +2 -14
  103. package/dist/cli/correction-latency.js +2 -14
  104. package/dist/cli/curate.d.ts +13 -17
  105. package/dist/cli/curate.js +68 -92
  106. package/dist/cli/dag.d.ts +4 -4
  107. package/dist/cli/dag.js +33 -27
  108. package/dist/cli/decisions.d.ts +4 -4
  109. package/dist/cli/decisions.js +33 -47
  110. package/dist/cli/eval.js +15 -13
  111. package/dist/cli/exit.d.ts +6 -0
  112. package/dist/cli/exit.js +11 -0
  113. package/dist/cli/explain.d.ts +1 -2
  114. package/dist/cli/explain.js +6 -4
  115. package/dist/cli/flag-values.d.ts +6 -1
  116. package/dist/cli/flag-values.js +27 -10
  117. package/dist/cli/flags.d.ts +1 -0
  118. package/dist/cli/flags.js +1 -1
  119. package/dist/cli/github.d.ts +14 -0
  120. package/dist/{connectors/github/cli-impl.js → cli/github.js} +43 -71
  121. package/dist/cli/goals.d.ts +2 -2
  122. package/dist/cli/goals.js +46 -50
  123. package/dist/cli/hook-runtime.d.ts +9 -27
  124. package/dist/cli/hook-runtime.js +15 -31
  125. package/dist/cli/init.d.ts +2 -2
  126. package/dist/cli/init.js +6 -12
  127. package/dist/cli/install-steps.js +3 -12
  128. package/dist/cli/last-sleep.d.ts +2 -1
  129. package/dist/cli/last-sleep.js +3 -0
  130. package/dist/cli/maintenance.d.ts +4 -4
  131. package/dist/cli/maintenance.js +14 -19
  132. package/dist/cli/object-verbs.js +4 -3
  133. package/dist/cli/owner-validation.d.ts +5 -28
  134. package/dist/cli/owner-validation.js +5 -28
  135. package/dist/cli/playbooks.d.ts +4 -4
  136. package/dist/cli/playbooks.js +23 -28
  137. package/dist/cli/print.d.ts +2 -5
  138. package/dist/cli/print.js +1 -4
  139. package/dist/cli/projects.d.ts +2 -2
  140. package/dist/cli/projects.js +1 -3
  141. package/dist/cli/provenance-coverage.d.ts +2 -6
  142. package/dist/cli/provenance-coverage.js +2 -6
  143. package/dist/cli/quality-repair-once.js +2 -2
  144. package/dist/cli/recall.d.ts +2 -4
  145. package/dist/cli/recall.js +55 -131
  146. package/dist/cli/refine-llm.d.ts +5 -31
  147. package/dist/cli/refine-llm.js +9 -36
  148. package/dist/cli/remember.d.ts +3 -3
  149. package/dist/cli/remember.js +122 -180
  150. package/dist/cli/scheduler.d.ts +2 -17
  151. package/dist/cli/scheduler.js +12 -18
  152. package/dist/cli/serve.js +21 -12
  153. package/dist/cli/session-hooks.d.ts +10 -18
  154. package/dist/cli/session-hooks.js +112 -113
  155. package/dist/cli/setup.d.ts +4 -4
  156. package/dist/cli/setup.js +19 -21
  157. package/dist/cli/shared.d.ts +9 -23
  158. package/dist/cli/shared.js +9 -32
  159. package/dist/cli/slack.d.ts +2 -2
  160. package/dist/cli/slack.js +19 -23
  161. package/dist/cli/sleep.d.ts +3 -2
  162. package/dist/cli/sleep.js +15 -16
  163. package/dist/cli/status.d.ts +9 -12
  164. package/dist/cli/status.js +55 -98
  165. package/dist/cli/stdin.d.ts +4 -6
  166. package/dist/cli/stdin.js +2 -3
  167. package/dist/cli/transfer.d.ts +9 -9
  168. package/dist/cli/transfer.js +66 -89
  169. package/dist/cli/usage.js +11 -5
  170. package/dist/cli.d.ts +66 -448
  171. package/dist/cli.js +87 -263
  172. package/dist/connectors/github/backfill.d.ts +5 -25
  173. package/dist/connectors/github/backfill.js +14 -49
  174. package/dist/connectors/github/deletion.d.ts +4 -18
  175. package/dist/connectors/github/deletion.js +2 -15
  176. package/dist/connectors/github/dlq.d.ts +8 -33
  177. package/dist/connectors/github/dlq.js +12 -29
  178. package/dist/connectors/github/ingest.d.ts +2 -6
  179. package/dist/connectors/github/ingest.js +4 -10
  180. package/dist/connectors/github/octokit-client.d.ts +4 -16
  181. package/dist/connectors/github/octokit-client.js +27 -24
  182. package/dist/connectors/github/ratelimit.d.ts +3 -14
  183. package/dist/connectors/github/ratelimit.js +3 -14
  184. package/dist/connectors/github/scope.d.ts +3 -5
  185. package/dist/connectors/github/scope.js +3 -5
  186. package/dist/connectors/github/signature.d.ts +4 -26
  187. package/dist/connectors/github/signature.js +4 -26
  188. package/dist/connectors/github/tenant-routing.d.ts +2 -24
  189. package/dist/connectors/github/tenant-routing.js +4 -26
  190. package/dist/connectors/github/transform.js +2 -16
  191. package/dist/connectors/github/types.d.ts +3 -15
  192. package/dist/connectors/github/types.js +2 -9
  193. package/dist/connectors/github/webhook.d.ts +2 -16
  194. package/dist/connectors/github/webhook.js +6 -22
  195. package/dist/connectors/slack/backfill.d.ts +4 -17
  196. package/dist/connectors/slack/backfill.js +4 -13
  197. package/dist/connectors/slack/dlq.d.ts +2 -19
  198. package/dist/connectors/slack/dlq.js +2 -19
  199. package/dist/connectors/slack/ingest.d.ts +2 -3
  200. package/dist/connectors/slack/ingest.js +2 -3
  201. package/dist/connectors/slack/scope.d.ts +2 -8
  202. package/dist/connectors/slack/scope.js +2 -8
  203. package/dist/connectors/slack/signature.d.ts +1 -6
  204. package/dist/connectors/slack/tenant-routing.d.ts +2 -19
  205. package/dist/connectors/slack/tenant-routing.js +2 -21
  206. package/dist/connectors/slack/transform.d.ts +2 -18
  207. package/dist/connectors/slack/transform.js +2 -18
  208. package/dist/connectors/slack/types.d.ts +3 -9
  209. package/dist/connectors/slack/types.js +2 -4
  210. package/dist/connectors/slack/web-client.js +33 -27
  211. package/dist/connectors/slack/webhook.d.ts +2 -19
  212. package/dist/connectors/slack/webhook.js +5 -26
  213. package/dist/connectors/slack/workspaces.d.ts +4 -24
  214. package/dist/connectors/slack/workspaces.js +4 -24
  215. package/dist/consolidate/conflicts.js +6 -14
  216. package/dist/consolidate/dag-summary.d.ts +8 -0
  217. package/dist/consolidate/dag-summary.js +41 -0
  218. package/dist/consolidate/dag.d.ts +5 -28
  219. package/dist/consolidate/dag.js +14 -75
  220. package/dist/consolidate/decay.js +7 -19
  221. package/dist/consolidate/dedupe.d.ts +6 -52
  222. package/dist/consolidate/dedupe.js +13 -71
  223. package/dist/consolidate/flush-units.d.ts +3 -4
  224. package/dist/consolidate/flush-units.js +3 -3
  225. package/dist/consolidate/half-life-migration.d.ts +3 -26
  226. package/dist/consolidate/half-life-migration.js +11 -28
  227. package/dist/consolidate/llm-passes.js +4 -21
  228. package/dist/consolidate/memory-value-weights.d.ts +2 -13
  229. package/dist/consolidate/memory-value-weights.js +2 -13
  230. package/dist/consolidate/memory-value.d.ts +11 -84
  231. package/dist/consolidate/memory-value.js +16 -104
  232. package/dist/consolidate/merge.js +10 -31
  233. package/dist/consolidate/merged-row.js +2 -1
  234. package/dist/consolidate/physics-pass.js +1 -3
  235. package/dist/consolidate/replay.d.ts +6 -38
  236. package/dist/consolidate/replay.js +14 -52
  237. package/dist/consolidate/run.js +1 -1
  238. package/dist/consolidate/sleep.d.ts +1 -8
  239. package/dist/consolidate/sleep.js +5 -17
  240. package/dist/consolidate/trace.d.ts +3 -18
  241. package/dist/consolidate/trace.js +3 -18
  242. package/dist/consolidate/traces.js +6 -22
  243. package/dist/core/ablation.d.ts +4 -91
  244. package/dist/core/ablation.js +4 -91
  245. package/dist/core/ambient.d.ts +1 -8
  246. package/dist/core/ambient.js +1 -8
  247. package/dist/core/capture-contract.d.ts +4 -2
  248. package/dist/core/capture-contract.js +4 -2
  249. package/dist/core/card.d.ts +4 -1
  250. package/dist/core/card.js +8 -0
  251. package/dist/core/compare.d.ts +11 -67
  252. package/dist/core/compare.js +9 -63
  253. package/dist/core/config.d.ts +10 -24
  254. package/dist/core/config.js +13 -14
  255. package/dist/core/handoff.d.ts +1 -7
  256. package/dist/core/handoff.js +1 -7
  257. package/dist/core/memory-quality.js +1 -1
  258. package/dist/core/memory.d.ts +41 -164
  259. package/dist/core/memory.js +51 -221
  260. package/dist/core/package-root.d.ts +3 -0
  261. package/dist/core/package-root.js +5 -0
  262. package/dist/core/physics-config.d.ts +1 -4
  263. package/dist/core/physics-config.js +3 -8
  264. package/dist/core/physics.d.ts +15 -61
  265. package/dist/core/physics.js +59 -122
  266. package/dist/core/project-identity.d.ts +17 -58
  267. package/dist/core/project-identity.js +17 -38
  268. package/dist/core/project-remote.js +13 -2
  269. package/dist/core/raw-append-only.d.ts +5 -0
  270. package/dist/core/raw-append-only.js +7 -0
  271. package/dist/core/salience.d.ts +1 -7
  272. package/dist/core/salience.js +1 -7
  273. package/dist/dashboard/dashboard-actions.js +2 -2
  274. package/dist/dashboard/dashboard-snapshot.d.ts +2 -1
  275. package/dist/dashboard/dashboard-snapshot.js +11 -2
  276. package/dist/dashboard/dashboard-types.d.ts +2 -1
  277. package/dist/dashboard/dashboard.d.ts +1 -0
  278. package/dist/dashboard/dashboard.js +50 -4
  279. package/dist/db/busy.d.ts +1 -1
  280. package/dist/db/busy.js +17 -8
  281. package/dist/db/connect.d.ts +1 -0
  282. package/dist/db/connect.js +3 -3
  283. package/dist/db/migrate.js +3 -3
  284. package/dist/db/migrations/types.d.ts +2 -5
  285. package/dist/db/migrations/v14.js +2 -3
  286. package/dist/db/migrations/v15.js +2 -8
  287. package/dist/db/migrations/v16.js +2 -3
  288. package/dist/db/migrations/v17.js +2 -3
  289. package/dist/db/migrations/v19.js +2 -5
  290. package/dist/db/migrations/v20.js +2 -7
  291. package/dist/db/migrations/v22.js +4 -17
  292. package/dist/db/migrations/v23.js +3 -14
  293. package/dist/db/migrations/v24.js +2 -4
  294. package/dist/db/migrations/v25.js +3 -8
  295. package/dist/db/migrations/v26.js +2 -13
  296. package/dist/db/migrations/v27.js +3 -11
  297. package/dist/db/migrations/v28.js +2 -14
  298. package/dist/db/migrations/v29.js +4 -18
  299. package/dist/db/migrations/v30.js +4 -16
  300. package/dist/db/migrations/v31.js +2 -15
  301. package/dist/db/migrations/v32.js +4 -22
  302. package/dist/db/migrations/v33.js +2 -15
  303. package/dist/db/migrations/v34.js +2 -11
  304. package/dist/db/migrations/v35.js +2 -11
  305. package/dist/db/migrations/v36.js +2 -11
  306. package/dist/db/migrations/v37.js +8 -33
  307. package/dist/db/migrations/v38.js +5 -38
  308. package/dist/db/migrations/v39.js +9 -20
  309. package/dist/db/migrations/v40.js +2 -9
  310. package/dist/db/migrations/v41.js +2 -24
  311. package/dist/db/migrations/v43.js +1 -1
  312. package/dist/db/migrations/v44.js +2 -8
  313. package/dist/db/migrations/v45.js +2 -7
  314. package/dist/db/migrations/v47.js +2 -3
  315. package/dist/db/migrations/v51.js +1 -1
  316. package/dist/db/open.d.ts +2 -0
  317. package/dist/db/open.js +17 -1
  318. package/dist/db/physics-state.d.ts +6 -22
  319. package/dist/db/physics-state.js +25 -36
  320. package/dist/db/raw-archive-mirror-cleanup.d.ts +2 -17
  321. package/dist/db/raw-archive-mirror-cleanup.js +2 -17
  322. package/dist/db/vector-store.d.ts +2 -0
  323. package/dist/db/vector-store.js +8 -1
  324. package/dist/doctor.js +74 -19
  325. package/dist/entry/session-text.js +2 -1
  326. package/dist/eval/eval-stats.d.ts +15 -53
  327. package/dist/eval/eval-stats.js +12 -42
  328. package/dist/eval/eval-suite.d.ts +2 -13
  329. package/dist/eval/eval-suite.js +74 -34
  330. package/dist/eval/eval.d.ts +6 -24
  331. package/dist/eval/eval.js +7 -34
  332. package/dist/eval/judgment.d.ts +0 -3
  333. package/dist/eval/judgment.js +19 -11
  334. package/dist/extensions/openclaw-plugin/index.js +1 -1
  335. package/dist/graph/extract.d.ts +5 -27
  336. package/dist/graph/extract.js +7 -33
  337. package/dist/graph/recall.d.ts +7 -20
  338. package/dist/graph/recall.js +14 -76
  339. package/dist/graph/stream.d.ts +7 -39
  340. package/dist/graph/stream.js +11 -34
  341. package/dist/graph/view.d.ts +9 -35
  342. package/dist/graph/view.js +11 -39
  343. package/dist/hooks/codex-wrapper.js +2 -2
  344. package/dist/hooks/copilot.js +2 -1
  345. package/dist/hooks/hook-blocks.d.ts +6 -2
  346. package/dist/hooks/hook-blocks.js +37 -124
  347. package/dist/hooks/json-hooks.d.ts +4 -36
  348. package/dist/hooks/json-hooks.js +18 -57
  349. package/dist/hooks/opencode.d.ts +0 -38
  350. package/dist/hooks/opencode.js +9 -76
  351. package/dist/hooks/shared.d.ts +8 -17
  352. package/dist/hooks/shared.js +29 -20
  353. package/dist/importers/core.d.ts +12 -37
  354. package/dist/importers/core.js +9 -27
  355. package/dist/importers/markdown-parse.d.ts +8 -22
  356. package/dist/importers/markdown-parse.js +8 -25
  357. package/dist/importers/markdown.js +3 -12
  358. package/dist/importers/sources.js +7 -35
  359. package/dist/importers/vault.d.ts +2 -8
  360. package/dist/importers/vault.js +25 -81
  361. package/dist/index.d.ts +6 -2
  362. package/dist/index.js +6 -2
  363. package/dist/learn/autolearn.d.ts +14 -41
  364. package/dist/learn/autolearn.js +14 -41
  365. package/dist/learn/extract.js +2 -4
  366. package/dist/learn/forward-claim-detector.d.ts +6 -30
  367. package/dist/learn/forward-claim-detector.js +14 -66
  368. package/dist/learn/invalidation.d.ts +6 -18
  369. package/dist/learn/invalidation.js +9 -26
  370. package/dist/mcp/admin-tools.js +3 -5
  371. package/dist/mcp/memory-tools.js +4 -9
  372. package/dist/mcp/protocol.d.ts +8 -26
  373. package/dist/mcp/protocol.js +3 -6
  374. package/dist/mcp/recall-tools.js +3 -3
  375. package/dist/mcp/request.d.ts +3 -11
  376. package/dist/mcp/request.js +10 -26
  377. package/dist/mcp/server.d.ts +3 -9
  378. package/dist/mcp/server.js +5 -16
  379. package/dist/mcp/session-state.d.ts +1 -1
  380. package/dist/mcp/session-state.js +5 -11
  381. package/dist/mcp/stdio.d.ts +2 -6
  382. package/dist/mcp/stdio.js +48 -12
  383. package/dist/mcp/tools.js +5 -3
  384. package/dist/objects/customer-notes.d.ts +7 -42
  385. package/dist/objects/customer-notes.js +7 -48
  386. package/dist/objects/decisions.d.ts +12 -50
  387. package/dist/objects/decisions.js +15 -53
  388. package/dist/objects/incidents.d.ts +7 -38
  389. package/dist/objects/incidents.js +7 -41
  390. package/dist/objects/policies.d.ts +11 -89
  391. package/dist/objects/policies.js +11 -98
  392. package/dist/objects/processes.d.ts +7 -52
  393. package/dist/objects/processes.js +7 -61
  394. package/dist/objects/project-briefs.d.ts +11 -55
  395. package/dist/objects/project-briefs.js +14 -75
  396. package/dist/objects/skills.d.ts +7 -42
  397. package/dist/objects/skills.js +8 -54
  398. package/dist/postinstall.js +6 -19
  399. package/dist/predictions/planning-fallacy.d.ts +11 -34
  400. package/dist/rerankers/clef.js +3 -31
  401. package/dist/rerankers/cross-encoder.js +4 -6
  402. package/dist/rerankers/jev.js +9 -6
  403. package/dist/rerankers/llm.d.ts +2 -11
  404. package/dist/rerankers/llm.js +14 -14
  405. package/dist/rerankers/outage-warning.d.ts +2 -1
  406. package/dist/rerankers/outage-warning.js +2 -1
  407. package/dist/rerankers/remote.d.ts +1 -0
  408. package/dist/rerankers/remote.js +2 -0
  409. package/dist/rerankers/types.d.ts +2 -14
  410. package/dist/search/boosts.d.ts +0 -2
  411. package/dist/search/boosts.js +2 -2
  412. package/dist/search/goal-boost.d.ts +23 -0
  413. package/dist/search/goal-boost.js +90 -0
  414. package/dist/search/hybrid.d.ts +2 -0
  415. package/dist/search/multihop.js +2 -3
  416. package/dist/search/path-context.d.ts +5 -18
  417. package/dist/search/path-context.js +5 -18
  418. package/dist/search/physics-search.js +11 -8
  419. package/dist/search/rrf.d.ts +7 -35
  420. package/dist/search/rrf.js +5 -30
  421. package/dist/search/vector.d.ts +7 -0
  422. package/dist/search/vector.js +35 -5
  423. package/dist/server/auth.d.ts +9 -28
  424. package/dist/server/auth.js +32 -25
  425. package/dist/server/boot.d.ts +2 -21
  426. package/dist/server/boot.js +63 -96
  427. package/dist/server/client-ip.d.ts +3 -19
  428. package/dist/server/client-ip.js +5 -28
  429. package/dist/server/defaults.d.ts +3 -0
  430. package/dist/server/defaults.js +4 -0
  431. package/dist/server/key-check-bounds.d.ts +2 -1
  432. package/dist/server/lifecycle.d.ts +5 -4
  433. package/dist/server/lifecycle.js +19 -4
  434. package/dist/server/mcp-http.js +10 -44
  435. package/dist/server/rate-limit.d.ts +5 -18
  436. package/dist/server/rate-limit.js +4 -13
  437. package/dist/server/request.d.ts +4 -8
  438. package/dist/server/request.js +9 -17
  439. package/dist/server/route-table.js +42 -49
  440. package/dist/server/routes/admin.js +22 -28
  441. package/dist/server/routes/customer-notes.js +7 -12
  442. package/dist/server/routes/decisions.js +10 -17
  443. package/dist/server/routes/incidents.js +12 -20
  444. package/dist/server/routes/memories.js +12 -32
  445. package/dist/server/routes/object-routes.d.ts +0 -5
  446. package/dist/server/routes/object-routes.js +7 -15
  447. package/dist/server/routes/policies.js +10 -18
  448. package/dist/server/routes/predictions.js +13 -25
  449. package/dist/server/routes/processes.js +16 -26
  450. package/dist/server/routes/project-briefs.js +9 -16
  451. package/dist/server/routes/recall.js +10 -35
  452. package/dist/server/routes/skills.js +8 -18
  453. package/dist/server/server-detect.d.ts +9 -53
  454. package/dist/server/server-detect.js +24 -90
  455. package/dist/server/sleep-offload.js +4 -1
  456. package/dist/server/types.d.ts +12 -10
  457. package/dist/server/validation.d.ts +3 -1
  458. package/dist/server/validation.js +10 -23
  459. package/dist/server.d.ts +2 -2
  460. package/dist/server.js +3 -2
  461. package/dist/sharing/global-store.d.ts +19 -0
  462. package/dist/sharing/global-store.js +75 -0
  463. package/dist/sharing/global-sync.d.ts +6 -0
  464. package/dist/sharing/global-sync.js +80 -0
  465. package/dist/sharing/project-merge.d.ts +4 -5
  466. package/dist/sharing/project-merge.js +9 -7
  467. package/dist/sharing/scope.d.ts +4 -11
  468. package/dist/sharing/scope.js +4 -11
  469. package/dist/sharing/search-both.d.ts +60 -0
  470. package/dist/sharing/search-both.js +138 -0
  471. package/dist/sharing/share.d.ts +38 -0
  472. package/dist/sharing/share.js +226 -0
  473. package/dist/store/ambient.js +4 -9
  474. package/dist/store/audit-event.d.ts +4 -12
  475. package/dist/store/audit-event.js +4 -12
  476. package/dist/store/audit.d.ts +2 -5
  477. package/dist/store/audit.js +4 -12
  478. package/dist/store/auth.d.ts +6 -6
  479. package/dist/store/auth.js +10 -9
  480. package/dist/store/candidates.d.ts +20 -3
  481. package/dist/store/candidates.js +77 -48
  482. package/dist/store/card-detail.d.ts +2 -1
  483. package/dist/store/card-detail.js +2 -1
  484. package/dist/store/cards.d.ts +14 -9
  485. package/dist/store/cards.js +72 -126
  486. package/dist/store/conflicts.d.ts +4 -21
  487. package/dist/store/conflicts.js +71 -150
  488. package/dist/store/connectors/github.d.ts +10 -10
  489. package/dist/store/connectors/github.js +10 -10
  490. package/dist/store/dashboard-reads.js +4 -8
  491. package/dist/store/delete-and-batch.d.ts +11 -31
  492. package/dist/store/delete-and-batch.js +48 -64
  493. package/dist/store/delivery-recorder.d.ts +8 -4
  494. package/dist/store/delivery-recorder.js +25 -15
  495. package/dist/store/diagnostics.js +6 -13
  496. package/dist/store/dormant.d.ts +7 -29
  497. package/dist/store/dormant.js +15 -56
  498. package/dist/store/embeddings/index.d.ts +11 -80
  499. package/dist/store/embeddings/index.js +71 -207
  500. package/dist/store/embeddings/local.js +15 -32
  501. package/dist/store/embeddings/provider.d.ts +16 -53
  502. package/dist/store/embeddings/provider.js +41 -69
  503. package/dist/store/entry-reads.d.ts +21 -57
  504. package/dist/store/entry-reads.js +65 -126
  505. package/dist/store/entry-row.d.ts +6 -35
  506. package/dist/store/entry-row.js +9 -37
  507. package/dist/store/entry-writes.d.ts +10 -16
  508. package/dist/store/entry-writes.js +17 -35
  509. package/dist/store/goals.d.ts +3 -40
  510. package/dist/store/goals.js +21 -160
  511. package/dist/store/graph-queue.d.ts +6 -22
  512. package/dist/store/graph-queue.js +14 -45
  513. package/dist/store/graph-reads.d.ts +11 -35
  514. package/dist/store/graph-reads.js +20 -58
  515. package/dist/store/graph-rows.d.ts +3 -6
  516. package/dist/store/graph-rows.js +6 -9
  517. package/dist/store/graph-view-rows.d.ts +2 -1
  518. package/dist/store/graph-view-rows.js +2 -1
  519. package/dist/store/graph-writes.d.ts +6 -31
  520. package/dist/store/graph-writes.js +13 -37
  521. package/dist/store/half-life.d.ts +2 -1
  522. package/dist/store/half-life.js +14 -16
  523. package/dist/store/handoffs.d.ts +5 -11
  524. package/dist/store/handoffs.js +16 -34
  525. package/dist/store/index-and-stats.d.ts +6 -19
  526. package/dist/store/index-and-stats.js +34 -82
  527. package/dist/store/markdown.d.ts +2 -6
  528. package/dist/store/markdown.js +21 -20
  529. package/dist/store/mirrors.d.ts +2 -6
  530. package/dist/store/mirrors.js +14 -23
  531. package/dist/store/open.js +6 -13
  532. package/dist/store/planning-fallacy-evidence.d.ts +2 -30
  533. package/dist/store/planning-fallacy-evidence.js +8 -37
  534. package/dist/store/port.d.ts +82 -79
  535. package/dist/store/predictions.d.ts +11 -51
  536. package/dist/store/predictions.js +38 -119
  537. package/dist/{cli → store}/quality-repair.js +15 -31
  538. package/dist/store/raw-archive.d.ts +4 -16
  539. package/dist/store/raw-archive.js +14 -29
  540. package/dist/store/recall-scope.d.ts +19 -79
  541. package/dist/store/recall-scope.js +21 -82
  542. package/dist/store/recall-trace.d.ts +10 -77
  543. package/dist/store/recall-trace.js +19 -95
  544. package/dist/store/rejected-values.js +7 -19
  545. package/dist/store/rejection.d.ts +12 -58
  546. package/dist/store/rejection.js +13 -65
  547. package/dist/store/report-reads.d.ts +6 -0
  548. package/dist/store/report-reads.js +29 -0
  549. package/dist/store/rows.d.ts +9 -19
  550. package/dist/store/rows.js +36 -34
  551. package/dist/store/rule-sql.d.ts +5 -0
  552. package/dist/store/rule-sql.js +37 -0
  553. package/dist/store/search-rows.d.ts +7 -38
  554. package/dist/store/search-rows.js +14 -50
  555. package/dist/store/sessions.d.ts +10 -47
  556. package/dist/store/sessions.js +17 -73
  557. package/dist/store/sqlite/connector-events-group.js +2 -2
  558. package/dist/store/sqlite/entry-writes-group.js +2 -2
  559. package/dist/store/sqlite/error-codec.js +4 -2
  560. package/dist/store/sqlite/executor.d.ts +2 -1
  561. package/dist/store/sqlite/executor.js +2 -1
  562. package/dist/store/sqlite/local.d.ts +3 -3
  563. package/dist/store/sqlite/local.js +1 -0
  564. package/dist/store/sqlite/object-rows.js +6 -3
  565. package/dist/store/sqlite/objects-group.js +4 -2
  566. package/dist/store/sqlite/quarantine-group.js +2 -2
  567. package/dist/store/sqlite/store.d.ts +1 -4
  568. package/dist/store/sqlite/store.js +2 -3
  569. package/dist/store/sqlite/vector-reads-group.js +2 -2
  570. package/dist/store/sqlite/worker-jobs.js +1 -1
  571. package/dist/store/sqlite/worker-ops.d.ts +13 -2
  572. package/dist/store/sqlite/worker-ops.js +13 -2
  573. package/dist/store/sqlite/worker-store.js +5 -2
  574. package/dist/store/summaries.d.ts +10 -62
  575. package/dist/store/summaries.js +34 -146
  576. package/dist/store/summary-dirty.js +1 -1
  577. package/dist/store/tenant-lookup.d.ts +6 -1
  578. package/dist/store/tenant-lookup.js +7 -0
  579. package/dist/store/tenant.d.ts +2 -16
  580. package/dist/store/tenant.js +4 -19
  581. package/dist/store/token-ledger.d.ts +13 -43
  582. package/dist/store/token-ledger.js +19 -50
  583. package/dist/store/usage-reports.js +5 -13
  584. package/dist/store/vector-index.d.ts +46 -0
  585. package/dist/store/vector-index.js +170 -0
  586. package/dist/store/working-memory.d.ts +6 -25
  587. package/dist/store/working-memory.js +18 -52
  588. package/dist/store/yaml.d.ts +1 -5
  589. package/dist/store/yaml.js +2 -6
  590. package/dist/support-bundle.js +7 -5
  591. package/dist/trust/reject-flow.js +1 -3
  592. package/dist/util/anthropic-messages.js +14 -2
  593. package/dist/util/atomic-write.d.ts +2 -1
  594. package/dist/util/atomic-write.js +35 -4
  595. package/dist/util/capped-json.d.ts +6 -0
  596. package/dist/util/capped-json.js +46 -0
  597. package/dist/util/crash-handlers.d.ts +8 -1
  598. package/dist/util/crash-handlers.js +52 -10
  599. package/dist/util/env.d.ts +13 -6
  600. package/dist/util/env.js +14 -7
  601. package/dist/util/home-path.d.ts +2 -1
  602. package/dist/util/home-path.js +4 -2
  603. package/dist/util/http-retry.d.ts +3 -1
  604. package/dist/util/http-retry.js +26 -5
  605. package/dist/util/log.d.ts +3 -2
  606. package/dist/util/log.js +25 -9
  607. package/dist/util/request-scope.d.ts +2 -1
  608. package/dist/util/request-scope.js +2 -1
  609. package/dist/util/secret-detect.d.ts +5 -30
  610. package/dist/util/secret-detect.js +13 -39
  611. package/dist/util/stored-json.d.ts +1 -1
  612. package/dist/util/stored-json.js +1 -1
  613. package/dist/util/token-text.d.ts +1 -4
  614. package/dist/util/token-text.js +1 -4
  615. package/dist/util/transcript-tail.d.ts +2 -0
  616. package/dist/util/transcript-tail.js +24 -23
  617. package/dist/util/version.d.ts +5 -20
  618. package/dist/util/version.js +5 -20
  619. package/extensions/openclaw-plugin/index.ts +1 -1
  620. package/extensions/openclaw-plugin/openclaw.plugin.json +1 -1
  621. package/extensions/openclaw-plugin/package.json +1 -1
  622. package/openclaw.plugin.json +1 -1
  623. package/package.json +1 -1
  624. package/dist/connectors/github/cli-impl.d.ts +0 -25
  625. package/dist/sharing/shared.d.ts +0 -187
  626. package/dist/sharing/shared.js +0 -563
  627. package/dist/store/vector-writes.d.ts +0 -13
  628. package/dist/store/vector-writes.js +0 -89
  629. /package/dist/{cli → store}/quality-repair.d.ts +0 -0
@@ -1,23 +1,6 @@
1
- /**
2
- * Learned memory-value scorer, wired into the sleep decay pass as a
3
- * rescue-only veto.
4
- *
5
- * computeMvFeatures mirrors benchmarks/memory-value/extract.mjs's
6
- * computeFeatures for the 8 live dims the fitter optimized over
7
- * (FIT_DIMS) — the only dims MEMORY_VALUE_WEIGHTS carries a weight for.
8
- * Any future edit to either side must keep them byte-equivalent; the parity
9
- * test in tests/memory-value-wiring.test.ts enforces this.
10
- *
11
- * scoreEntries mirrors benchmarks/memory-value/evaluate.mjs's per-store
12
- * min-max normalization + weighted scorer (no additional orientation
13
- * multiply — the frozen weights already encode sign/orientation).
14
- *
15
- * rescueSet implements rescue-only semantics: a condemned entry is
16
- * rescued iff its learned score ranks in the top 30% (RESCUE_BUDGET, the
17
- * measured keep-budget operating point) of its own tenant's non-pinned
18
- * candidate set. Deletes(flag-on) subset Deletes(flag-off) by construction — this
19
- * function can only ever shrink the condemned set, never grow it.
20
- */
1
+ /** Learned memory-value scorer, a rescue-only veto in the sleep decay pass (it can only shrink the condemned set); mirrors benchmarks/memory-value/*.mjs.
2
+ * rescueSet rescues a condemned entry iff it ranks in the top 30% (RESCUE_BUDGET) of its tenant's non-pinned set; memory-value-wiring.test.ts guards parity. */
3
+ import { DEFAULT_TENANT_ID } from '../util/env.js';
21
4
  import { calculateStrength } from '../core/memory.js';
22
5
  import { compareEntryIdentity } from '../core/compare.js';
23
6
  import { MEMORY_VALUE_WEIGHTS, SOURCE_ARTIFACT_SHA256 } from './memory-value-weights.js';
@@ -36,32 +19,11 @@ export const MV_FEATURE_NAMES = [
36
19
  /** The keep-budget operating point (the only point with measured
37
20
  * evidence): a code constant tied to that evidence, not user-tunable. */
38
21
  const RESCUE_BUDGET = 0.3;
39
- /**
40
- * Small-tenant degeneracy: below this per-tenant non-pinned candidate-set
41
- * size, a rank statistic is noise (the measured evidence says nothing about
42
- * tiny scale), and the floor prevents immortal-entry
43
- * convergence: keepN=ceil(0.3*N) guarantees >=1 rescue at N=1, so without a
44
- * floor a condemned-only 1-entry tenant would be rescued every single sleep
45
- * forever. A condemned-only tenant below the floor instead drains normally
46
- * as entries are deleted: the surviving rescued subset only ever shrinks
47
- * toward 0, never regrows past 10 to regain eligibility on its own. Code
48
- * constant tied to that reasoning, not user-tunable (same posture as
49
- * RESCUE_BUDGET).
50
- */
22
+ /** Per-tenant floor on the non-pinned candidate set: below it ranks are noise, and keepN=ceil(0.3*N) would rescue a 1-entry tenant's entry every sleep forever.
23
+ * A code constant tied to that reasoning, not user-tunable (like RESCUE_BUDGET). */
51
24
  const MIN_RESCUE_GROUP = 10;
52
- /**
53
- * Blind v1 feature dict for one MemoryEntry, restricted to the 8 dims the
54
- * frozen weights carry (mirrors extract.mjs's computeFeatures).
55
- *
56
- * CRITICAL: `strength` is CLOCK-BASIS `calculateStrength(entry, now)` with
57
- * NO DecayOptions — that is how the frozen weights' training features were
58
- * computed (extract.mjs never passes decayOpts). Passing the production
59
- * decay basis (config.decayBasis via consolidate.ts's decayOpts) into this
60
- * feature would silently break parity with the frozen weight vector. This
61
- * is an intentional divergence from the condemnation TRIGGER in
62
- * consolidate.ts, which keeps using decayOpts as today — only the rescue
63
- * FEATURE is clock-basis.
64
- */
25
+ /** Blind v1 feature dict for one entry, restricted to the 8 dims the frozen weights carry. `strength` is CLOCK-BASIS `calculateStrength(entry, now)` with no
26
+ * DecayOptions, as in the weights' training; passing the production decay basis would silently break parity with the frozen weights. */
65
27
  export function computeMvFeatures(entry, now) {
66
28
  const ageDays = (now.getTime() - Date.parse(entry.created)) / DAY_MS;
67
29
  const pos = entry.outcome_positive ?? 0;
@@ -77,16 +39,8 @@ export function computeMvFeatures(entry, now) {
77
39
  content_length: entry.content.length,
78
40
  };
79
41
  }
80
- /**
81
- * Throws if the weight constant is malformed: fewer/extra dims, a
82
- * non-finite weight value, or a missing source digest. Flag-on + a broken
83
- * constant must THROW, never silently behave as flag-off.
84
- *
85
- * Parameterized (defaults to the real frozen singleton) so the throw
86
- * conditions are directly unit-testable without mutating the frozen
87
- * MEMORY_VALUE_WEIGHTS export — mirrors fit.mjs's verifyFrozenWeights
88
- * (see tests/memory-value-fit.test.ts's `describe('verifyFrozenWeights')`).
89
- */
42
+ /** Throws on a malformed weight constant (wrong dims, non-finite weight, missing digest): flag-on with a broken constant must throw, never act as flag-off.
43
+ * Parameterized (default: the frozen singleton) so the throw paths are unit-testable. */
90
44
  function isFiniteWeightValue(value) {
91
45
  return typeof value === 'number' && Number.isFinite(value);
92
46
  }
@@ -105,25 +59,8 @@ export function validateWeights(weights = MEMORY_VALUE_WEIGHTS, digest = SOURCE_
105
59
  throw new Error('memory-value: weights constant is malformed — SOURCE_ARTIFACT_SHA256 digest missing (src/consolidate/memory-value-weights.ts)');
106
60
  }
107
61
  }
108
- /**
109
- * Min-max normalize each of the 8 features over the given entry set
110
- * (constant feature -> 0, matching evaluate.mjs), then score = dot(weights,
111
- * normalized). The normalization context is exactly the entries passed in —
112
- * callers control the bounded scope (per-tenant, non-pinned).
113
- *
114
- * `weights` defaults to the real frozen singleton; parameterized (like
115
- * validateWeights) so callers/tests can score against an explicit vector
116
- * without touching the module singleton.
117
- *
118
- * Non-finite features: Date.parse on a malformed `created`
119
- * string yields NaN, and NaN would silently corrupt every OTHER entry's
120
- * min-max in the same group. An entry with ANY non-finite computed feature
121
- * is excluded from the normalization context entirely (its raw values never
122
- * touch min/max) and always scores -Infinity — the lowest possible score, so
123
- * it sorts to the bottom of its tenant deterministically and (via rescueSet's
124
- * explicit finite-score guard below) can never be rescued. Conservative
125
- * direction: deletes(flag-on) subset deletes(flag-off) still holds.
126
- */
62
+ /** Min-max normalize the 8 features over the given entries (constant -> 0), then score = dot(weights, normalized); callers set the scope.
63
+ * An entry with any non-finite feature (NaN from a malformed `created`) is excluded from normalization and scores -Infinity, so it can never be rescued. */
127
64
  export function scoreEntries(entries, now, weights = MEMORY_VALUE_WEIGHTS) {
128
65
  const raw = new Map();
129
66
  for (const e of entries)
@@ -166,17 +103,8 @@ export function scoreEntries(entries, now, weights = MEMORY_VALUE_WEIGHTS) {
166
103
  }
167
104
  return scores;
168
105
  }
169
- /**
170
- * Groups non-pinned entries by tenantId, scores + ranks each tenant's
171
- * group independently, and returns per-entry rank context for every
172
- * non-pinned entry (not just condemned ones) — the shared basis for both
173
- * rescueSet's rescue decision and consolidate.ts's audit-row rank context,
174
- * so the two never compute the ranking differently.
175
- *
176
- * `weights`/`digest` default to the real frozen singleton — parameterized
177
- * (like validateWeights/scoreEntries) purely for direct unit-testability of
178
- * the fail-loud path, never overridden by production callers.
179
- */
106
+ /** Group non-pinned entries by tenantId, score and rank each group independently, and return rank context for every non-pinned entry;
107
+ * rescueSet and the consolidate audit rows share it so they never compute the ranking differently. */
180
108
  export function rankNonPinnedByTenant(entries, now, weights = MEMORY_VALUE_WEIGHTS, digest = SOURCE_ARTIFACT_SHA256) {
181
109
  validateWeights(weights, digest);
182
110
  const byTenant = new Map();
@@ -185,7 +113,7 @@ export function rankNonPinnedByTenant(entries, now, weights = MEMORY_VALUE_WEIGH
185
113
  continue; // pinned entries never compete for rescue (never condemned)
186
114
  // Default an undefined tenantId as dag.ts:341 does: a raw/legacy row can carry one at runtime,
187
115
  // and keying it "undefined" would split it into its own singleton tenant.
188
- const tenantId = e.tenantId ?? 'default';
116
+ const tenantId = e.tenantId ?? DEFAULT_TENANT_ID;
189
117
  const list = byTenant.get(tenantId);
190
118
  if (list)
191
119
  list.push(e);
@@ -217,24 +145,8 @@ export function rankNonPinnedByTenant(entries, now, weights = MEMORY_VALUE_WEIGH
217
145
  }
218
146
  return result;
219
147
  }
220
- /**
221
- * Rescue decision: a condemned entry is rescued iff it ranks in the top
222
- * 30% of its tenant's non-pinned candidate set by learned score. Returns the
223
- * subset of condemnedIds that are rescued — the caller filters commits
224
- * (rescued -> survivors) and threads the same set into detectConflicts.
225
- *
226
- * `weights`/`digest` default to the real frozen singleton; production
227
- * callers (consolidate.ts) never pass overrides — the params exist purely so
228
- * "flag on + a broken constant throws" is directly testable end-to-end
229
- * through this function without mutating the frozen module singleton.
230
- *
231
- * `precomputedRanks`: when the caller has already
232
- * computed the per-tenant ranking (e.g. consolidate.ts needs it separately
233
- * for detail/audit rank context), pass it here to skip the internal
234
- * rankNonPinnedByTenant call — the whole-store ranking pass then runs
235
- * exactly once per sleep instead of twice. Omitted (the default), rescueSet
236
- * computes it internally as before — existing callers/tests are unaffected.
237
- */
148
+ /** Rescue decision: the subset of condemnedIds ranking in the top 30% of their tenant's non-pinned set by learned score.
149
+ * Pass `precomputedRanks` to skip the internal ranking so the whole-store pass runs once per sleep; `weights`/`digest` overrides exist for tests only. */
238
150
  export function rescueSet(entries, condemnedIds, now, options = {}) {
239
151
  const { weights = MEMORY_VALUE_WEIGHTS, digest = SOURCE_ARTIFACT_SHA256, precomputedRanks } = options;
240
152
  validateWeights(weights, digest); // fail loud before any rescue computation
@@ -14,11 +14,8 @@ const MERGE_OVERLAP_THRESHOLD = 0.35; // Jaccard similarity for "related"
14
14
  const MERGE_MIN_CLUSTER = 2; // minimum cluster size to merge
15
15
  const MERGE_MAX_SOURCES = 5; // with MERGE_MAX_CHARS, keeps a merged row near 500 tokens, a third of the 1,500-token context budget
16
16
  const MERGE_MAX_CHARS = 2000; // total source text; sources past either cap stay unmerged and keep their half-life
17
- // Half-life scale for merged source episodics. Demotion must go through
18
- // half_life_days: calculateStrength() recomputes live strength from
19
- // last_retrieved/half_life and never reads the stored strength field, so a
20
- // stored-strength write is inert for ranking and gets overwritten by the
21
- // next sleep's decay pass anyway.
17
+ // Half-life scale for merged source episodics. Demote via half_life_days: calculateStrength() recomputes live strength and never reads the stored field,
18
+ // so a stored-strength write is inert for ranking and overwritten by the next decay pass.
22
19
  const MERGE_SOURCE_HALF_LIFE_FACTOR = 0.3;
23
20
  export function retireHeldTexts(run) {
24
21
  const { survivors } = run;
@@ -63,9 +60,7 @@ function partitionMergeCandidates(survivors) {
63
60
  }
64
61
  return mergeCandidatesByTenant;
65
62
  }
66
- // -------------------------------------------------------------------------
67
63
  // 3. Merge pass - episodic entries only
68
- // -------------------------------------------------------------------------
69
64
  /** Returns how many clusters were skipped because their merged text matches a rejected value. */
70
65
  export function mergePass(run) {
71
66
  const used = new Set();
@@ -123,16 +118,8 @@ function mergeCluster(run, partition, cluster, related, used) {
123
118
  run.pendingWrites.push(semantic);
124
119
  run.units.push([semantic.id, ...cluster.map((e) => e.id)]);
125
120
  result.semanticCreated++;
126
- // Demote source episodics (they've been compressed into neocortex):
127
- // scale half_life_days so they decay sooner while staying recoverable.
128
- // Immediate ranking is deliberately unchanged: dropping children below a
129
- // worse-retrieving summary regresses budget-bounded QA. The stored
130
- // strength is refreshed to the live value so inspect, replay sampling,
131
- // and strength-sorted assembly see the truth instead of a fake 0.3.
132
- // Mutate in place (not a copy): `cluster` holds the same object
133
- // references as `survivors`, and the later detectConflicts(survivors)
134
- // pass in this same run must see the post-demotion half-life, or it
135
- // can persist conflicts for entries the just-written state excludes.
121
+ // Scale half_life_days so merged sources decay sooner but stay recoverable; ranking is unchanged on purpose (demoting children regresses QA).
122
+ // Mutate in place: `cluster` shares references with `survivors`, and the later detectConflicts(survivors) must see the post-demotion half-life.
136
123
  demoteMergedSources(run, cluster);
137
124
  }
138
125
  return true;
@@ -163,14 +150,8 @@ function demoteMergedSources(run, cluster) {
163
150
  run.pendingWrites.push(e);
164
151
  }
165
152
  }
166
- // mergeContents is DETERMINISTIC CONCATENATION (not an LLM paraphrase)
167
- // — if a human rejected exactly this byte-identical rollup before, an
168
- // unguarded sleep would regenerate it every cycle and
169
- // batchWriteAndDelete's guard bypass (store.ts) would silently
170
- // re-assert it forever. This producer-side check is what makes that
171
- // bypass safe. A hit skips the WHOLE cluster: sources stay unmerged —
172
- // not demoted, not deleted — so a later sleep gets another chance if
173
- // the tombstone is lifted.
153
+ // mergeContents is deterministic, so a rollup a human already rejected would regenerate each cycle and batchWriteAndDelete's guard bypass would re-assert it;
154
+ // this producer-side check makes that bypass safe. A hit skips the whole cluster (no demote, no delete) so a later sleep can retry.
174
155
  function mergeRejected(run, semantic, cluster, related, used) {
175
156
  const { tombstones } = run;
176
157
  const newDigest = rejectionDigest(semantic.content);
@@ -180,9 +161,7 @@ function mergeRejected(run, semantic, cluster, related, used) {
180
161
  const mergeDigest = newHit ? newDigest : oldDigest;
181
162
  if (!tombstone)
182
163
  return false;
183
- // Still mark used — these members are not re-tried against a
184
- // DIFFERENT cluster within this same pass; next sleep re-clusters
185
- // them fresh.
164
+ // Still mark used: these members are not re-tried against a different cluster in this pass; the next sleep re-clusters them fresh.
186
165
  const rejected = newHit ? cluster : related; // the old format digested the uncapped list, so rows past the cap were rejected too
187
166
  for (const e of rejected)
188
167
  used.add(e.id);
@@ -203,9 +182,7 @@ function mergeRejected(run, semantic, cluster, related, used) {
203
182
  }
204
183
  return true;
205
184
  }
206
- // ---------------------------------------------------------------------------
207
185
  // Helpers
208
- // ---------------------------------------------------------------------------
209
186
  function mergeContents(entries) {
210
187
  // Each distinct text goes in once and in full (the merge demotes every source), one bullet with its lines indented, so heldTextKeys can read it back.
211
188
  // Newest first says which version is current; compareEntryIdentity settles ties, so the row and its rejection digest depend only on the sources.
@@ -215,7 +192,9 @@ function mergeContents(entries) {
215
192
  if (!texts.has(duplicateKey(e.content)))
216
193
  texts.set(duplicateKey(e.content), e.content);
217
194
  }
218
- const header = entries.length === 2 ? '[Consolidated from 2 related memories, newest first]' : `[Consolidated pattern from ${entries.length} related memories, newest first]`;
195
+ const header = entries.length === 2
196
+ ? '[Consolidated from 2 related memories, newest first]'
197
+ : `[Consolidated pattern from ${entries.length} related memories, newest first]`;
219
198
  return mergedText(header, [...texts.values()]);
220
199
  }
221
200
  function legacyMergeContents(entries) {
@@ -1,5 +1,6 @@
1
1
  // A sleep-merged row copies its sources' texts, so retiring a text (reject, or superseding its source) must reach the row too.
2
- // SHORTCUT: reject rewrites merged rows at once, live and dormant; supersede and `resolve --reject-loser` wait for the next sleep's check, which sees a dormant row only once restored.
2
+ // SHORTCUT: reject rewrites merged rows at once, live and dormant; supersede and `resolve
3
+ // --reject-loser` wait for the next sleep's check, which sees a dormant row only once restored.
3
4
  import { generateId } from '../core/memory.js';
4
5
  import { duplicateKey, heldTexts, mergedText } from '../util/same-text.js';
5
6
  /** The row that replaces a merged row once its retired texts leave: undefined when it holds none, null when nothing else is left. */
@@ -1,11 +1,9 @@
1
1
  import { refreshParticleProperties } from '../db/physics-state.js';
2
- import { loadStoredParticles, saveStoredParticles } from '../store/vector-writes.js';
2
+ import { loadStoredParticles, saveStoredParticles } from '../store/vector-index.js';
3
3
  import { simulate } from '../core/physics.js';
4
4
  import { errorMessage } from '../util/log.js';
5
5
  const STATS_DECIMALS = 4;
6
- // -------------------------------------------------------------------------
7
6
  // 2. Physics simulation pass
8
- // -------------------------------------------------------------------------
9
7
  export function physicsPass(run) {
10
8
  if (run.dryRun)
11
9
  return;
@@ -1,41 +1,9 @@
1
- /**
2
- * Replay — biologically-inspired rehearsal during consolidation.
3
- *
4
- * Hippocampal replay is internally-driven reactivation of memories during
5
- * slow-wave sleep: the brain picks important recent experiences and "plays
6
- * them back" without external input, strengthening them before they decay.
7
- * In McClelland's complementary-learning-systems framing, replay is also
8
- * how episodic memories train the neocortex (interleaved rehearsal); in
9
- * reward-modulated STDP, replay is gated by dopamine so rewarded
10
- * experiences get preferentially consolidated.
11
- *
12
- * This module implements a lightweight, deterministic analog. During each
13
- * `hippo sleep`, we sample N surviving memories by a priority score that
14
- * weighs reward feedback, emotional valence, under-rehearsal, and age —
15
- * then apply the same retrieval-strengthening dynamics `markRetrieved`
16
- * applies to real queries. The effect is that important memories stay
17
- * strong even when the user hasn't explicitly queried them recently.
18
- *
19
- * Distinct from the other consolidation passes:
20
- * - decay: removes what's too weak
21
- * - physics: moves particles in embedding space
22
- * - merge: collapses near-duplicate episodics into semantics
23
- * - REPLAY: picks winners and rehearses them (this file)
24
- */
1
+ /** Replay: during `hippo sleep`, sample N survivors weighted by reward, valence, under-rehearsal and age, then apply the `markRetrieved` strengthening.
2
+ * A lightweight deterministic analog of hippocampal replay, so important memories stay strong without being queried; distinct from decay, physics and merge. */
25
3
  import { type MemoryEntry } from '../core/memory.js';
26
- /**
27
- * Priority score used to rank survivors for replay. Higher = more likely
28
- * to be sampled. Pure function of the entry and current time.
29
- */
30
- export declare function replayPriority(entry: MemoryEntry, now: Date): number;
31
- /**
32
- * Pick `count` memories for replay, weighted by `replayPriority`, without
33
- * replacement. Deterministic given the same seed.
34
- *
35
- * The sampler is weighted but not greedy — picking by priority alone would
36
- * always pick the top-N, which overfits. Biological replay shows both
37
- * preferential-for-reward AND stochastic-exploration characteristics; we
38
- * keep the stochastic element so adjacent survivors aren't always ignored.
39
- */
4
+ /** Priority score for ranking survivors for replay (higher = more likely sampled); pure in the entry and current time. */
5
+ export declare function replayPriority(entry: MemoryEntry, now: Date, outcomeAblated: boolean): number;
6
+ /** Pick `count` memories for replay, weighted by `replayPriority`, without replacement; deterministic for a seed.
7
+ * Weighted but not greedy: always taking the top-N overfits, so a stochastic element keeps adjacent survivors in play. */
40
8
  export declare function sampleForReplay(survivors: MemoryEntry[], count: number, now: Date, seed?: number): MemoryEntry[];
41
9
  //# sourceMappingURL=replay.d.ts.map
@@ -1,27 +1,5 @@
1
- /**
2
- * Replay — biologically-inspired rehearsal during consolidation.
3
- *
4
- * Hippocampal replay is internally-driven reactivation of memories during
5
- * slow-wave sleep: the brain picks important recent experiences and "plays
6
- * them back" without external input, strengthening them before they decay.
7
- * In McClelland's complementary-learning-systems framing, replay is also
8
- * how episodic memories train the neocortex (interleaved rehearsal); in
9
- * reward-modulated STDP, replay is gated by dopamine so rewarded
10
- * experiences get preferentially consolidated.
11
- *
12
- * This module implements a lightweight, deterministic analog. During each
13
- * `hippo sleep`, we sample N surviving memories by a priority score that
14
- * weighs reward feedback, emotional valence, under-rehearsal, and age —
15
- * then apply the same retrieval-strengthening dynamics `markRetrieved`
16
- * applies to real queries. The effect is that important memories stay
17
- * strong even when the user hasn't explicitly queried them recently.
18
- *
19
- * Distinct from the other consolidation passes:
20
- * - decay: removes what's too weak
21
- * - physics: moves particles in embedding space
22
- * - merge: collapses near-duplicate episodics into semantics
23
- * - REPLAY: picks winners and rehearses them (this file)
24
- */
1
+ /** Replay: during `hippo sleep`, sample N survivors weighted by reward, valence, under-rehearsal and age, then apply the `markRetrieved` strengthening.
2
+ * A lightweight deterministic analog of hippocampal replay, so important memories stay strong without being queried; distinct from decay, physics and merge. */
25
3
  import { isOutcomeSlowAblated } from '../core/ablation.js';
26
4
  import { resolveConfidence } from '../core/memory.js';
27
5
  const VALENCE_WEIGHT = {
@@ -30,18 +8,13 @@ const VALENCE_WEIGHT = {
30
8
  negative: 1.5,
31
9
  critical: 2.0,
32
10
  };
33
- /**
34
- * Priority score used to rank survivors for replay. Higher = more likely
35
- * to be sampled. Pure function of the entry and current time.
36
- */
37
- export function replayPriority(entry, now) {
11
+ /** Priority score for ranking survivors for replay (higher = more likely sampled); pure in the entry and current time. */
12
+ export function replayPriority(entry, now, outcomeAblated) {
38
13
  const pos = entry.outcome_positive ?? 0;
39
14
  const neg = entry.outcome_negative ?? 0;
40
- // Reward signal: neutral memories get 1, strongly-rewarded memories > 1,
41
- // negative-dominated memories floor at 0.1 (so they're still eligible, just
42
- // much less likely to be sampled than neutral peers). Clamp is required
43
- // because sampleForReplay depends on all weights being positive.
44
- const rewardSignal = isOutcomeSlowAblated()
15
+ // Reward signal: neutral = 1, strongly rewarded > 1, negative-dominated floors at 0.1 (still eligible, just unlikely).
16
+ // The clamp is required because sampleForReplay needs all weights positive.
17
+ const rewardSignal = outcomeAblated
45
18
  ? 1.0 // EVAL-ONLY ablation (see ablation.ts): outcome-off also silences replay's reward bias
46
19
  : Math.max(0.1, 1 + pos * 0.5 + (pos - neg) * 0.25);
47
20
  const valence = VALENCE_WEIGHT[entry.emotional_valence] ?? 1.0;
@@ -57,11 +30,7 @@ export function replayPriority(entry, now) {
57
30
  const strengthFloor = Math.max(0.1, rawStrength);
58
31
  return rewardSignal * valence * underRehearsed * idleBoost * strengthFloor;
59
32
  }
60
- /**
61
- * Deterministic 32-bit RNG (Mulberry32). Same seed → same sequence.
62
- * Keeps replay reproducible for tests and audit runs without bringing
63
- * in a random-number dependency.
64
- */
33
+ /** Deterministic 32-bit RNG (Mulberry32): same seed, same sequence, so replay is reproducible without a random-number dependency. */
65
34
  function mulberry32(seed) {
66
35
  let s = seed >>> 0;
67
36
  return () => {
@@ -71,29 +40,22 @@ function mulberry32(seed) {
71
40
  return ((t ^ (t >>> 14)) >>> 0) / 4294967296;
72
41
  };
73
42
  }
74
- /**
75
- * Pick `count` memories for replay, weighted by `replayPriority`, without
76
- * replacement. Deterministic given the same seed.
77
- *
78
- * The sampler is weighted but not greedy — picking by priority alone would
79
- * always pick the top-N, which overfits. Biological replay shows both
80
- * preferential-for-reward AND stochastic-exploration characteristics; we
81
- * keep the stochastic element so adjacent survivors aren't always ignored.
82
- */
43
+ /** Pick `count` memories for replay, weighted by `replayPriority`, without replacement; deterministic for a seed.
44
+ * Weighted but not greedy: always taking the top-N overfits, so a stochastic element keeps adjacent survivors in play. */
83
45
  export function sampleForReplay(survivors, count, now, seed = Date.now() >>> 0) {
84
46
  if (count <= 0 || survivors.length === 0)
85
47
  return [];
86
48
  const rng = mulberry32(seed);
87
- // Deliberately-marked and aged-out memories are both untrusted; rehearsing
88
- // them would defeat the purpose of staleness, so derive rather than trust
89
- // the stored value (it no longer carries the age-out case, see memory.ts).
49
+ // Deliberately-marked and aged-out memories are both untrusted and rehearsing them defeats staleness, so derive rather than trust
50
+ // the stored value (it no longer carries the age-out case).
90
51
  const eligible = survivors.filter((e) => resolveConfidence(e, now) !== 'stale');
91
52
  if (eligible.length === 0)
92
53
  return [];
54
+ const outcomeAblated = isOutcomeSlowAblated();
93
55
  const pool = eligible.map((entry, idx) => ({
94
56
  entry,
95
57
  idx,
96
- weight: replayPriority(entry, now),
58
+ weight: replayPriority(entry, now, outcomeAblated),
97
59
  }));
98
60
  const want = Math.min(count, pool.length);
99
61
  const chosen = [];
@@ -1,5 +1,5 @@
1
1
  import { ftsDrift } from '../store/entry-row.js';
2
- import { NO_MERGE_TAGS } from '../sharing/shared.js';
2
+ import { NO_MERGE_TAGS } from '../sharing/share.js';
3
3
  export const REPLAY_COUNT_DEFAULT = 5;
4
4
  export function keptAsWritten(entry) {
5
5
  return entry.tags.some((tag) => NO_MERGE_TAGS.has(tag));
@@ -1,11 +1,4 @@
1
- /**
2
- * Consolidation engine ("Sleep") for Hippo.
3
- *
4
- * Steps:
5
- * 1. Decay pass - remove entries below strength threshold
6
- * 2. Merge pass - find episodic entries with high text overlap, create semantic summaries
7
- * 3. Stats tracking
8
- */
1
+ /** Consolidation engine ("Sleep"): decay pass (drop entries below the strength threshold), merge pass (semantic summaries of overlapping episodics), stats. */
9
2
  import { type WriteBudget } from '../util/write-budget.js';
10
3
  import { type ConsolidationResult } from './run.js';
11
4
  /**
@@ -1,14 +1,7 @@
1
- /**
2
- * Consolidation engine ("Sleep") for Hippo.
3
- *
4
- * Steps:
5
- * 1. Decay pass - remove entries below strength threshold
6
- * 2. Merge pass - find episodic entries with high text overlap, create semantic summaries
7
- * 3. Stats tracking
8
- */
1
+ /** Consolidation engine ("Sleep"): decay pass (drop entries below the strength threshold), merge pass (semantic summaries of overlapping episodics), stats. */
9
2
  import { evalNow } from '../core/ablation.js';
10
3
  import { canAutoDelete } from '../core/memory.js';
11
- import { loadAllEntries } from '../store/entry-reads.js';
4
+ import { loadAllEntriesWithBase } from '../store/entry-reads.js';
12
5
  import { commitInChunks, memoriesBackingObjects } from '../store/delete-and-batch.js';
13
6
  import { appendConsolidationRun, loadSessionDecayContext, incrementSleepCount } from '../store/index-and-stats.js';
14
7
  import { replaceDetectedConflicts } from '../store/conflicts.js';
@@ -40,14 +33,13 @@ export async function consolidate(hippoRoot, options = {}) {
40
33
  syncFtsIndex(hippoRoot, dryRun, result);
41
34
  // Host-wide by design: per-tenant filtering would mean N runs per host and no cross-tenant dedup.
42
35
  // The api.sleep audit row tags this with the admin synthetic actor.
43
- const all = loadAllEntries(hippoRoot);
36
+ const { entries: all, base: snapshot } = loadAllEntriesWithBase(hippoRoot);
44
37
  if (dryRun)
45
38
  for (const e of all)
46
39
  e.half_life_days = halfLife.halfLives.get(e.id) ?? e.half_life_days;
47
40
  const backingObjects = memoriesBackingObjects(hippoRoot);
48
41
  // Retirable: auto-deletable (never pinned, raw or kept for good) and not backing a first-class object.
49
42
  const retirable = (entry) => canAutoDelete(entry) && !backingObjects.has(entry.id);
50
- const snapshot = new Map(structuredClone(all).map((e) => [e.id, e]));
51
43
  const config = loadConfig(hippoRoot);
52
44
  const decayOpts = sessionDecayOptions(hippoRoot, config);
53
45
  const run = {
@@ -125,10 +117,8 @@ async function flushPending(run, snapshot, budget) {
125
117
  result.removed = result.removedIds.length;
126
118
  result.dormant = pendingDormant.filter((m) => left.has(m.entry.id)).length;
127
119
  }
128
- // Dormant retention: a dormant memory nobody restored within
129
- // dormant.retentionDays is deleted for good (0 keeps them forever). Runs
130
- // even when dormant.enabled is off, so turning it off still ages out what
131
- // earlier sleeps kept.
120
+ // Dormant retention: a dormant memory nobody restored within dormant.retentionDays is deleted for good (0 keeps forever);
121
+ // runs even when dormant.enabled is off, so turning it off still ages out what earlier sleeps kept.
132
122
  async function expireDormant(run, budget) {
133
123
  const { config, result, dryRun } = run;
134
124
  if (!(config.dormant.retentionDays > 0))
@@ -139,9 +129,7 @@ async function expireDormant(run, budget) {
139
129
  result.details.push(` ⌛ ${dryRun ? 'would expire' : 'expired'} ${result.dormantExpired} dormant memor${result.dormantExpired === 1 ? 'y' : 'ies'} older than ${config.dormant.retentionDays} days`);
140
130
  }
141
131
  }
142
- // -------------------------------------------------------------------------
143
132
  // 4. Log run
144
- // -------------------------------------------------------------------------
145
133
  function logRun(run, decay) {
146
134
  const { hippoRoot, now, result } = run;
147
135
  const detectedConflicts = detectConflicts(run.survivors, now, run.decayOpts, decay.rescuedIds);
@@ -1,10 +1,5 @@
1
- /**
2
- * Trace-layer helpers.
3
- *
4
- * A trace is a `MemoryEntry` with `layer === 'trace'` that captures an ordered
5
- * sequence of agent actions and their final outcome. v1 stores steps as
6
- * markdown in `content`; `renderTraceContent` is the canonical formatter.
7
- */
1
+ /** Trace-layer helpers. A trace is a `MemoryEntry` with `layer === 'trace'`: ordered agent actions and their outcome, stored as markdown in `content`
2
+ * (`renderTraceContent` formats it). */
8
3
  export interface TraceStep {
9
4
  action: string;
10
5
  observation: string;
@@ -15,17 +10,7 @@ export interface TraceRecord {
15
10
  steps: TraceStep[];
16
11
  outcome: 'success' | 'failure' | 'partial';
17
12
  }
18
- /**
19
- * Render a trace record as agent-readable markdown.
20
- *
21
- * Format:
22
- * Task: <task>
23
- * Outcome: <outcome>
24
- * Steps:
25
- * 1. <action>
26
- * → <observation> (omitted if observation is empty)
27
- * 2. ...
28
- */
13
+ /** Render a trace record as agent-readable markdown: `Task:`, `Outcome:`, then numbered `Steps:` with each observation on an arrow line (omitted if empty). */
29
14
  export declare function renderTraceContent(rec: TraceRecord): string;
30
15
  /**
31
16
  * Parse a JSON string into an array of TraceStep. Throws on invalid shape.
@@ -1,23 +1,8 @@
1
- /**
2
- * Trace-layer helpers.
3
- *
4
- * A trace is a `MemoryEntry` with `layer === 'trace'` that captures an ordered
5
- * sequence of agent actions and their final outcome. v1 stores steps as
6
- * markdown in `content`; `renderTraceContent` is the canonical formatter.
7
- */
1
+ /** Trace-layer helpers. A trace is a `MemoryEntry` with `layer === 'trace'`: ordered agent actions and their outcome, stored as markdown in `content`
2
+ * (`renderTraceContent` formats it). */
8
3
  import { isJsonString, isJsonObject } from '../util/json.js';
9
4
  import { errorMessage } from '../util/log.js';
10
- /**
11
- * Render a trace record as agent-readable markdown.
12
- *
13
- * Format:
14
- * Task: <task>
15
- * Outcome: <outcome>
16
- * Steps:
17
- * 1. <action>
18
- * → <observation> (omitted if observation is empty)
19
- * 2. ...
20
- */
5
+ /** Render a trace record as agent-readable markdown: `Task:`, `Outcome:`, then numbered `Steps:` with each observation on an arrow line (omitted if empty). */
21
6
  export function renderTraceContent(rec) {
22
7
  const lines = [];
23
8
  lines.push(`Task: ${rec.task}`);
@@ -11,14 +11,8 @@ import { log } from '../util/log.js';
11
11
  import { REPLAY_COUNT_DEFAULT } from './run.js';
12
12
  import { isJsonString } from '../util/json.js';
13
13
  import { DAY_MS } from '../util/time.js';
14
- // -------------------------------------------------------------------------
15
- // 1.4. Auto-promote complete sessions to traces
16
- // -------------------------------------------------------------------------
17
- //
18
- // For each session within the configured window that has a `session_complete`
19
- // event and no existing trace (idempotency via the source_session_id column),
20
- // render the action sequence as markdown and persist a Layer.Trace memory.
21
- // Traces inherit decay, search, replay, and physics from the base MemoryEntry.
14
+ // 1.4. Auto-promote complete sessions to traces: each session in the window with a `session_complete` event and no trace (idempotent via source_session_id)
15
+ // is rendered as markdown and persisted as a Layer.Trace memory, which inherits decay, search, replay and physics.
22
16
  export function promoteSessionTraces(run) {
23
17
  const { result } = run;
24
18
  if (run.dryRun || run.config.autoTraceCapture === false)
@@ -129,23 +123,13 @@ function traceRejected(run, trace, sessionId) {
129
123
  }
130
124
  return true;
131
125
  }
132
- // -------------------------------------------------------------------------
133
- // 1.5. Replay pass — rehearse high-value survivors
134
- // -------------------------------------------------------------------------
135
- //
136
- // Biologically-inspired counterpart to hippocampal replay during slow-wave
137
- // sleep: sample N memories weighted by outcome + valence + under-rehearsal
138
- // + idle time, then apply the same retrieval-strengthening `markRetrieved`
139
- // applies to real queries. Distinct from decay (removal), physics (motion),
140
- // and merge (compression) — this is the "rehearse the important stuff so
141
- // it doesn't fade" pass.
126
+ // 1.5. Replay pass: rehearse high-value survivors by sampling N memories weighted by outcome, valence, under-rehearsal and idle time,
127
+ // then applying the `markRetrieved` strengthening, so important memories don't fade.
142
128
  export function replayPass(run) {
143
129
  const { survivors, now } = run;
144
130
  const replayCount = run.config.replay?.count ?? REPLAY_COUNT_DEFAULT;
145
- // EVAL-ONLY ablation (see ablation.ts): replay rehearsal IS recall
146
- // strengthening (same markRetrieved dynamics), so the strengthen-off arm
147
- // silences the whole pass - markRetrieved would return unmutated entries
148
- // and persisting them anyway would still refresh updated_at / mirrors.
131
+ // EVAL-ONLY ablation (see ablation.ts): replay rehearsal is recall strengthening, so the strengthen-off arm silences the whole pass;
132
+ // persisting unmutated entries anyway would still refresh updated_at and mirrors.
149
133
  if (!(replayCount > 0 && survivors.length > 0 && !isRecallBoostAblated()))
150
134
  return;
151
135
  const seed = Math.floor(now.getTime() / 1000) & 0xffffffff;