版本: v3 (2026-04-16) · 位置: ~/Desktop/skill-knowledge-base/ · git 仓库已就绪
目标:把 Claude Code 的日常对话自动萃取成结构化知识,合并进 88 个 skill 的 *_knowledge.md,越用越聪明。
run.sh 只处理 last_ts.txt 之后的新对话| 文件 | 职责 | 行数 | 状态 |
|---|---|---|---|
scripts/run.sh | 一键入口:extract → merge → validate → commit | ~60 | 稳定 |
scripts/extract.sh | S0+S1+S2 三阶段萃取,输出 changelog.md | ~430 | v3 优化 |
scripts/s0_filter.py | 规则过滤(tool/code/时间戳精简) | ~430 | 新建 |
scripts/merge.sh | 按 skill 并发合并 + INDEX 写回 + git commit | ~240 | 修3bug |
scripts/validate.sh | 88 skill 的 knowledge.md 结构校验 | ~150 | 稳定 |
shared_schema.md | 17 实体 + 14 关系类型 + 决策树(S2/merge prompt 都引用) | 90 | 稳定 |
GLOBAL_INDEX.md | 88 skill 的速查表(每次 merge 后重写) | ~400 | 稳定 |
*_knowledge.md × 88 | 每个 skill 的知识文件 | — | 稳定 |
last_ts.txt | 增量游标(UTC ISO8601) | 1 | .gitignore 排除 |
changelog.md | S2 本轮产出暂存,merge 成功后清空 | 动态 | 通过 git 留痕 |
位置: scripts/s0_filter.py(extract.sh 调用)
成本: 0(纯 Python 规则)· 压缩率: 25-31%(对话型)/ 12% (纯讨论型)
[tool:Read {"file_path": "/a/b/c.sh", "offset": 160, "limit": 20}]
→ [tool:Read c.sh:160-180]
[tool:Grep {"pattern": "xxx", "path": "/long/path", "output_mode": "content"}]
→ [tool:Grep pattern='xxx' @path]...(N 行略)...[HH:MM:SS] 会破坏下游 session 分批 regex[tool:XXX keys=[a,b,c] 300B]任务: 删除闲聊/元讨论,保留技术变更段落的完整原文(不做摘要)
prompt 结构: system(S1_SYSTEM 规则) + user(INDEX[:6000] + batch_text)
退化链路: 见 §6
规则:
1. 删除:闲聊、确认("好的""继续")、调试中间过程、重复描述
2. 保留:bug 发现/修复、配置变更、架构决策、新功能实现、踩坑记录
3. 保留原文!不要摘要、不要改写。加段落标注 --- [skill] [ADD/UPDATE] 标题 ---
4. 删除元讨论(知识库系统本身的讨论)
5. 保留时间戳 [2026-xx-xxTxx:xx:xx.xxxZ]
6. 不使用任何工具 · 直接输出纯文本
任务: 读 S1 过滤结果 → 输出 ADD/UPDATE/DELETE 条目(参考 shared_schema.md)
主模型: claude -p opus(本地)· 兜底: OpenRouter anthropic/claude-opus-4-6
规则: 同一变更只输出一条 · 必须含硬数据(端口/函数名/路径)· 不记录元讨论
### 2026-04-16 skill-name ADD
- 变更描述(含硬数据)
- 源: session_xxx
### 2026-04-16 skill-name UPDATE
- 变更描述
- 源: session_xxx
并发: MAX_PARALLEL=3(避免 claude -p 挤占)
tmp/changelog_{skill}.txt,缺 knowledge.md 的走 tmp/newskill_{skill}.txt v3 修复 #1INDEX_UPDATED=1 才清空;异常时 changelog 保留 + .bak 备份2026-04-16 并行起 6 个 subagent,在 3 个代表性 session(6K/27K/48K chars)上测 7 个 OpenRouter 模型。
| 模型 | 914f3be2 (6K) | b3493ded (27K) | 5baa4a1e (48K) | 保留率 | 速度 | 稳定 | 评价 |
|---|---|---|---|---|---|---|---|
| claude-haiku-4.5 | OK 10% / 5s | OK 14% / 21s | 代理断 | 10-14% | 最快 | 2/3 | 首选(删最干净) |
| deepseek-v3.2 | OK 23% / 20s | OK 27% / 72s | OK 38% / 227s | 23-38% | 慢 | 3/3 | 兜底(唯一全过) |
| claude-sonnet-4.5 | OK 26% / 9s | 断 | 断 | 26% | 快 | 1/3 | 贵 8× 不推 |
| gemini-2.5-flash | OK 25% / 4s | OK 61% / 31s | OK 63% / 51s | 25→63% | 最快 | 3/3 | 大样本基本不删 |
| minimax-m2.7 | OK 65% / 43s | OK 55% / 91s | 断 | 55-65% | 中 | 2/3 | 保留过多 |
| qwen3-397b | OK 14% / 97s | 断 | OK 29% / 208s | 14-29% | 慢(thinking) | 2/3 | 贵 + 93% reasoning |
| grok-4.20 | OK 23% / 3s | 断 | 断 | 23% | 快 | 1/3 | 数据不足 |
anthropic/claude-haiku-4.5:nitro — 保留率 10-14% 真正做了过滤(S2 opus 能兜)deepseek/deepseek-v3.2-exp:nitro — 3/3 通过最稳claude -p sonnet — 走本地不经代理层| 参数 | 值 | 位置 | 理由 |
|---|---|---|---|
MAX_BATCH | 15000 | extract.sh Python | 实测 30K 仍被 Cloudflare RST,15K 是可靠安全区 |
call_openrouter_split retries | 2 | extract.sh L325 | RST 是硬拒绝不是抖动,重试 5 次浪费 77s |
max_tokens | 16000 | call_openrouter_split | 大 session 过滤后仍可能 >8K tokens,避免 finish=length 截断 |
| 模型后缀 | :nitro | 两处 | OpenRouter 官方 feature,自动选最快 provider |
MAX_PARALLEL | 3 | merge.sh | 避免 claude -p 挤占,平衡速度和成功率 |
| 增量阈值 | 5000 B | extract.sh | 小于此值不触发 AI 萃取 |
| S0 代码块阈值 | 30 行 | s0_filter.py | 超过则保留前 15 + 后 5 |
| shared_schema | INDEX[:6000] | S1 prompt | 过长会影响 S1 过滤效率 |
S1 调用流程
├─ 主路径: OpenRouter anthropic/claude-haiku-4.5:nitro × retry=2
│ ├─ 成功 → 进入 S2
│ └─ 失败
├─ 兜底 1: OpenRouter deepseek/deepseek-v3.2-exp:nitro × retry=2
│ ├─ 成功 → 进入 S2
│ └─ 失败
└─ 兜底 2: claude -p --model sonnet (本地)
└─ 成功 → 进入 S2(~100-200s/批)
S2 调用流程
├─ 主路径: claude -p --model opus (本地)
└─ 兜底: OpenRouter anthropic/claude-opus-4-6
Empty reply from server / RemoteDisconnected)
把 prompt + 对话拼在单个 user message 里,OpenRouter WAF 命中 "超长 user message" 规则。拆成 system(prompt) + user(对话) 可绕过。
已抽出 call_openrouter_split(model, system_prompt, user_content, ...) 函数。
路由器 192.168.31.1 跑 OpenWrt + Clash TUN 模式,openrouter.ai 被劫持解析到 198.18.13.4(TEST-NET-2 段)。TLS 握手 + 证书都 OK,但路由器代理对大 body 缓冲不够会断连。根本解: 路由器 Clash 加规则 openrouter.ai → DIRECT。
sonnet 直调 OpenRouter 9s 完成,同样请求经 claude -p 545s。瓶颈在 SDK / tool loop / stdin 处理,非模型本身。但 claude -p 是退化链路最后一环,慢但 100% 不走代理层。
推理模型 CoT bug: content="" 但 reasoning 有内容。call_openrouter_split 已 fallback 到 reasoning。
| # | 问题 | 根因 | 修复 |
|---|---|---|---|
| #1 | km-pipeline skill 永久丢数据 | merge.sh Step 2 [[ ! -f "$kg" ]] 跳过不存在的 {skill}_knowledge.md,changelog 里的条目被丢弃 |
判断提前到 Step 1 分组阶段,不存在自动走 tmp/newskill_{s}.txt 的 NEW_SKILL 创建路径 |
| #3 | GLOBAL_INDEX 不写回 | Step 4 prompt 要求 AI 输出"需要改的行",AI 只生成建议文字不操作文件 | prompt 改为输出完整新 GLOBAL_INDEX.md(或 NONE),shell 5 分支: 合规 md → .bak + 覆盖; NONE → 不动; 其他 → 保留 + WARN |
| #4 | scripts/*.log 被 commit | .gitignore 有规则但文件已 tracked |
git rm --cached 掉 extract.log/merge.log/last_ts.txt |
| 阶段 | 耗时 | 产出 |
|---|---|---|
| Extract (12 条知识 / 2 批) | 14m22s | changelog 9442 B |
| Merge (3 skill) | 3m20s | aliyun / cpmiao-main / hivemux |
| INDEX 更新 | 70s | GLOBAL_INDEX.md |
| Validate | 5s | 79 PASS / 7 WARN / 4 FAIL |
| git commit | <1s | 6 files, +141/-127 |
| 总计 | 18m55s | commit a81ae95 |
| 样本 | 原大小 | 过滤后 | 压缩率 | 场景 |
|---|---|---|---|---|
| session_914f3be2 | 6,588 | 4,515 | -31% | 对话型 |
| session_b3493ded | 27,491 | 18,968 | -31% | 对话型 |
| session_5baa4a1e | 48,006 | 42,039 | -12% | 纯讨论 |
| incremental.txt | 220,556 | 166,295 | -25% | 混合 |
| 模型 | 48K 大 session | 月度估算(30 轮) |
|---|---|---|
| haiku-4.5:nitro | ~$0.005 | ~$0.15 |
| deepseek-v3.2:nitro | ~$0.009 | ~$0.27 |
| claude -p sonnet | Claude Pro 包月 | 0 增量 |
| S2 opus | 包月 | 0 增量 |
cd ~/Desktop/skill-knowledge-base
bash scripts/run.sh
# 等 run.log 出现 "===== 完成 (1135s, 12 条知识) ====="
# 只跑 extract
bash scripts/extract.sh
# 只跑 merge (MERGE_MODEL=sonnet 或 opus)
MERGE_MODEL=sonnet bash scripts/merge.sh
# 只跑 validate
bash scripts/validate.sh
# 清空日志和 changelog, 把 last_ts 回退 2 小时
> changelog.md
> scripts/extract.log
python3 -c "from datetime import datetime, timedelta, timezone
ts = datetime.now(timezone.utc) - timedelta(hours=2)
print(ts.strftime('%Y-%m-%dT%H:%M:%S.000Z'))" > last_ts.txt
openrouter.ai / api.anthropic.com 加入 DIRECT,治本而非治标wx.config/sk-xxx/URL)触发 WAF 时做 placeholder 替换(仅异常路径)| commit | 时间 | 内容 |
|---|---|---|
125eb39 | 2026-04-16 13:00 | 修复一键流程 3 硬 bug(km-pipeline 丢数据 / INDEX 不写回 / log 进 git) |
a81ae95 | 2026-04-16 12:12 | 合并知识更新: aliyun, cpmiao-main, hivemux |
14ad4c5 | 2026-04-16 | diff 服务换为 klaus (pip install klaus) |
06a7862 | 2026-04-16 | 一键流程就绪 (run.sh) |
4f68065 | 2026-04-16 | 9 项 Schema 优化完成(shared_schema, validate.sh, ALIAS 映射等) |
f7be052 | 2026-04-16 | git 仓库初始化 (414 files, 64K lines) |