§N§标签系统与ctx_reduce:Magic Context如何实现缓存安全的上下文瘦身
【免费下载链接】magic-contextUnbounded context. Memory that manages itself. One session, for life. The hippocampus for coding agents, part of CortexKit.项目地址: https://gitcode.com/gh_mirrors/mag/magic-context
Magic Context 是一款专为编程智能体(Coding Agent)设计的上下文管理插件,它通过独创的§N§ 标签系统和ctx_reduce 工具,在长期会话中自动完成上下文瘦身,同时保护模型服务商的提示词缓存不被破坏,让一个会话可以连续运行数周甚至数月而无需手动压缩。
为什么上下文瘦身必须"缓存安全"?
长会话有一个绕不开的成本问题:提示词缓存。模型服务商对"重复的提示词前缀"提供缓存命中,价格远低于全价。一个跑了很久的会话,缓存前缀占了总成本的大头——任何一次不必要的前缀改动(缓存失效,bust)都会让整段前缀重新计价。
传统的"压缩"方案会让智能体停下来重读一切,既打断工作流,又直接砸掉缓存。Magic Context 的做法不同:它把瘦身操作设计成"搭便车"——只在缓存本来就要失效的那一刻,顺路把积压的清理工作一起完成,绝不单独制造一次失效。
💡 核心原则:任何删除操作,永远不能以自己的名义触发一次缓存失效。
这条规则在架构文档 ARCHITECTURE.md 中有完整阐述,标签与回收机制的细节则写在 docs/architecture/reclaim.md。
§N§标签系统:给每段内容发一个永久"门牌号"
瘦身的第一步不是删,而是编号。
Magic Context 的打标签器会为每一条消息、每一段文件内容、每一个工具调用的输出分配一个持久的标签,会话内的编号在对话中表现为§N§。比如智能体执行了一次搜索,结果前就会带上§42§这样的标记。
这套编号有几个关键特性:
- 持久:标签存在 SQLite 数据库(
context.db)的tags表中,跨轮次、跨重启不变; - 唯一:工具标签以"会话 + 调用ID + 归属消息"为复合键,即使宿主复用调用ID也不会撞号;
- 有档案:被删内容的原文完整保存在
source_contents里,随时可取回; - 状态明确:每个标签有
active(活跃)、dropped(已删)、compacted(压缩前)三种状态。
打标签逻辑位于 packages/plugin/src/hooks/magic-context/tag-messages.ts。
有了门牌号,"删除第几段内容"就不再是模糊描述,而是精确的§42§。
ctx_reduce:智能体盖章,系统统一执行
有了标签,智能体需要清理桌面时,调用ctx_reduce工具并传入标签范围即可,例如"3-5"或"1,2,9"。
这里有个精妙的设计:ctx_reduce 只"盖章",不"删除"。
- 调用后,标签只是被记入待处理队列(
pending_ops表),内容依然完整可见; - 真正的删除发生在下一次"本来就要重写前缀"的变换轮次上,由系统一次性扫完队列;
- 已删除的内容留下一个唯一的占位符
[dropped §N§],它是标签号的纯函数——不同轮次渲染出的字节完全一致,绝不会因为占位符变化而炸掉缓存。
工具本身实现在 packages/plugin/src/tools/ctx-reduce/tools.ts。它的描述甚至用了一个形象的比喻:这不是扔垃圾,而是"把桌上不再需要的文件盖上『已处理』的章"——判断标准不是"我读完了吗",而是"接下来的工作还需要它留在桌上吗?"
缓存安全的核心:单一"失效许可"
整篇文章最核心的一点:所有清理通道共享同一份"失效许可"。
每一轮变换开始时,系统会判定这一轮是否本来就要重写前缀(例如历史学家发布了新的压缩摘要、模型或系统提示词发生了变化、使用率进入强制区间)。判定为"是"的轮次,才会放行以下所有清理动作:
| 清理通道 | 触发条件 | 说明 |
|---|---|---|
| 智能体盖章删除 | ctx_reduce 队列有积压 | 搭在既有失效上执行 |
| 年龄回收 | 老的工具输出超过阈值 | 智能体不盖章也能自动瘦身 |
| 智能去重 | 可选,默认关闭 | 重复的只读结果只保留最新一份 |
| 紧急回收 | 使用率进入约 85% 强制区间 | 按工具重要度分层丢弃 |
任何一条通道都不能单独制造失效——标记只是入队,落地永远搭便车。这一条被写进了架构文档的"承重不变量"章节(ARCHITECTURE.md 中 "Load-bearing invariants" 一节),并且历史上真实事故(一次"年龄回收绕过了历史学家否决,一次阈值穿越变成两次计价的失效")直接推动了该机制的统一。
保护窗口:最新的工作集永远安全
自动回收永远不会碰对话的最新部分。protection-window.ts会计算出一个"保护窗口"(默认约为可用软限的 5%,有上下限约束),落在窗口内的标签:
- 被
ctx_reduce标记时会被接受但报告为"held"(搁置)——等更新的工作把它们挤出窗口后才生效; - 对智能体来说这很友好:误标了刚生成的输出也没有任何伤害。
此外,最近 20 次工具调用有"骨架窗口":输入较小的调用保留真实参数、只删输出;输入较大的则整体移除,保证模型不会对着残缺的参数产生幻觉。
ctx_expand:删错了?随时取回
瘦身的最后一道保险是可逆性。
被删除的内容都进"档案馆"(source_contents)。智能体只要调用ctx_expand(tag=N),就能把§N§对应的原文完整取回——包括完整的工具输入和输出;也可以用start/end按消息序号展开一段历史。工具说明见 packages/plugin/src/tools/ctx-expand/constants.ts。
也就是说:ctx_reduce 删掉的只是"桌面上的复印件",原件永远在档案柜里。这让智能体可以大胆瘦身,不必担心误删。
用户视角:它如何影响你的日常使用
- 默认开启:智能体驱动的瘦身(标签 +
ctx_reduce)在主要会话中默认启用; - 可整体关闭:关掉后,过时的工具输出会纯粹按"年龄"自动丢弃,智能体完全不参与上下文管理;
- 可观察:
/ctx-status命令会展示当前标签、待删除队列、缓存 TTL 和瘦身进度;/ctx-flush可强制立即应用所有排队操作; - 效果:长会话中缓存命中率保持在高位,按缓存计费的供应商下成本显著降低,且没有"压缩暂停"打断工作流。
小结
Magic Context 的上下文瘦身哲学可以浓缩为三句话:
- 先编号,再动手——§N§ 标签让每次删除都精确、可追溯、可回放;
- 只盖章,不抢跑——ctx_reduce 只入队,落地永远搭在既有的缓存失效上;
- 删了都能回来——原文永久归档,ctx_expand 一键取回。
这套机制让"无限长的会话"不再是口号:上下文自己管理自己,而缓存,始终活着。
【免费下载链接】magic-contextUnbounded context. Memory that manages itself. One session, for life. The hippocampus for coding agents, part of CortexKit.项目地址: https://gitcode.com/gh_mirrors/mag/magic-context
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考