recallnest 2.2.0 → 2.3.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 (249) hide show
  1. package/.env +4 -0
  2. package/CLAUDE.md +1 -1
  3. package/README.md +30 -5
  4. package/README_CN.md +30 -5
  5. package/config.json +55 -0
  6. package/connectors/examples/email-adapter.ts +73 -0
  7. package/connectors/examples/logs-adapter.ts +103 -0
  8. package/connectors/examples/rss-adapter.ts +95 -0
  9. package/logs/daily-recall.error.log +0 -0
  10. package/logs/daily-recall.log +60 -0
  11. package/logs/ingest-2026-04-11.log +110 -0
  12. package/logs/ingest-2026-04-12.log +90 -0
  13. package/logs/ingest-2026-04-13.log +87 -0
  14. package/logs/launchagent-stderr.log +0 -0
  15. package/logs/launchagent-stdout.log +0 -0
  16. package/package.json +1 -1
  17. package/src/cli.ts +30 -0
  18. package/src/connector-types.ts +57 -0
  19. package/src/conversation-importer.ts +25 -1
  20. package/src/data-checkup.ts +31 -1
  21. package/src/doctor.ts +29 -0
  22. package/src/ingest.ts +203 -0
  23. package/src/mcp-server.ts +2 -2
  24. package/src/obsidian-connector.ts +282 -0
  25. package/src/session-schema.ts +2 -2
  26. package/src/source-heartbeat.ts +108 -0
  27. package/.claude-plugin/CLAUDE.md +0 -29
  28. package/.claude-plugin/marketplace.json +0 -18
  29. package/.dockerignore +0 -11
  30. package/.github/workflows/ci.yml +0 -28
  31. package/.mcp.json +0 -9
  32. package/CHANGELOG.md +0 -51
  33. package/DEMO.md +0 -94
  34. package/Dockerfile +0 -20
  35. package/EVAL.md +0 -89
  36. package/FAILURES.md +0 -75
  37. package/OPERATIONS.md +0 -59
  38. package/ROADMAP.md +0 -245
  39. package/SKILL.md +0 -250
  40. package/assets/dashboard.png +0 -0
  41. package/assets/knowledge-graph.png +0 -0
  42. package/assets/recallnest-workbench.png +0 -0
  43. package/assets/screenshots/ui-full.png +0 -0
  44. package/assets/screenshots/ui-overview.png +0 -0
  45. package/assets/screenshots/ui-search.png +0 -0
  46. package/assets/ui/app.js +0 -1031
  47. package/assets/ui/index.html +0 -224
  48. package/assets/ui/styles.css +0 -781
  49. package/assets/wechat-qr.jpg +0 -0
  50. package/bun.lock +0 -337
  51. package/daily-reflections/2026-03-05.md +0 -15
  52. package/daily-reflections/2026-03-06.md +0 -15
  53. package/daily-reflections/2026-03-07.md +0 -7
  54. package/daily-reflections/2026-03-08.md +0 -34
  55. package/daily-reflections/2026-03-09.md +0 -35
  56. package/daily-reflections/2026-03-10.md +0 -36
  57. package/daily-reflections/2026-03-11.md +0 -35
  58. package/daily-reflections/2026-03-12.md +0 -36
  59. package/daily-reflections/2026-03-13.md +0 -35
  60. package/daily-reflections/2026-03-14.md +0 -35
  61. package/daily-reflections/2026-03-15.md +0 -35
  62. package/daily-reflections/2026-03-16.md +0 -41
  63. package/daily-reflections/2026-03-17.md +0 -10
  64. package/daily-reflections/2026-03-18.md +0 -10
  65. package/daily-reflections/2026-03-19.md +0 -10
  66. package/daily-reflections/2026-03-20.md +0 -10
  67. package/daily-reflections/2026-03-21.md +0 -10
  68. package/daily-reflections/2026-03-22.md +0 -10
  69. package/daily-reflections/2026-03-23.md +0 -10
  70. package/daily-reflections/2026-03-24.md +0 -10
  71. package/daily-reflections/2026-03-25.md +0 -32
  72. package/daily-reflections/2026-03-26.md +0 -37
  73. package/daily-reflections/2026-03-27.md +0 -35
  74. package/daily-reflections/2026-03-28.md +0 -35
  75. package/daily-reflections/2026-03-29.md +0 -35
  76. package/daily-reflections/2026-03-30.md +0 -36
  77. package/daily-reflections/2026-03-31.md +0 -35
  78. package/daily-reflections/2026-04-01.md +0 -35
  79. package/daily-reflections/2026-04-02.md +0 -35
  80. package/daily-reflections/2026-04-03.md +0 -37
  81. package/daily-reflections/2026-04-04.md +0 -37
  82. package/daily-reflections/2026-04-05.md +0 -35
  83. package/daily-reflections/2026-04-06.md +0 -36
  84. package/daily-reflections/2026-04-07.md +0 -35
  85. package/daily-reflections/2026-04-08.md +0 -35
  86. package/daily-reflections/2026-04-12.md +0 -35
  87. package/data/alias-map.example.json +0 -22
  88. package/docs/api-reference.md +0 -1291
  89. package/docs/architecture.md +0 -168
  90. package/docs/memory-boundary-contract.md +0 -226
  91. package/docs/memory-categories.md +0 -119
  92. package/docs/pipeline-audit-ultramemory.md +0 -177
  93. package/docs/plans/2026-03-08-query-expansion.md +0 -270
  94. package/docs/plans/2026-03-16-continuity-layer.md +0 -196
  95. package/docs/plans/2026-04-01-recall-boost.md +0 -100
  96. package/docs/plans/mcp-tiering-plan.md +0 -126
  97. package/docs/research/recall-quality-audit-2026-03-22.md +0 -153
  98. package/docs/self-evolution.md +0 -198
  99. package/docs/superpowers/plans/2026-03-19-ingest-pipeline-upgrade.md +0 -782
  100. package/docs/superpowers/plans/2026-04-11-constructive-retrieval-emotion.md +0 -1195
  101. package/docs/superpowers/specs/2026-03-19-ingest-pipeline-upgrade-design.md +0 -77
  102. package/docs/superpowers/specs/2026-03-23-pull-claude-desktop-design.md +0 -95
  103. package/docs/superpowers/specs/2026-04-11-constructive-retrieval-emotion-design.md +0 -398
  104. package/eval/continuity/results-2026-03-16.md +0 -117
  105. package/eval/continuity/results-2026-03-19.md +0 -453
  106. package/eval/continuity/runbook.md +0 -110
  107. package/eval/continuity/seed-cases.md +0 -54
  108. package/eval/reports/2026-03-06-abstract-query-baseline.md +0 -96
  109. package/eval/reports/2026-03-06-aws-ssh-baseline.md +0 -82
  110. package/eval/reports/2026-03-06-baseline.md +0 -82
  111. package/eval/reports/query-expansion.md +0 -138
  112. package/glama.json +0 -6
  113. package/lm +0 -19
  114. package/plan-philosophy-upgrades.md +0 -363
  115. package/plan-product-upgrades.md +0 -155
  116. package/plan-v1.2-distributable.md +0 -105
  117. package/plan.md +0 -140
  118. package/research-memory-evolution.md +0 -440
  119. package/research-rl-agent-memory.md +0 -330
  120. package/scripts/archive-distilled-junk.ts +0 -116
  121. package/scripts/backfill-anchors.ts +0 -130
  122. package/scripts/backfill-l0l1l2.ts +0 -98
  123. package/scripts/blind-scan.ts +0 -588
  124. package/scripts/cleanup-step1-exact-dups.ts +0 -117
  125. package/scripts/cleanup-step2-template-dups.ts +0 -113
  126. package/scripts/cleanup-step3-stale-content.ts +0 -149
  127. package/scripts/cleanup-step4-orphan-scopes.ts +0 -131
  128. package/scripts/delete-distilled-junk.ts +0 -88
  129. package/scripts/diagnose-vector-search.ts +0 -132
  130. package/scripts/distill-facts.ts +0 -305
  131. package/scripts/health-check.ts +0 -343
  132. package/scripts/incremental-ingest.sh +0 -71
  133. package/scripts/migrate-language.ts +0 -75
  134. package/scripts/mlp-health-check.ts +0 -382
  135. package/scripts/pull-claude-desktop.ts +0 -515
  136. package/scripts/re-ingest-cc.sh +0 -66
  137. package/scripts/rebalance-memory-health.ts +0 -181
  138. package/scripts/run-desktop-ingest.sh +0 -11
  139. package/scripts/start-server.sh +0 -12
  140. package/scripts/verify-emotion-decay.ts +0 -148
  141. package/scripts/viz-dashboard.html +0 -423
  142. package/scripts/viz-export.ts +0 -703
  143. package/src/__tests__/access-tracker-novelty.test.ts +0 -228
  144. package/src/__tests__/activity-counter.test.ts +0 -96
  145. package/src/__tests__/admission-control.test.ts +0 -206
  146. package/src/__tests__/anchor-generator.test.ts +0 -67
  147. package/src/__tests__/auto-consolidation.test.ts +0 -168
  148. package/src/__tests__/auto-recall.test.ts +0 -131
  149. package/src/__tests__/babel-integration.test.ts +0 -139
  150. package/src/__tests__/batch-dedup.test.ts +0 -65
  151. package/src/__tests__/capture-engine.test.ts +0 -1144
  152. package/src/__tests__/capture-heuristic.test.ts +0 -171
  153. package/src/__tests__/cascade-forget.test.ts +0 -210
  154. package/src/__tests__/category-min-scores.test.ts +0 -33
  155. package/src/__tests__/cc8-cc1-essential-context.test.ts +0 -298
  156. package/src/__tests__/circuit-breaker.test.ts +0 -99
  157. package/src/__tests__/cluster-consolidation.test.ts +0 -712
  158. package/src/__tests__/confidence-metadata.test.ts +0 -125
  159. package/src/__tests__/confidence-tracker.test.ts +0 -249
  160. package/src/__tests__/conflict-advisor.test.ts +0 -206
  161. package/src/__tests__/conflict-escalation.test.ts +0 -149
  162. package/src/__tests__/conflict-lifecycle.test.ts +0 -83
  163. package/src/__tests__/conflict-output.test.ts +0 -85
  164. package/src/__tests__/conflict-store.test.ts +0 -374
  165. package/src/__tests__/consolidation-engine.test.ts +0 -181
  166. package/src/__tests__/constructive-retrieval.test.ts +0 -509
  167. package/src/__tests__/context-collapse-renderer.test.ts +0 -214
  168. package/src/__tests__/context-composer-pins.test.ts +0 -64
  169. package/src/__tests__/context-composer-task-selection.test.ts +0 -24
  170. package/src/__tests__/context-reconstructor.test.ts +0 -65
  171. package/src/__tests__/context-renderer.test.ts +0 -91
  172. package/src/__tests__/continuity-eval.test.ts +0 -275
  173. package/src/__tests__/continuity-schema.test.ts +0 -97
  174. package/src/__tests__/conversation-importer.test.ts +0 -692
  175. package/src/__tests__/core-recall-eval.test.ts +0 -235
  176. package/src/__tests__/core-summary.test.ts +0 -109
  177. package/src/__tests__/data-checkup.test.ts +0 -225
  178. package/src/__tests__/decay-exemption.test.ts +0 -84
  179. package/src/__tests__/dedup-actions.test.ts +0 -58
  180. package/src/__tests__/dedup-guard.test.ts +0 -39
  181. package/src/__tests__/deterministic-id.test.ts +0 -39
  182. package/src/__tests__/distill-lock.test.ts +0 -176
  183. package/src/__tests__/doctor.test.ts +0 -303
  184. package/src/__tests__/dream-pipeline.test.ts +0 -232
  185. package/src/__tests__/drill-down.test.ts +0 -108
  186. package/src/__tests__/embedder.test.ts +0 -122
  187. package/src/__tests__/emotion-decay.test.ts +0 -46
  188. package/src/__tests__/emotion-detector.test.ts +0 -56
  189. package/src/__tests__/emotion-phase1-integration.test.ts +0 -153
  190. package/src/__tests__/emotion-retrieval.test.ts +0 -56
  191. package/src/__tests__/entity-resolver.test.ts +0 -58
  192. package/src/__tests__/ethics-layer.test.ts +0 -476
  193. package/src/__tests__/event-segmenter.test.ts +0 -153
  194. package/src/__tests__/feature-flags-integration.test.ts +0 -54
  195. package/src/__tests__/frequency-tracker.test.ts +0 -113
  196. package/src/__tests__/graph-export.test.ts +0 -489
  197. package/src/__tests__/hotness-blend.test.ts +0 -76
  198. package/src/__tests__/ingest.test.ts +0 -360
  199. package/src/__tests__/interference-detector.test.ts +0 -203
  200. package/src/__tests__/kg-extractor.test.ts +0 -184
  201. package/src/__tests__/kg-store.test.ts +0 -198
  202. package/src/__tests__/llm-consolidation.test.ts +0 -226
  203. package/src/__tests__/mcp-efficiency.test.ts +0 -288
  204. package/src/__tests__/memory-boundaries.test.ts +0 -237
  205. package/src/__tests__/memory-evolution-b2-b3-e1.test.ts +0 -243
  206. package/src/__tests__/memory-evolution.test.ts +0 -271
  207. package/src/__tests__/memory-health-rebalance.test.ts +0 -144
  208. package/src/__tests__/memory-lint.test.ts +0 -271
  209. package/src/__tests__/memory-output.test.ts +0 -215
  210. package/src/__tests__/multi-vector.test.ts +0 -242
  211. package/src/__tests__/narrative-architecture.test.ts +0 -456
  212. package/src/__tests__/pending-review.test.ts +0 -77
  213. package/src/__tests__/post-retrieval-filter.test.ts +0 -178
  214. package/src/__tests__/ppr-traversal.test.ts +0 -256
  215. package/src/__tests__/prediction-engine.test.ts +0 -349
  216. package/src/__tests__/predictive-prospective-memory.test.ts +0 -416
  217. package/src/__tests__/preference-guard-smoke.test.ts +0 -211
  218. package/src/__tests__/preference-matcher.test.ts +0 -230
  219. package/src/__tests__/preference-slots.test.ts +0 -205
  220. package/src/__tests__/prospective-memory.test.ts +0 -283
  221. package/src/__tests__/query-entity-detector.test.ts +0 -171
  222. package/src/__tests__/query-expander-alias.test.ts +0 -89
  223. package/src/__tests__/query-expander.test.ts +0 -34
  224. package/src/__tests__/recall-governor.test.ts +0 -227
  225. package/src/__tests__/recall-mode.test.ts +0 -64
  226. package/src/__tests__/result-synthesizer.test.ts +0 -198
  227. package/src/__tests__/resume-context.test.ts +0 -4898
  228. package/src/__tests__/retrieval-trace.test.ts +0 -213
  229. package/src/__tests__/retriever-boundary-weight.test.ts +0 -136
  230. package/src/__tests__/retroactive-boost.test.ts +0 -223
  231. package/src/__tests__/salience-scoring.test.ts +0 -106
  232. package/src/__tests__/scope-inventory.test.ts +0 -200
  233. package/src/__tests__/scope-policy.test.ts +0 -69
  234. package/src/__tests__/session-checkpoint.test.ts +0 -259
  235. package/src/__tests__/session-distiller.test.ts +0 -611
  236. package/src/__tests__/session-gc.test.ts +0 -215
  237. package/src/__tests__/skill-engine.test.ts +0 -546
  238. package/src/__tests__/skill-promotion.test.ts +0 -349
  239. package/src/__tests__/store-scope-audit.test.ts +0 -81
  240. package/src/__tests__/supersede-chain.test.ts +0 -154
  241. package/src/__tests__/temporal-parser.test.ts +0 -241
  242. package/src/__tests__/temporal-validity.test.ts +0 -160
  243. package/src/__tests__/term-registry.test.ts +0 -121
  244. package/src/__tests__/tool-output-compressor.test.ts +0 -133
  245. package/src/__tests__/topic-tag.test.ts +0 -113
  246. package/src/__tests__/trusted-memory.test.ts +0 -828
  247. package/src/__tests__/version-manager.test.ts +0 -213
  248. package/src/__tests__/workflow-observation.test.ts +0 -400
  249. package/src/__tests__/write-verifier.test.ts +0 -122
