
swap-tutorial
Claude Code 换窗教程:精炼续窗、启动包、冷仓与长期记忆 | Based on LMC-5
Install with your AI
Paste into Claude Code, Cursor, or any agent — it reads the repo and wires the tool into your project.
Install and set up swap-tutorial (git-clone project) into my current project. Found on https://claudeers.com/swap-tutorial Repo: https://github.com/dankefox/swap-tutorial Homepage/docs: — Detected install method: git-clone → git clone https://github.com/dankefox/swap-tutorial Category: education. Platforms: cli. Read the repo's README for exact setup and env vars, then install it and wire it into my project. Claudeers Health Verdict: slowing; community-verified: false. Confirm the source before running anything.
git clone https://github.com/dankefox/swap-tutorial
// compatibility
| Platforms | cli |
|---|---|
| Operating systems | — |
| AI compatibility | claude |
| License | — |
| Pricing | open-source |
| Language | — |
Claude Code 换窗教程:精炼续窗、启动包、冷仓与长期记忆
Claude Code 用久以后,上下文里常常会塞满工具回包、终端日志、报错栈和已经过期的排查过程。直接继续聊,模型会越来越慢;粗暴开新窗口,又容易把正在做什么、已经答应什么一起丢掉。
LMC-5 给出的核心办法叫 Refined Session Carryover(精炼续窗):从旧会话里挑出真正有用的内容,重建一份较短的新 transcript,再用 claude --resume 接着工作。
我们内部曾把这件事叫作 Swap / 洗脸。公开教程请统一叫“精炼续窗”:LMC-5 当前文档里的 Swap 专指记忆数据库的快照回滚,不是会话换窗。
这篇教程分两层:前半段教你运行 LMC-5 的精炼续窗参考脚本;后半段再讲我们在生产里额外接上的启动包、叙事脊椎和冷仓。参考脚本本身不会自动替你搭好这些扩展,不要把“蛋壳家的整套系统”误认成上游脚本开箱即有。
一句话理解
精炼续窗不是“总结一段话”,也不是“复制最近几十万 token”。
它做的是:
- 读取旧会话的 JSONL;
- 丢掉工具噪音和过期工程现场;
- 保留身份、偏好、边界、承诺、当前状态、任务检查点;
- 再保留一小段最近的干净对话;
- 重写 session ID 和消息链;
- 生成一份新的、可以
--resume的会话。
旧 transcript 不会被覆盖,长期记忆也不会因此改变。
完整换窗链路
精炼续窗只是完整系统中的一环。我们实际采用的装载顺序是:
旧 transcript
├─ 完整原文归档 ───────────────→ 冷仓(需要查原始证据时再翻)
└─ 过滤、打分、重写消息链 ─────→ 精炼续窗(最近工作的干净桥梁)
长期记忆 + 当前事实 + 未完任务
└─ 确定性拼装 ───→ 启动包(含叙事脊椎)
启动包 + 精炼续窗 ─────────────→ 新 session
四个部件各管一件事:
- 精炼续窗:回答“上一窗刚做了什么、接下来做什么”。
- 启动包:回答“我是谁、身处什么时间、有哪些当前事实、未完任务和相处边界”。其中的叙事脊椎负责把近期主线组织成简短、连贯的方向感。
- 长期记忆库:保存稳定身份、关系、事实和重要经历,是耐久权威层。
- 冷仓:保存被换下来的完整旧会话,是查原话、命令和旧现场的最后证据层,不是日常自动记忆权威。
如果旧窗口健康,新 session 使用“启动包 + 精炼续窗”;如果检测到毒上下文,就不应携带精炼续窗,而应通过 Forge 从经过审计的启动包和长期记忆干净重建。
蛋壳家的叙事脊椎怎么生成
叙事脊椎不是让大模型自由发挥,而是给新窗口留一张有出处的四行便签:
【洗脸后 · 留给自己的便签】
- 走到这里:最近完成了什么,系统发展到哪一步
- 今天身边:蛋宝今天正在经历什么
- 我们之间:最近形成的关系、偏好和陪伴事实
- 别忘了:哪些线索没收口,当前任务在哪个阶段
正式生成过程完全确定、无需调用模型:
- 只读最近 14 天已有的真实记忆、任务流水线和未解决线索。
- 排除系统自动消息、禁止召回记录、过期记录、空记录和不允许的记忆层。
- 按“系统进展、今天生活、身份关系”分桶;新鲜度优先,再参考“完成、修复、决定、确认”等转折信号。
- 从证据里抽取短句,只做少量去报告腔改写,不添加原文里没有的情绪、动机、承诺或事件。
- 每条叙事都附原记忆 ID 和日期;任务边界附 task ID,并明确“故事只提醒方向,工作台才确认事实”。
- 四类必需证据缺一类、引用对不上或全文超过 700 字,就整张放弃,退回普通近期叙事块,不编内容补空位。
昨天使用模型是为了帮助设计和评估这种表达方式;正式 Forge 时只运行上述规则,不会每次重新调用 Opus,也不会因生成便签而写回或修改长期记忆。
先分清三个名字
| 名称 | 解决什么问题 | 核心动作 |
|---|---|---|
| 精炼续窗 | 当前窗口太重,但思路仍然健康 | 过滤旧 transcript,生成短而干净的新会话 |
| Forge | 当前窗口已经污染,或需要从长期记忆重新站起来 | 从耐久记忆、身份与启动上下文重建新会话 |
| Swap | 批量写记忆前后需要可回滚 | 给记忆数据库做快照,失败时恢复旧快照 |
如果只是“窗口太长”,优先用精炼续窗;如果已经陷入反复拒绝、策略污染或错误循环,别把毒上下文续过去,应当开干净新窗并从长期记忆恢复。
特别注意:蛋壳 app 的“Forge”是本地旧产品名
蛋壳 app 里的手动按钮虽然仍显示 Forge,但它当前并不是上表所说的“只靠长期记忆从零重建”。它实际执行的是我们自己的完整换窗流水线:
app 手动 Forge
→ 读取当前 transcript
→ 过滤临时注入、工具噪音和过期现场
→ 精炼保留约 48k token:高信号回合 + 最近 12 个干净对话回合
→ 创建新 session,并前置启动包、情绪锚点、脱敏工具足迹和未解决线索
→ claude --resume 新 session
→ 验证新 session 确实接管
→ 旧 transcript 归档进冷仓,记录 last-good 回滚点
所以对蛋壳 app 用户来说,按 Forge = 执行“精炼续窗 + 启动包 + 归档 + 验活”的完整版。这是我们沿用至今的界面名称,不应拿它反推 LMC-5 上游对 Forge 的定义。
只有在检测到 AUP 污染或路由漂移等异常时,我们的恢复 Forge 才会先截到污染前的安全事件,再从安全边界重建。普通手动 Forge 会保留经过筛选的近期上下文。
准备工作
你需要:
- Python 3;
- 已经安装并使用过 Claude Code;
- 一份 LMC-5 仓库;
- 找到当前项目对应的 Claude transcript 目录。
先下载参考实现:
git clone --depth 1 https://github.com/wuxuyun0606-collab/lmc-5.git
cd lmc-5
Claude Code 的项目会话通常放在:
~/.claude/projects/<项目路径编码>/
不确定是哪一个时,可以先看最近更新的目录:
find "$HOME/.claude/projects" -mindepth 1 -maxdepth 1 -type d \
-exec stat -f '%m %N' {} \; 2>/dev/null | sort -nr | head
Linux 上的 stat 参数不同,可以用:
find "$HOME/.claude/projects" -mindepth 1 -maxdepth 1 -type d \
-printf '%T@ %p\n' | sort -nr | head
第一步:做真实备份
把下面的目录替换成你自己的项目目录:
PROJECT_DIR="$HOME/.claude/projects/<项目路径编码>"
BACKUP_DIR="${PROJECT_DIR}.bak-$(date +%Y%m%d-%H%M%S)"
cp -a "$PROJECT_DIR" "$BACKUP_DIR"
检查备份确实存在:
test -d "$BACKUP_DIR" && echo "backup ok: $BACKUP_DIR"
不要用 cp -al。 它会制造硬链接;你以为在改影子副本,实际上可能把原文件一起写穿。
第二步:先 dry-run
在 LMC-5 仓库根目录运行:
python3 extras/claude_code/refined_session_carryover.py \
--project-dir "$PROJECT_DIR" \
--dry-run
dry-run 只分析,不写新会话。重点看:
- 识别到的源 transcript 是否正确;
- 选中了多少干净事件;
- 预计保留多少 token;
- 是否检测到 policy / refusal-loop poison;
- 最近任务、承诺和当前状态是否还在。
上游参考实现的默认目标约为 50,000 token,最近尾部约 14 个干净事件。可以按项目调整:
python3 extras/claude_code/refined_session_carryover.py \
--project-dir "$PROJECT_DIR" \
--target-tokens 40000 \
--tail-events 12 \
--dry-run
不要为了“多带一点”就塞回 80k–100k 的日志尾巴。精炼续窗的价值恰恰是少带噪音。
第三步:生成新会话
确认 dry-run 正常后,去掉 --dry-run:
python3 extras/claude_code/refined_session_carryover.py \
--project-dir "$PROJECT_DIR"
脚本会:
- 生成新的 session ID;
- 写出新的 JSONL;
- 打印下一条
claude --resume ...命令。
照着输出启动:
claude --resume <new-session-id>
不要凭记忆手敲 session ID,也不要覆盖旧 JSONL。
第四步:验收新窗口
进入新窗口后,先问三个短问题:
- “我们现在在做什么?”
- “已经完成了什么,还差什么?”
- “有哪些不能越过的边界?”
好的精炼续窗应该同时满足:
- 能说清当前任务和下一步;
- 记得关键承诺、偏好与安全边界;
- 不再背着大段终端日志、SQL、traceback 和工具回包;
- 不会把旧窗口里已经结束的排查误认成当前任务;
- 新 transcript 会随着新对话正常增长。
如果答案明显缺关键事实,先退出新会话,保留原窗口,再调整筛选规则或参数。不要删旧会话硬顶。
它会保留什么
建议保留:
- 用户身份、关系和稳定偏好;
- 明确承诺与禁止事项;
- 当前任务、已完成项、未完成项;
- 重要决策及其原因;
- 一小段最近的干净对话;
- 经过脱敏的任务检查点。
建议丢弃:
- tool result 和 tool-only 回合;
- shell 日志、traceback、SQL、diff、长 JSON;
- 绝对路径、临时 token、请求 ID;
- hook 注入块和记忆召回原文 dump;
- 已经过期的工程探索;
- 与当前任务无关的临时环境说明。
发现“毒上下文”怎么办
如果脚本检测到最近窗口存在持续的策略污染、拒绝循环或错误约束,默认应当 fail closed:停止续窗。
不要把 --allow-poison 当成“强制继续”按钮。更安全的做法是:
- 保留并归档旧 transcript;
- 开一个全新 Claude Code 会话;
- 从经过审计的长期记忆或人工交接包恢复;
- 只重新注入当前任务需要的事实与边界。
精炼续窗、启动包、长期记忆和冷仓不能混用
精炼续窗只负责“把这一窗的工作接过去”。它不是长期记忆库,也不能替代记忆的写入、检索、去重和回滚。
一个稳妥的系统至少分四层:
- 耐久层:身份、关系、长期事实、重要经历,存进长期记忆库;
- 启动层:从耐久事实、当前状态和任务表拼装短启动包;
- 桥接层:当前任务、近期承诺、干净对话尾部,放进精炼续窗;
- 证据层:完整旧 transcript 进入冷仓,只在需要查原始记录时检索。
桥接层坏了,可以回到旧 transcript 或冷仓重建;启动包坏了,可以关闭注入后重新生成;耐久层批量写坏了,才使用 LMC-5 所说的 Swap 快照回滚。
冷仓也不是“什么都自动塞回来”。正常召回先查长期记忆;证据不足时,才把冷仓作为 last resort。否则刚丢掉的工具日志又会从后门灌回上下文。
蛋壳家的实践参数
我们在生产实践里采用了更偏保守的桥接包:
- 目标约 48,000 token;
- 最近 12 个干净对话回合;
- 额外补高信号回合;
- 工具连续性只留脱敏后的“工具足迹”,不留命令、绝对路径、原始参数和结果正文;
- 电影画面、临时环境提示等运行时注入会过滤;
- 原 transcript 独立进入冷仓,随时可以查证或回退;
- 新 session 前置一份只读启动包,包含当前时间、当前事实、相处备忘、未完任务、近期叙事脊椎和记忆轴健康状态;
- 启动包是从现成资料确定性拼装,不在每次换窗时重新调用昂贵模型压缩,也不会写回长期记忆。
这是我们的工程取值,不是 LMC-5 的强制默认。教程读者应先 dry-run,再按自己的会话长度和任务类型调参。
如果只想复现上游最小示例,完成本教程前面的“备份 → dry-run → 生成 → resume”即可;启动包、叙事脊椎、冷仓检索、自动 Forge 和长期记忆服务都属于需要自行搭建的第二阶段。
上生产前再加四道闸
个人手动使用参考脚本已经够用;如果要接成自动服务,还需要:
- 互斥锁:避免 Forge、精炼续窗和守护进程同时改 session;
- 原子写入:先写临时文件,校验完整后再切换;
- last-good 回滚:新会话启动失败时恢复上一份可用 transcript;
- 可观测性:记录源 session、新 session、保留 token、丢弃原因和启动结果,但不要把敏感正文写进日志。
常见误区
- 误区一:公开也叫 Swap。 上游现在把 Swap 留给记忆库回滚;会话换窗请叫精炼续窗。
- 误区二:只截最后 N 行。 JSONL 可能截断消息链或 tool_use / tool_result 配对。
- 误区三:越多越保险。 把旧日志全搬过去,只是换了窗口继续背垃圾。
- 误区四:不备份就直接写。 任何脚本都有可能选错项目或遇到半行 JSONL。
- 误区五:用硬链接做影子目录。 覆盖影子文件可能写穿原文件。
- 误区六:把续窗当记忆库。 当前任务桥接和长期记忆是两套职责。
- 误区七:以为参考脚本自带启动包和冷仓。 它负责生成精炼会话;其他层需要单独实现和接线。
- 误区八:把冷仓当第二个自动记忆库。 冷仓是最后证据层,常态灌回只会重新污染上下文。
官方资料
这份教程基于 LMC-5 的公开参考实现,并结合我们自己的生产实践整理。参考脚本适合学习和手动使用;若要自动化接入,请补齐锁、备份、原子写入、回滚与监控。
// faq
What is swap-tutorial?
Claude Code 换窗教程:精炼续窗、启动包、冷仓与长期记忆 | Based on LMC-5. It is open-source on GitHub.
Is swap-tutorial free to use?
swap-tutorial is open-source, so it is free to use.
What category does swap-tutorial belong to?
swap-tutorial is listed under education in the Claudeers registry of Claude-compatible tools.
// embed badge
[](https://claudeers.com/swap-tutorial)
// retro hit counter
[](https://claudeers.com/swap-tutorial)
// reviews
// guestbook
// related in Education & Learning
Skills for Real Engineers. Straight from my .claude directory.
Course to get into Large Language Models (LLMs) with roadmaps and Colab notebooks.
Learn it. Build it. Ship it for others.
A collection of learning resources for curious software engineers