@a9i5k4/dsh-auto-memory 2.2.6 → 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.
- package/README.md +20 -10
- package/README.zh-CN.md +22 -10
- package/docs/CONTINUITY-FLOW.md +222 -0
- package/docs/HANDBOOK.md +354 -0
- package/docs/INTEGRATION-ANALYSIS.md +348 -0
- package/docs/M-CM7-HANDOFF-LAYERED-RETRIEVAL.md +311 -0
- package/docs/M8-MEMORY-HUB.md +1 -1
- package/docs/PROMPT-PACK-LAYERED-RECALL.md +474 -0
- package/docs/PROMPT-SET-STRICT.md +389 -0
- package/docs/RELEASE-GO-NOGO.md +82 -0
- package/docs/ROADMAP.md +162 -0
- package/docs/STATUS-BOARD.md +147 -0
- package/docs/USER-GUIDE.en.md +382 -0
- package/docs/USER-GUIDE.zh-CN.md +382 -289
- package/docs/prompts/EXEC-ORDER.md +77 -0
- package/docs/prompts/FEEDING-SCRIPT.md +174 -0
- package/docs/prompts/FEEDING-SEQUENCE.md +61 -0
- package/docs/prompts/FIX-AGENT-M8-2b.md +119 -0
- package/docs/prompts/FIX-AGENT-P11.md +97 -0
- package/docs/prompts/FIX-AGENT-P12-FULL-REGRESSION.md +135 -0
- package/docs/prompts/FIX-AGENT-P12.md +113 -0
- package/docs/prompts/FIX-AGENT-P13-PYTHON-RANK.md +100 -0
- package/docs/prompts/FIX-AGENT-P8.md +120 -0
- package/docs/prompts/FIX-AGENT-P9.md +110 -0
- package/docs/prompts/FIX-AGENT-P9a.md +94 -0
- package/docs/prompts/FIX-AGENT-P9d.md +114 -0
- package/docs/prompts/FIX-AGENT-TEMPORAL-ARM.md +148 -0
- package/docs/prompts/LIVE-VERIFY-ZCODE.md +105 -0
- package/docs/prompts/M8-1-fact-metadata.md +45 -0
- package/docs/prompts/M8-2-ADJUDICATION.md +98 -0
- package/docs/prompts/M8-2-importance-wiring.md +42 -0
- package/docs/prompts/M8-2b-evidence-pipeline.md +52 -0
- package/docs/prompts/M8-3-enable-verify.md +49 -0
- package/docs/prompts/M8-R-REPORT.md +156 -0
- package/docs/prompts/M8-R-research.md +67 -0
- package/docs/prompts/P1-l0-index.md +30 -0
- package/docs/prompts/P10-importance-calibration.md +45 -0
- package/docs/prompts/P11-silent-catch-observability.md +43 -0
- package/docs/prompts/P2-semantic-recall.md +30 -0
- package/docs/prompts/P3-fusion.md +28 -0
- package/docs/prompts/P4-l0-response.md +28 -0
- package/docs/prompts/P5-handoff-anchor.md +28 -0
- package/docs/prompts/P6-ledger-weight.md +27 -0
- package/docs/prompts/P7-write-fix.md +26 -0
- package/docs/prompts/P8-rrf-wiring.md +47 -0
- package/docs/prompts/P9-REVIEW-DECISION.md +95 -0
- package/docs/prompts/P9-evidence-write-coverage.md +113 -0
- package/docs/prompts/README.md +105 -0
- package/docs/prompts/ZCODE-DROPIN.md +229 -0
- package/docs/prompts/_COMMON.md +88 -0
- package/lib/client.js +36 -2
- package/lib/context-host.js +77 -2
- package/lib/evidence-agg.js +81 -0
- package/lib/fact-store.js +32 -0
- package/lib/handoff-anchor.js +114 -0
- package/lib/index.js +402 -43
- package/lib/l0-extract.js +149 -0
- package/lib/l0-index.js +239 -0
- package/lib/m7-wire.js +4 -3
- package/lib/memory-importance.js +70 -0
- package/lib/python-setup.js +16 -4
- package/lib/recall-fusion.js +99 -0
- package/lib/shadow-retrieval.js +2 -2
- package/lib/storage-manage.js +17 -0
- package/lib/subagent-gc.js +8 -1
- package/lib/temporal-parse.js +159 -0
- package/package.json +1 -1
- package/python/worker_semantic_v1.py +28 -1
|
@@ -0,0 +1,311 @@
|
|
|
1
|
+
# M-CM7 · 交接分层检索(Handoff Layered Retrieval)
|
|
2
|
+
|
|
3
|
+
> 写于 2026-09-08,基于 v2.2.5 源码。上位:[M-CM-PLAN.md](M-CM-PLAN.md)、[S3-TARGET-ARCHITECTURE.md](S3-TARGET-ARCHITECTURE.md)。
|
|
4
|
+
> **问题**:接续已从"能不能接上"推进到"接得准不贵"。当前新窗口消费旧内容只有"全量读"与"机械截断"两档,缺中间层。本文探索把分层检索引入**衔接通路**,并给出实施规划。
|
|
5
|
+
> 借鉴来源:OpenViking 公开 README 与论文 VikingMem(arXiv:2605.29640)所描述的分层上下文与目录递归检索机制;**不涉其源码**(AGPLv3,见 S1 §0)。
|
|
6
|
+
|
|
7
|
+
---
|
|
8
|
+
|
|
9
|
+
## 1. 问题陈述:分层已存在,缺的是"逐层收敛"
|
|
10
|
+
|
|
11
|
+
> **2026-09-08 修正**:初版判断"没有分层"有误。源码核对确认 `buildContinueCarry()`(`index.js:2126`)**已实现四层材料**,`index.js:2159` 明确声明:
|
|
12
|
+
> `第0层=指令+白板 / 第1层=交接账本(四段式) / 第2层=近期线程(最近 20 条,单条上限 700 字) / 第3层=完整转写(按需 read)`,总预算 `carryText.slice(0, 18000)`。
|
|
13
|
+
> 因此本节重写:**问题不是没有分层,而是分层被用作"全量平铺",而非"逐层收敛"。**
|
|
14
|
+
|
|
15
|
+
### 1.1 三处使分层失效的实现
|
|
16
|
+
|
|
17
|
+
| # | 位置 | 现状 | 后果 |
|
|
18
|
+
|---|---|---|---|
|
|
19
|
+
| **A** | `:2158` 首条指令 | 「请**先读完**下面的交接材料恢复上下文」 | 分层形同虚设——指令要求全读,模型不会选择性取用 |
|
|
20
|
+
| **B** | `:2168` 第3层指引 | 「**接续前先用 read 工具读取该转写文件**」 | **最大开销点**:强制全量 read 完整转写,分层退化为一刀切全读 |
|
|
21
|
+
| **C** | `:2161-2162` 各层截断 | `plan.slice(0,3000)` / `ledger.slice(0,8000)` / 总 `slice(0,18000)` | 仍是**位置截断**:账本内权重最高的段落(失败原因)可能因排在尾部被整体截掉 |
|
|
22
|
+
|
|
23
|
+
### 1.2 缺的三样(真正的增量)
|
|
24
|
+
|
|
25
|
+
分层(layered material)解决的是"材料怎么组织",尚未解决:
|
|
26
|
+
|
|
27
|
+
1. **锚点索引层**——缺一张"有哪些可下钻的锚点"的廉价地图。当前模型看到的是内容本身,不是索引,因而无从选择。
|
|
28
|
+
2. **段级权重**——四层按**类型**分,未按**重要性**分;账本内部四段无权重,截断时截的是位置。
|
|
29
|
+
3. **按需下钻契约**——当前是"材料全部预置 + 强制 read",缺少"先看索引 → 只取所需 → 确需才读原文"的调用约定。
|
|
30
|
+
|
|
31
|
+
**一句话**:已有分层是**静态组织**;M-CM7 要补的是**动态收敛**。
|
|
32
|
+
|
|
33
|
+
### 1.1 同一失效模式的第三个实例
|
|
34
|
+
|
|
35
|
+
值得单独指出:`lib/ws-overview-rank.js`(M10,2026-09-08)修复的问题——`discoverWorkspaces().slice(0,8)` 按**字母序**取样,导致真正带记忆的活跃工作区排在 20 位开外、永远进不了跨工作区总结——与本项目另外两处已知缺陷同源:
|
|
36
|
+
|
|
37
|
+
| 位置 | 表现 | 出处 |
|
|
38
|
+
|---|---|---|
|
|
39
|
+
| `shadow-retrieval-pre.js:248` | `queryTerms` 按字典序截断 | S2 问题 1 |
|
|
40
|
+
| `ws-overview-rank.js` | 工作区按字母序取样 | M10 issue #24 |
|
|
41
|
+
| **handoff 注入** | 按字符位置截断 | 本文 |
|
|
42
|
+
|
|
43
|
+
**结论**:机械顺序(字典序 / 位置序)代替相关性选择,是本项目反复出现的失效模式。M-CM7 的方案应作为这一模式的统一解法,而非单点修补。
|
|
44
|
+
|
|
45
|
+
---
|
|
46
|
+
|
|
47
|
+
## 2. 借鉴:OpenViking 分层检索的精确机制
|
|
48
|
+
|
|
49
|
+
据公开 README 与 VikingMem 论文,其分层上下文包含三个要点(均为公开描述,非源码):
|
|
50
|
+
|
|
51
|
+
1. **三层表示**:写入时每条内容生成 L0 摘要(~100 tok)/ L1 概览(~2k tok)/ L2 原文,按需加载。
|
|
52
|
+
2. **目录亦分层**:**目录本身携带 L0/L1**(`.abstract` / `.overview`),使 Agent 在读取完整文件前即可判断该目录是否值得下钻。
|
|
53
|
+
3. **目录递归检索**:向量检索先定位得分最高的**目录**,再**逐层向下钻取**;返回结果自带周围上下文。
|
|
54
|
+
|
|
55
|
+
**可迁移的核心命题**:**每一层是一个独立的检索空间**,检索过程是在层间逐层收敛候选,而非在单一扁平空间里做一次 top-k。
|
|
56
|
+
|
|
57
|
+
---
|
|
58
|
+
|
|
59
|
+
## 3. 方案设计:HLR 三层结构
|
|
60
|
+
|
|
61
|
+
为交接语料(PLAN 白板 + 四段式 ledger + 旧会话转写)建立三层,每层一个独立检索空间。
|
|
62
|
+
|
|
63
|
+
### L0 · 锚点层(Anchor Layer)
|
|
64
|
+
|
|
65
|
+
- **内容**:每条交接记录的**结构化锚点**,而非自由摘要。固定 schema:
|
|
66
|
+
```
|
|
67
|
+
[id] 时间 | 状态标记 | 目标(1行) | 下一步(1行) | 关键实体(文件/命令/错误码)
|
|
68
|
+
```
|
|
69
|
+
- **体量**:每条 ≈ 80–120 tok;N 条全量常驻
|
|
70
|
+
- **检索空间**:词法为主(实体、错误码、文件名精确匹配优先)+ 轻量向量
|
|
71
|
+
- **注入策略**:**全量固定注入**
|
|
72
|
+
|
|
73
|
+
### L1 · 段落层(Section Layer)
|
|
74
|
+
|
|
75
|
+
- **内容**:四段各自的完整内容(`## 任务状态` / `## 目标` / `## 已试方案与失败原因` / `## 进度与下一步`),每段 ≤5 行
|
|
76
|
+
- **体量**:单次下钻 ≈ 150–400 tok
|
|
77
|
+
- **检索空间**:词法 + 语义双臂(复用 C1/C2/C3)
|
|
78
|
+
- **取回方式**:工具调用 `memory_recall(scope=handoff, layer=L1, q=…)`
|
|
79
|
+
|
|
80
|
+
### L2 · 原文层(Raw Layer)
|
|
81
|
+
|
|
82
|
+
- **内容**:完整账本原文、旧会话全量转写(`prev-session-*.md`)
|
|
83
|
+
- **取回方式**:现有 `read` 工具 / `memory_recall(scope=sessions)`
|
|
84
|
+
- **改造点**:转写应**分块并索引**,而非整体 read(见 §5 H5)
|
|
85
|
+
|
|
86
|
+
### 3.1 层间收敛流程
|
|
87
|
+
|
|
88
|
+
```
|
|
89
|
+
新窗口启动
|
|
90
|
+
└→ 注入 L0 锚点表(全量、字节稳定)
|
|
91
|
+
↓ 模型读锚点表,判断相关锚点
|
|
92
|
+
↓ 按需:memory_recall(scope=handoff, layer=L1, q=…)
|
|
93
|
+
└→ 命中段落(150–400 tok)
|
|
94
|
+
↓ 确需细节
|
|
95
|
+
└→ L2 分块读取(分块号,非整体)
|
|
96
|
+
```
|
|
97
|
+
|
|
98
|
+
---
|
|
99
|
+
|
|
100
|
+
### 3.4 为什么"纯解析生成锚点"不可行(实际产物核对,2026-09-08)
|
|
101
|
+
|
|
102
|
+
对 `~/.dsh/memory/workspaces/--D--dsh-auto-memory--/handoff/` 实际产物抽样后的结论:**账本与白板是"给人读的自然语言文档",不是"给机器检索的结构化索引"**,二者职责冲突。四条证据:
|
|
103
|
+
|
|
104
|
+
**(1) 段内异质——按段加权必然错配**
|
|
105
|
+
|
|
106
|
+
`handoff-20260908-142730.md` 的「已试方案与失败原因」三条**全部是成功的解法**(PAT push 成功 / npm publish 退出码 0 / 分叉后纯 FF 合并),并非失败。若按段标记权重,会把**高价值的成功经验**误标为"失败原因"——语义即错。
|
|
107
|
+
|
|
108
|
+
**(2) 单段内混装多种性质的内容**
|
|
109
|
+
|
|
110
|
+
同文件「进度与下一步」同时包含:
|
|
111
|
+
- `[x] 2.2.1 发布`(已完成 → 实为**状态**)
|
|
112
|
+
- `[ ] 下一步第一步:console 打 client ctx…`(真正的**待办**)
|
|
113
|
+
- `[ ] 史实以白板「史实更正」段为准`(**元指令**,非待办)
|
|
114
|
+
|
|
115
|
+
段级权重(`失败原因 .35 / 下一步 .30 / …`)加在**整段**上,而段内有价值密度差异极大的条目——加权对象错误。
|
|
116
|
+
|
|
117
|
+
**(3) 写入侧污染:标题重复**
|
|
118
|
+
|
|
119
|
+
抽样最近 6 个账本,**3 个含两个 `# 交接账本` 标题行且时间戳不一致**(如 `handoff-20260908-142730.md` 首行 14:27、第三行 15:00)。纯解析取首个标题将得到错误时间戳,且破坏后续所有段解析。
|
|
120
|
+
|
|
121
|
+
**(4) 白板退化为日志**
|
|
122
|
+
|
|
123
|
+
`PLAN.md` 并列堆积 2.2.5 / 2.2.6 发布状态与历史踩坑记录,无老化机制。白板的定位是"当前树"(git tree),实际写成了"提交日志"(commit log)——Hindsight 的「ONE OBSERVATION PER DISTINCT FACET / PRESERVE HISTORY」要求二者**分离存储**,当前实现未分离。
|
|
124
|
+
|
|
125
|
+
**结论**:锚点索引不能从现有文档**解析**得出,必须在写入侧**另行产出**——即 §3.5 的 **G2′**(结构化 sidecar)。这与 OpenViking 的 `.abstract` / `.overview` **sidecar 与正文分离**是同一设计。
|
|
126
|
+
|
|
127
|
+
---
|
|
128
|
+
|
|
129
|
+
## 3.5 改造清单:现在要改的六处(精确到行)
|
|
130
|
+
|
|
131
|
+
> 全部针对 `buildContinueCarry()`(`index.js:2126-2192`)。按 ROI 排序,**G1+G3 合并即为最小可交付增量**——仅改两处文案/指引,即可消除"强制全读",零结构风险。
|
|
132
|
+
|
|
133
|
+
### G1 · 首条指令:从"先读完"改为"先看锚点,按需取"
|
|
134
|
+
|
|
135
|
+
**位置**:`index.js:2158`
|
|
136
|
+
|
|
137
|
+
| | 文案 |
|
|
138
|
+
|---|---|
|
|
139
|
+
| 现 | `接续上一会话的任务。请**先读完**下面的交接材料恢复上下文,然后直接继续推进未完成事项,不要重新开始。` |
|
|
140
|
+
| 改 | `接续上一会话的任务。先读第0层的**锚点索引**判断需要哪些上下文,再按需取用对应层,然后直接继续推进未完成事项,不要重新开始。锚点索引不足以判断时才 read 完整转写。` |
|
|
141
|
+
|
|
142
|
+
**理由**:分层失效的根源在指令——模型被要求全读,就不会选择性取用。
|
|
143
|
+
|
|
144
|
+
### G2′ · 结构化锚点 sidecar(**取代原"纯解析"方案**)
|
|
145
|
+
|
|
146
|
+
> **2026-09-08 第二次修正**:原 G2 设想"从账本四段纯解析生成锚点",经实际产物核对**不可行**。证据见 §3.4。改为**写入侧产出结构化 sidecar**。
|
|
147
|
+
|
|
148
|
+
**方案**:修改 `refreshRitualPrompt()`(`index.js:2049`),要求 AI 在写账本的**同一轮**内,额外产出一个结构化锚点块,写入 `handoff/anchors-<ts>.json`(或账本末尾的 `<!-- anchors … -->` 注释块)。
|
|
149
|
+
|
|
150
|
+
**为何是同一轮**:AI 此时持有完整上下文,且**不新增 LLM 轮次**——这是满足 0.75 时序约束(§7.3)的关键。
|
|
151
|
+
|
|
152
|
+
**锚点单元 schema**:
|
|
153
|
+
|
|
154
|
+
```json
|
|
155
|
+
{"v":1,"items":[
|
|
156
|
+
{"id":"a1","type":"solution","w":0.9,"text":"npm publish ENEEDAUTH → .npmrc 钉 registry+令牌",
|
|
157
|
+
"refs":["npm","publish","ENEEDAUTH"],"st":"stable"},
|
|
158
|
+
{"id":"a2","type":"todo","w":1.0,"text":"console 打 client ctx 确认 remote 服务真实挂载名",
|
|
159
|
+
"refs":["client.js:45","remote.session"],"st":"volatile"},
|
|
160
|
+
{"id":"a3","type":"meta","w":0.8,"text":"史实以白板「史实更正」段为准","refs":[],"st":"stable"},
|
|
161
|
+
{"id":"a4","type":"status","w":0.4,"text":"2.2.1 发布全链路完成","refs":[],"st":"volatile"}
|
|
162
|
+
]}
|
|
163
|
+
```
|
|
164
|
+
|
|
165
|
+
| 字段 | 说明 |
|
|
166
|
+
|---|---|
|
|
167
|
+
| `type` | 枚举:`solution` 解法 / `failure` 失败 / `todo` 待办 / `meta` 元指令 / `status` 状态 / `goal` 目标 |
|
|
168
|
+
| `w` | **AI 自评权重**(0–1),非硬编码——避免段级加权的错配 |
|
|
169
|
+
| `refs` | 文件名 / 错误码 / 命令 / 行号,供词法精确匹配下钻 |
|
|
170
|
+
| `st` | 稳定性:`volatile` / `stable` / `superseded` |
|
|
171
|
+
|
|
172
|
+
**排序**:`type` 基础优先级 × `w` × 新近度(见 §4.2),**非时间序、非字符序**。
|
|
173
|
+
|
|
174
|
+
**落地要点**:
|
|
175
|
+
- 解析为**纯函数**(`lib/handoff-anchor-pre.js`),schema 校验 fail-soft:sidecar 缺失或非法 → 回退到现有四层平铺,**绝不阻塞接续**。
|
|
176
|
+
- 每个锚点给出 `refs`,使下钻可走 `memory_recall(scope=handoff, ref=…)` 精确定位,而非整篇返回。
|
|
177
|
+
|
|
178
|
+
### G2″ · 顺带修掉两个写入侧缺陷(数据源头质量)
|
|
179
|
+
|
|
180
|
+
| 缺陷 | 证据 | 修法 |
|
|
181
|
+
|---|---|---|
|
|
182
|
+
| **账本标题重复** | 最近 6 个账本中 3 个含 2 个 `# 交接账本` 标题行且时间戳不一致(如 `handoff-20260908-142730.md` 为 14:27 / 15:00) | 追加写入前检测已存在标题,存在则跳过;或改为解析时取**最后一个**标题 |
|
|
183
|
+
| **白板退化为日志** | `PLAN.md` 并列堆积 2.2.5 / 2.2.6 发布状态与历史踩坑记录,无老化机制 | 白板区分「当前状态」与「历史」;历史在版本收敛后移入 `handoff/archive/`(复用现有 PLAN 归档机制) |
|
|
184
|
+
|
|
185
|
+
> **⚠️ 附带风险(需确认)**:`PLAN.md` 中存在形如「PAT 在 `D:\dsh_debug\.dsh-memory\MEMORY.md` 第 5 行(93 字符)」「npm 令牌 `npm_ViUqqR5p…`(MEMORY.md 第 24 行)」的凭证**位置与前缀**描述。`stripSensitiveSections` 是否覆盖此类"指针式"泄露(非完整令牌但指明位置与前缀)**需实测确认**;若未覆盖,应在写入侧门禁(`sanitizeForWrite`)增补规则——这与 README「凭证永不进提示词」的承诺直接相关。
|
|
186
|
+
|
|
187
|
+
### G3 · 第3层:去掉"接续前必须先 read"(**最大 token 节省点**)
|
|
188
|
+
|
|
189
|
+
**位置**:`index.js:2168`
|
|
190
|
+
|
|
191
|
+
| | 文案 |
|
|
192
|
+
|---|---|
|
|
193
|
+
| 现 | `- **接续前先用 read 工具读取该转写文件**,以完全理解旧会话的讨论、结论与未竟事项;任务推进中也可随时回读。` |
|
|
194
|
+
| 改 | `- 完整转写已归档:{path}。**仅在锚点索引与第0–2层不足以推进时才 read**;优先用 memory_recall_pre(scope='sessions', query='关键词') 定位片段,避免整篇读取。` |
|
|
195
|
+
|
|
196
|
+
**理由**:当前实现强制全量 read,分层在此处退化为一刀切。
|
|
197
|
+
|
|
198
|
+
### G4 · 账本按段解析 + 权重化截断
|
|
199
|
+
|
|
200
|
+
**位置**:`index.js:2162`(`ledger.slice(0, 8000)`)
|
|
201
|
+
|
|
202
|
+
改为三段式处理:
|
|
203
|
+
1. **解析**:按 `## 任务状态` / `## 目标` / `## 已试方案与失败原因` / `## 进度与下一步` 切分;
|
|
204
|
+
2. **加权**:失败原因 `0.35` > 下一步 `0.30` > 目标 `0.20` > 任务状态 `0.15`(理由见 §4.2);
|
|
205
|
+
3. **截断**:预算按权重分配,**不足时从最低权重段开始截**,而非截尾部。
|
|
206
|
+
|
|
207
|
+
**效果**:直接消除"权重最高的失败原因因排在尾部被整体截掉"这一故障模式。
|
|
208
|
+
|
|
209
|
+
### G5 · 分层预算取代总截断
|
|
210
|
+
|
|
211
|
+
**位置**:`index.js:2183`(`carryText: parts.join(NL + NL).slice(0, 18000)`)
|
|
212
|
+
|
|
213
|
+
改为:锚点表**固定不截** + 各层独立预算(白板 3000 / 账本 8000 / 线程按条)。避免在高权重内容之前被低优先级内容耗尽总预算。
|
|
214
|
+
|
|
215
|
+
### G6 · 抽纯函数核心 + smoke 锁定
|
|
216
|
+
|
|
217
|
+
新建 `lib/handoff-anchor-pre.js`(纯函数、零 IO、IO 注入,遵循项目 `*-pre.js` 惯例),导出:
|
|
218
|
+
|
|
219
|
+
| 函数 | 职责 |
|
|
220
|
+
|---|---|
|
|
221
|
+
| `parseLedgerSectionsPre(text)` | 四段解析,返回 `{status, goal, failures, next}` |
|
|
222
|
+
| `buildAnchorIndexPre(sections, meta)` | 生成锚点表(权重 × 新近度排序) |
|
|
223
|
+
| `rankSectionsByWeightPre(sections, budget)` | 权重化预算分配与截断 |
|
|
224
|
+
|
|
225
|
+
配套 `tests/smoke/smoke-test-handoff-anchor-pre.mjs`,用 fixture 锁定解析与排序——与 `ws-overview-rank.js`(M10)同一范式。
|
|
226
|
+
|
|
227
|
+
---
|
|
228
|
+
|
|
229
|
+
## 4. 关键约束与解法
|
|
230
|
+
|
|
231
|
+
### 4.1 前缀缓存纪律(硬约束)
|
|
232
|
+
|
|
233
|
+
**风险**:按相关性动态选择注入内容,会破坏"已发请求不可原地改写"的字节级稳定纪律。
|
|
234
|
+
|
|
235
|
+
**解法(关键)**:
|
|
236
|
+
- **L0 锚点表全量固定注入**——不随当前任务变化,因此字节稳定,前缀缓存不失效。
|
|
237
|
+
- **下钻全部经由工具调用**——工具返回值在后续轮次追加,不改写已注入前缀。这与既有架构"静态纪律层 + 动态快照 + 按需取回"完全同构。
|
|
238
|
+
- **净效果**:模型由"被动接受截断"转为"主动按需取回",而前缀缓存纪律不动摇。这是本方案成立的前提,也是它优于"按任务动态裁剪注入"的原因。
|
|
239
|
+
|
|
240
|
+
### 4.2 权重从何而来
|
|
241
|
+
|
|
242
|
+
用户提出"权重分析"诉求。交接内容的权重应**领域化定义**,而非通用相关性:
|
|
243
|
+
|
|
244
|
+
| 段落 | 权重理由 |
|
|
245
|
+
|---|---|
|
|
246
|
+
| **已试方案与失败原因** | **最高**——死路信息不可从其他处推导,重复踩坑成本最高 |
|
|
247
|
+
| **进度与下一步** | 高——决定新窗口的第一个动作(refreshRitual 已要求"下一步必须是可直接执行的第一步,带文件路径或命令") |
|
|
248
|
+
| **目标** | 中——稳定少变 |
|
|
249
|
+
| **任务状态** | 低——易过期,且常可由进展反推 |
|
|
250
|
+
|
|
251
|
+
补充三个权重因子(沿用 S3 §3.3 的稳定性维度):
|
|
252
|
+
- `stability`:`volatile`(进行中)/ `stable`(已决定)/ `superseded`(已被取代)
|
|
253
|
+
- `recency`:最近一次交接优先
|
|
254
|
+
- `explicit`:含可执行命令/文件路径的段落加权
|
|
255
|
+
|
|
256
|
+
**L0 锚点表按 `importance × recency` 排序输出,取代当前的时间序/字符序**——这直接消除 §1.1 的机械顺序问题。
|
|
257
|
+
|
|
258
|
+
### 4.3 生成时机
|
|
259
|
+
|
|
260
|
+
| 方案 | 优劣 |
|
|
261
|
+
|---|---|
|
|
262
|
+
| **写入时生成**(推荐) | `refreshRitualPrompt()` 已在旧会话末触发一次 LLM 调用重写 PLAN + 写 ledger(`:2049`),**顺带产出 L0 sidecar 的边际成本极低**;且写入时上下文最完整 |
|
|
263
|
+
| 读取时惰生成 | 省写入成本,但新窗口首次访问有延迟,且丢失旧会话上下文 |
|
|
264
|
+
|
|
265
|
+
**结论**:写入时生成,与 refreshRitual 同批次产出。
|
|
266
|
+
|
|
267
|
+
---
|
|
268
|
+
|
|
269
|
+
## 5. 实施规划
|
|
270
|
+
|
|
271
|
+
| 阶段 | 内容 | 依赖 | 验收 |
|
|
272
|
+
|---|---|---|---|
|
|
273
|
+
| **H1** | 交接语料结构化:ledger 四段解析 + L0 锚点 sidecar 生成(写入时,过 `sanitizeForWrite`) | 无 | 解析正确性 + 门禁不回退;smoke 函数级 |
|
|
274
|
+
| **H2** | L0 锚点表注入新窗口(替代现有 PLAN≤1200 + ledger≤800 机械截断) | H1 | 注入字节稳定性断言;token 账本对比(改造前/后) |
|
|
275
|
+
| **H3** | `memory_recall` 增 `layer` 参数(L0/L1/L2),支持段级下钻 | H1 | 段级召回正确性;沿用 M5 cite 规范 |
|
|
276
|
+
| **H4** | 权重层:importance × recency × stability 排序,取代机械顺序 | H2 | 排序回归锁定(纯函数 + fixture) |
|
|
277
|
+
| **H5** | 旧会话转写分块 + 索引,L2 改为按块取回 | H3 | 分块不丢信息;按需取回 token 下降 |
|
|
278
|
+
| **H6** | 可观测与评估:衔接成功率、下钻率、token 开销三指标 | H2–H5 | 见 §6 |
|
|
279
|
+
|
|
280
|
+
**建议起点**:H1 + H2 合并为第一个可交付增量——它已经能消除"机械截断"这一最痛点,且不动检索路径。
|
|
281
|
+
|
|
282
|
+
---
|
|
283
|
+
|
|
284
|
+
## 6. 评估指标(与 S1 科学性补强同源)
|
|
285
|
+
|
|
286
|
+
| 指标 | 定义 | 用途 |
|
|
287
|
+
|---|---|---|
|
|
288
|
+
| **衔接成功率** | 新窗口 AI 正确回答"上一窗口在做什么 / 下一步是什么"的比例 | 主指标 |
|
|
289
|
+
| **死路继承率** | 新窗口是否复述出"已试过的失败方案" | 衡量最高权重段落是否生效 |
|
|
290
|
+
| **下钻率** | 需要下钻到 L1/L2 的任务占比 | 验证 L0 是否足以支撑多数任务 |
|
|
291
|
+
| **注入 token** | 新窗口启动时的固定注入开销 | 对比改造前(H2 前后对照) |
|
|
292
|
+
| **总 token** | 注入 + 下钻之和 | 验证"分层是否真的更省" |
|
|
293
|
+
|
|
294
|
+
**实验设计**:构造 N 组"旧窗口做完 → 新窗口接手"的对照任务,分别跑 ①现有固定截断 ②全量 read ③HLR 三层,比较上表指标;配对 bootstrap(B=2000)给差值 CI——**直接复用 M7 的 held-out 评估通路**。
|
|
295
|
+
|
|
296
|
+
---
|
|
297
|
+
|
|
298
|
+
## 7. 风险与边界
|
|
299
|
+
|
|
300
|
+
1. **L0 摘要质量决定上限**:锚点写错,下钻方向即错。缓解:固定 schema 填空(弱模型也能填),不靠自由摘要;并对锚点做可审计落盘。
|
|
301
|
+
2. **生成成本**:每次 refreshRitual 增加一次结构化输出。缓解:与现有调用同批次,非独立调用。
|
|
302
|
+
3. **与官方压缩的边界(阈值 0.75)**:`waterLevelThreshold` 与 `autoContinueThreshold` 已于 2026-09-08 **同步下调至 0.75**(`index.js:229` / `:237`),理由是**官方自动压缩阈值为 80%,必须留余量**(commit `ca75808`);`c4912f4` 进一步把水位检查补到 pre-step,使交接与官方压缩站同一条边界。
|
|
303
|
+
- **对 HLR 的约束**:L0 锚点注入与 refreshRitual 触发**必须发生在 0.75 之前完成**,不得因新增的锚点生成步骤而推迟到 80% 之后——否则交接将被官方压缩抢先,助产失效。H1 的 sidecar 生成是纯文本处理(非 LLM 独立调用,与 refreshRitual 同批次),应据此验证其不引入新的时序风险。
|
|
304
|
+
- 边界重申:**仍只在 host 允许的时点助产,不替 host 决定压缩**。
|
|
305
|
+
4. **不重复造轮子**:L1 检索直接复用 C1/C2/C3 三引擎与现有融合,不新建检索通路。
|
|
306
|
+
|
|
307
|
+
---
|
|
308
|
+
|
|
309
|
+
## 8. 一句话
|
|
310
|
+
|
|
311
|
+
**接续的下半场不是"把更多旧内容塞进新窗口",而是让新窗口先看到一张便宜的地图(L0 锚点表),再自己决定走哪条路——而这张地图必须是固定的,否则前缀缓存就没有了。**
|
package/docs/M8-MEMORY-HUB.md
CHANGED
|
@@ -102,4 +102,4 @@
|
|
|
102
102
|
- [x] 零进程/网络原语卫生(H6)
|
|
103
103
|
- [x] fact store 41 断言 + hub 综合 33 断言
|
|
104
104
|
- [x] 全量回归 35 套件全绿
|
|
105
|
-
- [
|
|
105
|
+
- [x] live 验证(2026-09-09 用户重启 3080 后,执行侧 loopback 代验:GET /memory-hub 200/177ms 三层 overview;hub-pre 落盘 episodes=22/facts=3/procedures=9,含重启后新会话条目;fv2 emit explicit_lane 激活)
|