@@ -1,100 +0,0 @@
1
- # RecallNest 召回优化实施清单
2
-
3
- > 2026-04-01 发现问题:高频信息(如"轮巡仓库")召回失败
4
- > 根因:短查询 vs 长文档 embedding 距离过大 + 无频率加权
5
- > 与已有 P1-P5 互补,本清单聚焦**检索召回**环节
6
-
7
- ---
8
-
9
- ## P0: 短查询召回增强(优先级最高)
10
-
11
- ### P0.1 双层索引 — 原文 + 检索锚点
12
-
13
- - [ ] `capture-engine.ts` / `ingest.ts`:存储时同时生成一句话摘要(≤80 chars),存入 `metadata.anchor`
14
- - [ ] `search.ts`:检索时同时搜原文向量和 anchor 向量,取 max score
15
- - [ ] 效果:短 query "轮巡仓库" 匹配短 anchor "每日轮巡4个win4r仓库",距离大幅缩短
16
- - **预估:** ~120 LOC
17
- - **风险:** 低——不改原文存储,纯增量字段
18
- - **依赖:** 无
19
-
20
- ### P0.2 高频 boost — 重复提及自动提权
21
-
22
- - [ ] 新增 `frequency-tracker.ts`:记录 query→memory 的命中次数
23
- - [ ] 评分公式:`final_score = base_score × (1 + log2(hit_count) × boost_factor)`
24
- - [ ] hit_count ≥ 3 → peripheral 自动升为 core tier
25
- - [ ] 持久化:写入 `data/frequency-stats.json`,跨 session 累积
26
- - **预估:** ~100 LOC
27
- - **风险:** 中——需要平衡 boost 幅度,避免旧高频记忆永远压过新记忆
28
- - **依赖:** 无
29
-
30
- ### P0.3 短查询自动扩展
31
-
32
- - [ ] `search.ts`:检测 query ≤ 6 字符时,调用 LLM 扩展为 3-5 个同义关键词
33
- - [ ] 扩展结果缓存到 `data/query-expansion-cache.json`,相同 query 不重复调用
34
- - [ ] 备选:不用 LLM,维护一个 `data/alias-map.json` 手动/自动映射("轮巡" → "轮巡 仓库 patrol repo 每日检查")
35
- - **预估:** ~60 LOC(alias-map 方案)/ ~100 LOC(LLM 方案)
36
- - **风险:** alias-map 低;LLM 方案增加延迟 ~200ms
37
- - **依赖:** 无
38
-
39
- ---
40
-
41
- ## 高频 vs 查重 平衡机制(P0.2 的关键设计)
42
-
43
- ### 问题
44
-
45
- 高频 boost 和去重是一对矛盾:
46
- - **boost 说**:提到 10 次的东西一定重要,提权!
47
- - **dedup 说**:同一条信息存了 10 遍,应该合并!
48
-
49
- ### 设计方案:分层计数,不是分层存储
50
-
51
- ```
52
- 存储层:dedup 照做,相同内容只保留 1 条(现有 consolidation 逻辑不变)
53
- 计数层:新增 frequency-tracker,记录的是 **query 命中次数**,不是存储条数
54
- ```
55
-
56
- **关键区分:**
57
-
58
- | 维度 | 存储去重 | 召回加权 |
59
- |------|---------|---------|
60
- | 触发时机 | 写入时(store/ingest) | 检索时(search) |
61
- | 操作对象 | 重复的 memory 条目 | query→memory 的命中频率 |
62
- | 目标 | 数据库不膨胀 | 高频信息排前面 |
63
- | 互相影响 | 不影响——去重后只剩 1 条,但那 1 条的 hit_count 持续累积 |
64
-
65
- ### 边界情况处理
66
-
67
- 1. **旧高频 vs 新相关**
68
- - 时间衰减:`effective_hits = hit_count × decay(days_since_last_hit)`
69
- - 30 天没被命中 → hit_count 等效减半,不会永远霸榜
70
-
71
- 2. **高频但已过时**
72
- - 用户说"轮巡仓库从4个变成3个了" → store_memory 更新
73
- - 旧条目被 consolidation 标记为 superseded → hit_count 不继承
74
- - 新条目从 0 开始计,但因为用户接下来会频繁触发,很快追上
75
-
76
- 3. **频率统计粒度**
77
- - 按 memory_id 计数,不按 query 文本
78
- - "轮巡" "轮巡仓库" "patrol repo" 命中同一条 memory → 同一个 counter +1
79
- - 避免同义词分散计数
80
-
81
- ---
82
-
83
- ## 与现有 P1-P5 的关系
84
-
85
- | 现有项 | 关系 |
86
- |--------|------|
87
- | P1 摘要保真 | P0.1 的 anchor 生成需要 P1 的保真约束,但可并行开发 |
88
- | P2 聚类摘要 | 互补——P2 解决注入时省 token,P0 解决检索时找得到 |
89
- | P3 增量 ingest | P0.1 的 anchor 字段需要对已有数据 backfill,P3 的增量逻辑可复用 |
90
- | P4 data-checkup | 可加一项检查:anchor 字段覆盖率(多少 memory 已有 anchor) |
91
- | P5 大文件门控 | 无直接关系 |
92
-
93
- ---
94
-
95
- ## 验证标准
96
-
97
- - [ ] `search_memory("轮巡")` → 返回轮巡仓库相关记忆,score ≥ 70%
98
- - [ ] `search_memory("轮巡仓库")` → 返回结果,score ≥ 80%
99
- - [ ] 高频记忆(命中 ≥5 次)自动出现在 `resume_context` 的 core 区
100
- - [ ] 去重后数据库条目数不增长(frequency 只在 tracker 层累积)
@@ -1,126 +0,0 @@
1
- # MCP Tool Surface Tiering Plan
2
-
3
- ## Goal
4
- Reduce MCP tool surface from 24 to ~10 for daily agents, moving governance tools to CLI-only.
5
-
6
- ## Current Tools (24)
7
-
8
- ### Tier 1: Core (5) — Always Exposed
9
- - `resume_context` — startup continuity
10
- - `search_memory` — proactive recall
11
- - `store_memory` — durable write
12
- - `checkpoint_session` — work handoff
13
- - `latest_checkpoint` — checkpoint read
14
-
15
- ### Tier 2: Advanced (10) — Exposed by Default
16
- - `store_case` — structured case write
17
- - `store_workflow_pattern` — structured pattern write
18
- - `promote_memory` — evidence → durable
19
- - `explain_memory` — retrieval explain
20
- - `distill_memory` — compact briefing
21
- - `brief_memory` — create brief asset
22
- - `pin_memory` — pin for reuse
23
- - `list_assets` — list assets
24
- - `list_pins` — list pins
25
- - `memory_stats` — db stats
26
-
27
- ### Tier 3: Governance (9) — CLI Only, Not MCP
28
- - `workflow_observe`
29
- - `workflow_health`
30
- - `workflow_evidence`
31
- - `list_conflicts`
32
- - `resolve_conflict`
33
- - `audit_conflicts`
34
- - `escalate_conflicts`
35
- - `list_dirty_briefs`
36
- - `clean_dirty_briefs`
37
-
38
- ## Implementation
39
-
40
- ### Step 1: Add Tier Config
41
- Add to `mcp-server.ts`:
42
-
43
- ```typescript
44
- // Environment: RECALLNEST_MCP_TIER=core|advanced|full (default: advanced)
45
- const MCP_TIER = process.env.RECALLNEST_MCP_TIER || "advanced";
46
-
47
- const TOOL_TIERS: Record<string, "core" | "advanced" | "governance"> = {
48
- // Core (always)
49
- resume_context: "core",
50
- search_memory: "core",
51
- store_memory: "core",
52
- checkpoint_session: "core",
53
- latest_checkpoint: "core",
54
-
55
- // Advanced
56
- store_case: "advanced",
57
- store_workflow_pattern: "advanced",
58
- promote_memory: "advanced",
59
- explain_memory: "advanced",
60
- distill_memory: "advanced",
61
- brief_memory: "advanced",
62
- pin_memory: "advanced",
63
- list_assets: "advanced",
64
- list_pins: "advanced",
65
- memory_stats: "advanced",
66
- export_memory: "advanced",
67
-
68
- // Governance (CLI-only)
69
- workflow_observe: "governance",
70
- workflow_health: "governance",
71
- workflow_evidence: "governance",
72
- list_conflicts: "governance",
73
- resolve_conflict: "governance",
74
- audit_conflicts: "governance",
75
- escalate_conflicts: "governance",
76
- list_dirty_briefs: "governance",
77
- clean_dirty_briefs: "governance",
78
- };
79
-
80
- function shouldRegisterTool(toolName: string): boolean {
81
- const tier = TOOL_TIERS[toolName];
82
- if (!tier) return true; // unknown tools always register
83
- if (MCP_TIER === "full") return true;
84
- if (MCP_TIER === "advanced") return tier !== "governance";
85
- if (MCP_TIER === "core") return tier === "core";
86
- return true;
87
- }
88
- ```
89
-
90
- ### Step 2: Wrap Tool Registrations
91
- Replace `server.tool()` calls with conditional registration:
92
-
93
- ```typescript
94
- function registerTool(...) {
95
- if (!shouldRegisterTool(name)) {
96
- console.log(`[MCP] Skipping ${name} (tier: ${TOOL_TIERS[name]})`);
97
- return;
98
- }
99
- server.tool(name, description, schema, handler);
100
- }
101
- ```
102
-
103
- ### Step 3: Update CLI for Governance Tools
104
- Ensure governance tools are fully accessible via CLI:
105
- - `recallnest workflow-observe ...` → already exists
106
- - `recallnest conflicts list ...` → already exists
107
- - Add `recallnest dirty-briefs list/clean` if missing
108
-
109
- ## Testing
110
-
111
- 1. Default run: `bun src/mcp-server.ts` → should register ~15 tools (core + advanced)
112
- 2. Tier=core: `RECALLNEST_MCP_TIER=core bun src/mcp-server.ts` → 5 tools
113
- 3. Tier=full: `RECALLNEST_MCP_TIER=full bun src/mcp-server.ts` → 24 tools (backward compatible)
114
- 4. Smoke test: MCP import works for all tiers
115
-
116
- ## Files to Modify
117
-
118
- - `src/mcp-server.ts` — add tier config + conditional registration
119
-
120
- ## Verification
121
-
122
- ```bash
123
- cd ~/recallnest
124
- RECALLNEST_MCP_TIER=core bun src/mcp-server.ts &
125
- # Check logs for registered tools
126
- ```
@@ -1,153 +0,0 @@
1
- # RecallNest Recall Quality Audit — 2026-03-22
2
-
3
- ## Executive Summary
4
-
5
- This audit assessed three dimensions of RecallNest's memory quality: **ingest noise ratio**, **case/pattern recall relevance**, and **checkpoint content quality**. The system has strong retrieval-side relevance mechanisms (multi-stage scoring, reranking, noise filtering) and robust checkpoint sanitization, but suffers from weak ingest-side validation for evidence-layer data and a critical gap in case recall — 5,853 stored cases are effectively invisible due to over-aggressive filtering. The top 5 issues are ranked below with concrete fix suggestions.
6
-
7
- ---
8
-
9
- ## Top 5 Highest-Impact Quality Issues
10
-
11
- ### 1. Case Recall is Effectively Broken (CRITICAL)
12
-
13
- **Finding**: 0 out of 5 probes returned any case results, despite 5,853 cases in the store. Vector search finds relevant cases (similarity 0.70–0.74), but the selection pipeline filters them all out.
14
-
15
- **Root cause**: `isTaskCandidateUseful` in `src/ranking.ts:168` rejects non-structured cases (`if (category === "cases" && !structured) return false`). Most stored cases are raw transcript chunks in `cc:` scopes, not structured `Case: problem/solution` format. Additionally, `selectTaskResults` in `src/context-composer-task-selection.ts:298-300` filters non-durable candidates when durable ones exist.
16
-
17
- **Impact**: The entire case recall subsystem provides zero value. Users who stored debugging solutions, fix recipes, or incident resolutions never see them recalled.
18
-
19
- **Fix suggestion**:
20
- - **File**: `src/ranking.ts` — `isTaskCandidateUseful` function (~line 168)
21
- - **Approach**: Relax the structured-only filter for cases with high vector similarity (>0.72). Add a fallback path: if zero structured cases pass, allow top-N unstructured cases with high similarity scores through. This preserves precision for normal recall but prevents the "zero results" cliff.
22
- - **Classification**: Quick win (localized change, testable in isolation)
23
-
24
- ### 2. Noise Filtering Only at Retrieval, Not Ingest (MODERATE-HIGH)
25
-
26
- **Finding**: The noise filter in `src/noise-filter.ts` only runs during `hybridRetrieval()` and `vectorOnlyRetrieval()` — NOT during ingest. Noisy data (bash progress output, screenshot base64, tool-use tags, system messages, permission instructions) is stored permanently in the evidence layer. The noise occupies embedding space, dilutes vector search quality, and wastes MMR diversity budget on filtering out junk.
27
-
28
- **Root cause**: The ingest pipeline in `src/ingest.ts` only validates on text length (> 8 chars). No content quality check, no protocol filtering, no diagnostic artifact detection. 59.2% of all 39,580 entries are category "fact" — many are low-signal transcript snippets. 84.5% are from ephemeral `cc:*` session scopes.
29
-
30
- **Impact**: The store is bloated with low-value entries. Retrieval-side filtering is a band-aid — the noisy entries still consume storage, slow vector search, and can occasionally leak through retrieval filters into recall results.
31
-
32
- **Fix suggestion**:
33
- - **File**: `src/ingest.ts` — add pre-storage filtering after chunking
34
- - **File**: `src/noise-filter.ts` — extract shared noise patterns into reusable functions
35
- - **Approach**: Apply the existing noise filter patterns at ingest time as a hard gate. Add additional ingest-specific patterns: reject chunks under 30 chars matching boilerplate, base64-heavy content, bash progress output, and tool-use protocol tags. Score chunk information density and skip purely routine/acknowledgment content.
36
- - **Classification**: Deeper refactor (needs heuristic set + testing against real transcripts to avoid false negatives)
37
-
38
- ### 3. Checkpoint Scope Normalization Gap (MODERATE)
39
-
40
- **Finding**: Three different scope strings exist for the same project: `project:recallnest` (114 checkpoints), `recallnest` (24), and `project:RecallNest` (4). A `resume_context` call with one variant misses checkpoints stored under another.
41
-
42
- **Root cause**: No scope normalization at checkpoint save time. The 24 `recallnest` checkpoints are from March 16–17 before conventions solidified. The 4 `project:RecallNest` checkpoints have a case mismatch.
43
-
44
- **Impact**: `getLatest()` by scope can return a stale checkpoint instead of the truly latest one if the most recent was stored under a non-canonical scope string. This directly affects continuity recovery quality.
45
-
46
- **Fix suggestion**:
47
- - **File**: `src/session-engine.ts` — checkpoint save path
48
- - **Approach**: Add a `normalizeScope()` function that lowercases and ensures `project:` prefix. Apply it both at save time and at query time. For historical data, run a one-time migration script to normalize existing checkpoint scopes.
49
- - **Classification**: Quick win (small utility function + migration script)
50
-
51
- ### 4. Empty/Fallback Checkpoints Displace Useful Recovery Data (MODERATE)
52
-
53
- **Finding**: ~44% of checkpoints (69 of 156) have sanitization artifacts. Of these, ~10% (16) have only fallback summary text ("Checkpoint captured current task state without repo-state details.") plus empty structured fields. These provide zero recovery value but can be returned by `getLatest()`, displacing useful checkpoints.
54
-
55
- **Additional concern**: No checkpoint expiry mechanism exists. All 156 checkpoints persist indefinitely (156 files in ~6 days = ~9,500/year projected). No age-based pruning, no size limits, no archive mechanism. File-system based storage means O(n) scan on every retrieval.
56
-
57
- **Root cause**: The checkpoint API accepts and stores checkpoints even when all meaningful fields are empty or sanitized away.
58
-
59
- **Impact**: If a fallback-only checkpoint is the most recent for a scope, `resume_context` returns useless continuity data. Combined with no expiry, checkpoint directory will grow unbounded.
60
-
61
- **Fix suggestion**:
62
- - **File**: `src/session-engine.ts` — `checkpoint_session` handler
63
- - **Approach**: (a) Add a quality gate before saving: if summary would be fallback AND decisions/openLoops/nextActions are all empty, either reject with a warning or mark as `quality: "minimal"` so `getLatest()` can prefer higher-quality alternatives. (b) Add checkpoint age check in `resume_context` — warn if > 24h old. (c) Implement expiry: archive checkpoints older than 30 days.
64
- - **Classification**: Quick win for quality gate; medium effort for expiry
65
-
66
- ### 5. Importance Defaults Too Permissive + Weak Tier Inference (MODERATE)
67
-
68
- **Finding**: Most ingested transcript memories get default importance 0.7 — no distinction between high-value technical insights and casual chat. Tier assignment is purely category-based (`profile`/`patterns` -> "working", everything else -> "peripheral") with no semantic quality analysis.
69
-
70
- **Root cause**: No importance scoring at ingest time. The decay engine (`src/decay-engine.ts`) uses a 3-tier system (core/working/peripheral) with different Weibull decay curves, but tier promotion requires 3+ accesses or importance >= 0.5 (peripheral -> working) or 10+ accesses or importance >= 0.8 (working -> core). Since everything starts at 0.7 importance, most evidence-layer memories sit at "peripheral" tier forever.
71
-
72
- **Impact**: Low-value transcript entries compete fairly with high-value durable memories in retrieval scoring. The importance weight formula `0.7 + 0.3 * importance` gives a 0.7-importance entry 91% the score of a 1.0-importance entry — barely distinguishable.
73
-
74
- **Fix suggestion**:
75
- - **File**: `src/ingest.ts` — post-parse stage; `src/decay-engine.ts` — tier logic
76
- - **Approach**: Use LLM (already integrated via `smartExtractBatch` in ingest.ts:328) to assign importance during ingestion. For non-LLM path, use heuristics: code-heavy content -> importance 0.8, error resolution -> 0.85, boilerplate -> 0.3. Widen the importance multiplier range (e.g., `0.5 + 0.5 * importance`) to make it more discriminating.
77
- - **Classification**: Deeper refactor (needs scoring model + tuning)
78
-
79
- ---
80
-
81
- ## Additional Findings
82
-
83
- ### What's Working Well
84
-
85
- | Area | Rating | Evidence |
86
- |---|---|---|
87
- | Tool output filtering | Excellent | 98.7% clean — `parseCCTranscript` type filter is effective |
88
- | Hybrid retrieval pipeline | Excellent | 8-stage scoring with RRF fusion, Weibull decay, MMR diversity |
89
- | Checkpoint schema design | Good | Strict Zod validation, appropriate field limits, well-structured |
90
- | Repo-state sanitizer (post-deploy) | Excellent | Zero leaks since March 18 deployment |
91
- | Checkpoint summary quality | Good | 75% of checkpoints have rich, actionable content |
92
- | Durable memory dedup | Good | Two-stage vector + LLM semantic dedup with canonical key matching |
93
- | Cross-encoder reranking | Good | Jina/Pinecone/Voyage reranking available for semantic re-ranking |
94
- | Retrieval profiles | Good | 4 task-tuned profiles (default, writing, debug, fact-check) with appropriate tuning |
95
- | Cue coverage diversity | Good | Greedy set-cover algorithm prevents duplicate pattern recall |
96
- | Entity capture | Good | Specific, useful entities (file paths, tool names, PR refs). 8-entity limit sufficient |
97
-
98
- ### Pattern vs Case Recall Asymmetry
99
-
100
- Patterns recall well because they tend to be durable and structured (967 eligible entries, 2.5% of store). Cases fail because the same filtering criteria are applied but cases in the store are overwhelmingly unstructured transcript chunks. This is a design asymmetry — the system was built for curated patterns but cases accumulated organically.
101
-
102
- ### Dedup Gap When LLM Unavailable
103
-
104
- Evidence-layer transcript ingest skips LLM semantic dedup if no embedder is available (`src/ingest.ts:817-821`) — it queues for later processing but still ingests the raw chunk with only vector dedup. When LLM is unavailable, borderline-similar chunks (similarity 0.68-0.80) are stored as separate entries, leading to near-duplicate pollution.
105
-
106
- ### Checkpoint Coverage Details
107
-
108
- - 156 checkpoints across 94 sessions (March 16-22)
109
- - March 21 has only 3 checkpoints vs 28-46 on other days — potential gap
110
- - `resume_context` correctly uses checkpoint as first line of recovery with entity supplementation
111
- - 220-char headline truncation loses detail from rich summaries, but full checkpoint is available in response body
112
- - **No checkpoint-to-durable promotion pipeline**: High-quality checkpoint decisions never automatically become durable memories
113
- - **Limited coverage in resume_context**: Only 3-5 lines from checkpoint extracted (<5% of max checkpoint content)
114
-
115
- ### Distillation Opportunity
116
-
117
- 23,441 "fact" entries could be periodically distilled into fewer, higher-quality durable memories. This would improve the signal-to-noise ratio of the entire store and make vector search more effective. The existing `distill_memory` tool could be leveraged for this.
118
-
119
- ---
120
-
121
- ## Quick Wins vs Deeper Refactors
122
-
123
- ### Quick Wins (1-2 days each)
124
-
125
- 1. **Relax case recall filter** — Allow high-similarity unstructured cases when zero structured cases match (`src/ranking.ts`)
126
- 2. **Scope normalization** — `normalizeScope()` at save + query time (`src/session-engine.ts`)
127
- 3. **Empty checkpoint gate** — Reject or flag checkpoints with all-fallback content (`src/session-engine.ts`)
128
- 4. **Historical data cleanup** — Re-sanitize 9 pre-guard checkpoint files (one-time script)
129
- 5. **Checkpoint staleness warning** — Warn in `resume_context` when checkpoint is >24h old (`src/context-composer.ts`)
130
-
131
- ### Deeper Refactors (1-2 weeks each)
132
-
133
- 1. **Ingest-time noise filtering** — Apply noise patterns + content quality scoring at ingest (`src/ingest.ts` + `src/noise-filter.ts`)
134
- 2. **Importance scoring at ingest** — LLM or heuristic-based importance assignment during ingestion (`src/ingest.ts`)
135
- 3. **Case promotion pipeline** — Auto-promote high-quality `cc:` cases to `memory:` scope based on structure detection and retrieval frequency
136
- 4. **Fact distillation pipeline** — Periodic batch job to consolidate 23,441 low-value fact entries into curated durable memories
137
- 5. **Checkpoint expiry and indexing** — Archive old checkpoints + migrate from filesystem scan to indexed storage
138
- 6. **Checkpoint-to-durable promotion** — Auto-promote high-quality decisions/nextActions to `events` or `cases` memory category
139
-
140
- ---
141
-
142
- ## Methodology
143
-
144
- - **Architecture review**: Full codebase analysis of 89 source files (~19,500 LOC TypeScript) across all subsystems — ingestion, retrieval, checkpoint, conflict, workflow observation.
145
- - **Ingest noise analysis**: Traced the parser pipeline through `src/ingest.ts`, analyzed noise filter patterns in `src/noise-filter.ts`, reviewed dedup thresholds and LLM fallback behavior. Parsed 10 real CC transcripts, classified 792 text blocks for noise type.
146
- - **Case/pattern recall analysis**: Ran 5 `composeResumeContext` probes with different task prompts against `project:recallnest` scope. Traced the selection pipeline through `src/ranking.ts` and `src/context-composer-task-selection.ts`. Compared vector search results vs final pipeline output.
147
- - **Checkpoint audit**: Schema analysis of `src/session-schema.ts` + `src/session-engine.ts`, then quality review of all 156 checkpoint files from March 16-22. Field-level emptiness analysis, scrubbing effectiveness verification, scope distribution analysis.
148
- - **Retrieval pipeline audit**: Full trace through `src/retriever.ts` 8-stage scoring pipeline, `src/decay-engine.ts` Weibull decay, `src/embedder.ts` multi-provider embedding, and `src/retrieval-profiles.ts` task-tuned profiles.
149
-
150
- ---
151
-
152
- *Report generated 2026-03-22 by recallnest-quality-8ad2b7 team (coordinator + 3 research agents)*
153
- *Supersedes earlier draft by recallnest-quality-69722c team*
@@ -1,198 +0,0 @@
1
- # Self-Evolution: How RecallNest Memories and Workflows Evolve
2
-
3
- > 自我进化原理:RecallNest 不只让记忆自己整合、衰减、上浮,也开始观察 workflow 什么时候做对、什么时候做错。
4
-
5
- ## Overview
6
-
7
- Traditional memory systems are append-only: store everything, search later, hope for the best. Over time, they bloat with duplicates, outdated entries, and noise.
8
-
9
- RecallNest takes a different approach: **memories evolve**. They consolidate, decay, and surface based on usage — just like biological memory.
10
-
11
- ```
12
- Store → Classify → Decay → Access → Consolidate → Promote/Demote
13
- │ │ │ │ │ │
14
- ▼ ▼ ▼ ▼ ▼ ▼
15
- New 6 types Weibull "Use it Merge Core ↔
16
- memory auto- curve or lose similar Working ↔
17
- assigned over it" entries Peripheral
18
- time
19
- ```
20
-
21
- ---
22
-
23
- ## Workflow Observation Loop
24
-
25
- RecallNest now separates self-evolution signals from regular memory.
26
-
27
- Instead of turning every workflow failure into another `events` row, RecallNest records workflow observations in a dedicated append-only store:
28
-
29
- ```
30
- Observe → Inspect → Health → Evidence → Fix / Test
31
- │ │ │ │ │
32
- ▼ ▼ ▼ ▼ ▼
33
- record aggregate degrade package repair the
34
- success/ 7d / 30d or stay top workflow,
35
- failure health healthy signals then observe again
36
- ```
37
-
38
- - **`workflow_observe`** records whether `resume_context`, `checkpoint_session`, or another workflow primitive succeeded, failed, was corrected, or was missed
39
- - **`workflow_health`** aggregates recent observations into a health report or degraded-workflow dashboard
40
- - **`workflow_evidence`** packages recent issue observations and suggestions so tests, rules, and prompts can be tightened
41
- - these records live outside the 6 memory categories and are not composed into `resume_context`
42
- - managed MCP / HTTP continuity calls now append `resume_context` / `checkpoint_session` observations automatically, and checkpoint repo-state sanitization is recorded as `corrected`
43
-
44
- That boundary is deliberate: self-evolution needs operational telemetry, not more noisy durable memory.
45
-
46
- ---
47
-
48
- ## The Three-Tier Lifecycle
49
-
50
- Every memory lives in one of three tiers:
51
-
52
- | Tier | Description | Typical Size |
53
- |------|-------------|--------------|
54
- | **Core** | Essential knowledge, accessed frequently | ~5% of total |
55
- | **Working** | Actively useful, moderate access | ~25% of total |
56
- | **Peripheral** | Rarely accessed, candidates for archival | ~70% of total |
57
-
58
- > 三层生命周期:核心层(常用的 5%)→ 工作层(中等频率 25%)→ 边缘层(低频 70%)
59
-
60
- ### Promotion and Demotion
61
-
62
- Memories move between tiers based on access patterns:
63
-
64
- - **Promotion** (peripheral → working → core): Memory accessed ≥ N times within a window
65
- - **Demotion** (core → working → peripheral): Memory not accessed for extended period
66
- - **Archival**: Peripheral memories with zero access beyond decay threshold get archived (not deleted)
67
-
68
- ---
69
-
70
- ## Weibull Decay
71
-
72
- RecallNest uses the [Weibull distribution](https://en.wikipedia.org/wiki/Weibull_distribution) for time-based memory decay, inspired by human forgetting curves.
73
-
74
- > Weibull 衰减模型比简单的线性衰减更符合人类遗忘曲线:开始衰减慢,后面加速。
75
-
76
- ### Why Weibull, not Exponential?
77
-
78
- | Model | Behavior | Problem |
79
- |-------|----------|---------|
80
- | Linear | Constant decay rate | Too aggressive early on |
81
- | Exponential | Fast initial decay | Important but old memories vanish too quickly |
82
- | **Weibull** | Slow start, accelerating decay | Matches human memory: recent stays fresh, old fades naturally |
83
-
84
- ### Formula
85
-
86
- ```
87
- decay(t) = exp(-(t / λ)^k)
88
-
89
- where:
90
- t = days since last access
91
- λ = scale parameter (half-life, default: 120 days)
92
- k = shape parameter (default: 1.5, gives the "slow then fast" curve)
93
- ```
94
-
95
- ### Impact on Search
96
-
97
- Decay factor multiplies the retrieval score:
98
-
99
- ```
100
- final_score = relevance_score × decay(days_since_access)
101
- ```
102
-
103
- A highly relevant but stale memory can still surface if the semantic match is strong enough.
104
-
105
- ---
106
-
107
- ## Memory Consolidation
108
-
109
- Over time, you accumulate many memories about the same topic. Consolidation merges them.
110
-
111
- > 记忆整合:找到主题相近的记忆簇,按策略合并或去重,保持记忆库精简。
112
-
113
- ### Merge vs. Append Strategies
114
-
115
- | Category | Strategy | Why |
116
- |----------|----------|-----|
117
- | `profile` | **Merge** | User identity evolves; latest version wins |
118
- | `preferences` | **Merge** | Preferences update within the same slot; concrete item preferences stay separate |
119
- | `entities` | **Merge** | Entity info accumulates; consolidate |
120
- | `patterns` | **Merge** | Patterns refine over time |
121
- | `events` | **Append** | Events are facts; dedup but keep distinct entries |
122
- | `cases` | **Append** | Case studies are unique; dedup only exact matches |
123
-
124
- ### How It Works
125
-
126
- 1. For each category, compute pairwise cosine similarity
127
- 2. Cluster entries with similarity > threshold (default: 0.85)
128
- 3. For **merge** categories: LLM combines the cluster into one entry, archives originals
129
- 4. For **append** categories: remove exact duplicates, keep distinct entries
130
- 5. Update access counts (merged entry inherits the sum)
131
-
132
- `preferences` needs one extra guard: do not collapse same-brand, different-item preferences into one topic-level memory. A summary can exist, but it should not replace the atomic preference facts. The same idea now also applies to slot-aware reply-style and tool-choice preferences.
133
-
134
- ### Safety
135
-
136
- - Default mode is **dry-run**: preview changes before applying
137
- - Original entries are **archived**, never deleted
138
- - Consolidation is triggered manually or via scheduled task, never automatic
139
-
140
- ---
141
-
142
- ## Gap Detection
143
-
144
- RecallNest tracks what you search for and notices when searches consistently return poor results.
145
-
146
- > 缺口检测:分析搜索日志,找出你经常问但记忆库覆盖不足的主题。
147
-
148
- ### How It Works
149
-
150
- 1. Log every search query and its top result score
151
- 2. Periodically analyze: which topics have avg score < threshold?
152
- 3. Cluster low-score queries by topic
153
- 4. Generate a gap report with suggestions
154
-
155
- ### Example Gap Report
156
-
157
- ```
158
- Topic: "deployment pipeline"
159
- Searches: 8 in last 30 days
160
- Avg top score: 0.12
161
- Suggestion: Consider documenting your deployment workflow
162
-
163
- Topic: "API rate limiting"
164
- Searches: 5 in last 30 days
165
- Avg top score: 0.18
166
- Suggestion: Store your rate limiting strategy and past incidents
167
- ```
168
-
169
- ---
170
-
171
- ## Access-Based Surfacing ("Use It or Lose It")
172
-
173
- > 用进废退:经常被搜到的记忆权重上升,长期无人问津的权重下降。
174
-
175
- The access tracker records every time a memory appears in search results. This creates a feedback loop:
176
-
177
- ```
178
- Accessed often → higher tier → higher base score → more likely to surface
179
- Never accessed → lower tier → lower base score → gradually fades
180
- ```
181
-
182
- This is the "use it or lose it" principle applied to AI memory.
183
-
184
- ---
185
-
186
- ## Putting It All Together
187
-
188
- A typical memory lifecycle:
189
-
190
- 1. **Day 0**: New memory stored → classified as `events` → tier: `peripheral`
191
- 2. **Day 1-30**: Searched 5 times → promoted to `working`
192
- 3. **Day 30-90**: Searched 15 more times → promoted to `core`
193
- 4. **Day 120**: Consolidated with 3 similar memories → single refined entry
194
- 5. **Day 180+**: Access drops to zero → demoted to `working`
195
- 6. **Day 365+**: Still no access → demoted to `peripheral`, Weibull decay significant
196
- 7. **Archival**: If importance < threshold after extended inactivity → archived
197
-
198
- The result: your memory index stays lean, relevant, and self-maintaining.