上下文引擎与压缩机制教程

advanced
## 什么是上下文引擎 上下文引擎是 OpenClaw 的核心组件之一,它负责**构建发送给 AI 模型的完整提示词**。每次你发送一条消息,上下文引擎会把以下内容组装成一个完整的 prompt: ``` ┌─────────────────────────────┐ │ SOUL.md(人设) │ │ IDENTITY.md(身份) │ │ USER.md(用户资料) │ │ AGENTS.md(操作说明) │ │ TOOLS.md(工具说明) │ │ 已安装的 Skills │ │ MEMORY.md(长期记忆) │ │ ───────────────────────── │ │ 对话历史(压缩摘要 + 近期消息)│ │ ───────────────────────── │ │ 你的新消息 │ └─────────────────────────────┘ ``` 上下文引擎的核心任务是:在有限的 Token 窗口内,尽可能多地保留有用信息。 ## 上下文窗口管理 ### Token 限制 每个 AI 模型都有上下文窗口大小限制(以 Token 计): | 模型 | 上下文窗口 | 大约字数(中文) | |------|-----------|----------------| | GPT-4o | 128K tokens | ~6 万字 | | Claude 3.5 Sonnet | 200K tokens | ~10 万字 | | DeepSeek V3 | 64K tokens | ~3 万字 | | Ollama 本地模型 | 通常 4K-32K | ~2千-1.5万字 | 上下文引擎会自动根据模型的窗口大小来管理内容: 1. **系统提示词**(SOUL.md、AGENTS.md 等)占用固定空间 2. **对话历史**占用动态空间,随对话增长 3. **新消息 + 工具调用结果**需要预留空间 当对话历史接近窗口上限时,上下文引擎会触发**压缩**。 ### Token 预算分配 上下文引擎大致按以下比例分配 Token 预算: ``` 系统提示词(引导文件 + Skills):约 20-30% 对话历史:约 50-60% 预留空间(新消息 + 回复):约 15-20% ``` ## 对话压缩(Compaction) ### 什么是压缩 当对话历史占用的 Token 接近上限时,上下文引擎会自动触发**压缩(compaction)**。压缩的过程是: 1. 取出较早的对话消息 2. 让 AI 模型生成一段**摘要** 3. 用摘要替换原始消息 4. 释放 Token 空间给新对话 ``` 压缩前: [消息1] [消息2] [消息3] ... [消息50] [消息51] [新消息] ↑ Token 快满了! 压缩后: [摘要:消息1-40的总结] [消息41] ... [消息51] [新消息] ↑ 空间充足 ``` ### 压缩触发条件 压缩在以下情况下自动触发: - 对话历史的 Token 数超过上下文窗口的 **70%**(默认阈值) - 可以通过配置调整阈值 ### 压缩配置 在 `openclaw.json` 中可以调整压缩行为: ```json { "compaction": { "enabled": true, "threshold": 0.7, "model": "gpt-4o-mini" } } ``` | 配置项 | 说明 | 默认值 | |--------|------|--------| | `enabled` | 是否启用自动压缩 | `true` | | `threshold` | 触发压缩的 Token 占比阈值 | `0.7` | | `model` | 用于生成摘要的模型 | 与主模型相同 | > 💡 建议用便宜的模型(如 `gpt-4o-mini` 或 `deepseek-chat`)来做压缩摘要,节省成本。 ### 压缩的影响 压缩是有损的——摘要不可能完美保留所有细节: - ✅ 保留:关键决策、重要结论、代码修改记录 - ❌ 可能丢失:具体的对话语气、中间的试错过程、细节数据 如果你发现智能体"忘记"了之前讨论的某个细节,很可能是被压缩掉了。解决方法: 1. 把重要信息写入 MEMORY.md(长期记忆) 2. 在 AGENTS.md 中记录关键规则 3. 开始新会话时重新说明关键上下文 ## 消息队列模式 上下文引擎支持三种消息队列模式,控制消息如何被处理: ### steer(引导模式) ``` 用途:在用户消息之前注入系统指令 优先级:最高 ``` steer 消息会被插入到用户消息之前,用于引导智能体的行为。典型用途: - Hooks 在消息处理前注入额外指令 - 系统级别的临时规则 ### followup(跟进模式) ``` 用途:在当前回复之后追加后续任务 优先级:中等 ``` followup 消息会在智能体完成当前回复后自动处理。典型用途: - 多步骤任务的自动串联 - 工具调用后的后续处理 ### collect(收集模式) ``` 用途:收集多条消息后批量处理 优先级:最低 ``` collect 模式会等待一段时间,收集用户的多条消息后一起处理。典型用途: - 用户连续发送多条消息时,避免逐条回复 - 群组聊天中收集多人发言后统一回复 ### 队列处理顺序 ``` 1. steer 消息(引导指令) ↓ 2. 用户消息(当前输入) ↓ 3. AI 回复 ↓ 4. followup 消息(后续任务) ↓ 5. collect 消息(批量收集) ``` ## Token 使用与成本控制 ### Token 消耗来源 每次对话的 Token 消耗包括: | 来源 | 说明 | 大约占比 | |------|------|---------| | 系统提示词 | SOUL.md + AGENTS.md + Skills 等 | 20-30% | | 对话历史 | 之前的消息和回复 | 40-50% | | 当前消息 | 你发送的新消息 | 5-10% | | AI 回复 | 模型生成的回复 | 15-25% | | 工具调用 | 工具的输入和输出 | 变化大 | ### 每个 Skill 的 Token 开销 每安装一个 Skill,系统提示词会增加约 **24+ Token**。如果你安装了 20 个 Skill,仅 Skill 描述就占用约 500 Token。 建议:只安装真正需要的 Skill,定期清理不用的。 ### 成本优化建议 1. **选择合适的模型**:日常对话用便宜模型(DeepSeek),复杂任务用强模型(GPT-4o) 2. **控制上下文长度**:及时开始新会话(`/new`),避免单个会话过长 3. **启用压缩**:确保 compaction 开启,用便宜模型做摘要 4. **精简 Skills**:卸载不常用的 Skill,减少系统提示词开销 5. **使用本地模型**:Ollama 运行本地模型,零 API 成本 ## 压缩与 Memory 的关系 压缩和 Memory 是两个不同的机制,但它们互相配合: | 对比 | 压缩(Compaction) | 记忆(Memory) | |------|-------------------|---------------| | 作用范围 | 单个会话内 | 跨会话持久化 | | 触发方式 | 自动(Token 超限) | 智能体主动写入 | | 存储位置 | 会话文件内 | MEMORY.md 文件 | | 信息类型 | 对话摘要 | 关键事实和偏好 | | 可恢复性 | 不可恢复原始消息 | 可手动编辑 | ### 最佳实践 - **短期信息**靠压缩:当前任务的上下文,压缩后保留摘要即可 - **长期信息**靠 Memory:用户偏好、项目规则、重要决策,应该写入 MEMORY.md - **关键规则**靠 SOUL.md/AGENTS.md:不会被压缩,每次会话都加载 ### 信息持久化策略 ``` 重要程度:低 → 高 ┌──────────┬──────────┬──────────┬──────────┐ │ 对话消息 │ 压缩摘要 │ MEMORY.md│ SOUL.md │ │ 会话结束 │ 会话内 │ 跨会话 │ 永久 │ │ 即丢失 │ 有损保留 │ 持久保存 │ 每次加载 │ └──────────┴──────────┴──────────┴──────────┘ ``` ## 调试上下文 如果你想了解当前上下文的状态,可以: ```bash # 查看当前会话的 Token 使用情况 openclaw status # 查看记忆系统状态 openclaw memory status ``` 在聊天中也可以直接问智能体: ``` 你现在的上下文还记得多少内容? ``` 智能体会告诉你它当前能"看到"的信息范围。 ## 小结 上下文引擎是 OpenClaw 的"大脑调度中心": - 它负责组装发送给模型的完整提示词 - 通过压缩机制自动管理 Token 窗口 - 消息队列模式控制消息的处理顺序 - 合理配置可以显著降低 API 成本 理解上下文引擎的工作原理,能帮助你更好地优化智能体的表现和成本。 #上下文引擎 #对话压缩 #Token管理 #消息队列 #龙虾技能库