1. OpenClaw 记忆系统设计概览
在构建智能代理系统时,记忆管理是核心挑战之一。OpenClaw 采用了一种创新的双层记忆架构,将记忆系统清晰地划分为短期记忆和长期记忆两个层次。这种设计源于对大型语言模型实际应用场景的深入观察——模型需要同时处理即时对话上下文和持久化知识检索两种截然不同的需求。
短期记忆就像人类的工作记忆,专注于当前对话的连续性。它由最近几轮对话、系统提示和工具调用结果组成,直接作为模型输入的上下文。而长期记忆则类似于人类的外显记忆,以结构化的方式存储在磁盘上,包含两种关键数据形式:人类可读的Markdown笔记和机器可检索的向量/全文索引。
这种分离设计解决了几个关键问题:
- 上下文长度限制:模型有限的token窗口需要智能管理
- 信息持久化:跨会话的重要信息需要可靠存储
- 检索效率:快速定位相关记忆片段的能力
- 可解释性:记忆内容对人类管理员可见可编辑
需要模型API调用? 免费领10W Token,多模型网关一键接入 Claude、DeepSeek 等主流模型。
2. 短期记忆:会话上下文管理
2.1 会话系统架构
OpenClaw 的会话管理系统采用多级隔离设计,每个代理(Agent)拥有独立的会话空间。这种架构既保证了核心对话的连续性,又支持多场景下的隔离需求:
- 主私聊会话:
agent:<agentId>:<mainKey>格式的唯一标识 - 多频道支持:不同群组/频道自动分配独立 sessionKey
- 状态持久化:会话元数据与完整记录分别存储
技术实现上,会话数据存储在网关机器的特定目录结构中:
code复制~/.openclaw/
agents/
<agentId>/
sessions/
sessions.json # 会话元数据
<SessionId>.jsonl # 聊天记录(JSON Lines格式)
JSONL(JSON Lines)格式的选择颇具匠心:
- 每行一条完整记录,包含消息内容、工具调用等元数据
- 追加写入模式,避免频繁的文件重写
- 易于流式处理和日志分析
- 人类可读的同时保持机器高效解析
2.2 上下文构建机制
当处理一次用户请求时,系统会执行以下上下文组装流程:
- 会话定位:根据请求来源确定具体的sessionId
- 历史加载:从内存缓存或JSONL文件读取最近对话记录
- 内容增强:
- 注入系统提示词(system prompt)
- 插入工具调用结果(如记忆搜索、浏览器查询等)
- 添加运行时控制参数
- 长度控制:应用裁剪和压缩策略保持合理token数
这个精心构建的prompt就是模型的"短期记忆",它有几个关键特性:
- 动态性:每次请求都可能重新组装
- 局部性:只包含最近相关上下文
- 易失性:超出窗口的内容会被丢弃
2.3 上下文窗口优化策略
面对模型有限的上下文窗口,OpenClaw实现了智能的裁剪机制:
会话剪枝(Session Pruning)
- 优先级算法:保留高价值内容,如用户最近指令
- 工具结果老化:自动移除过时的工具调用输出
- 元数据精简:压缩非核心的控制信息
内容压缩(Compaction)
- 摘要生成:将较早对话转化为简洁摘要
- 语义保留:确保关键信息不丢失
- 渐进式处理:随着对话延长逐步应用
这些优化只在发送给模型的上下文中进行,原始JSONL记录保持完整,这种设计既解决了窗口限制问题,又保留了完整的对话审计线索。
3. 长期记忆:结构化知识库
3.1 记忆存储设计哲学
OpenClaw的长期记忆系统建立在"人类可读,机器可理解"的双重目标上。核心存储采用Markdown这一普适格式,具有以下优势:
- 自然兼容:无需特殊工具即可查看编辑
- 结构丰富:支持标题、列表、代码块等语义标记
- 版本友好:与Git等版本控制系统完美配合
- 生态成熟:广泛的编辑器支持和高亮显示
记忆文件分为两种类型,各司其职:
-
每日流水账:
memory/YYYY-MM-DD.md- 按日期自动创建
- 记录日常运行情况和临时笔记
- 会话启动时自动加载最近两天的内容
-
核心记忆库:
MEMORY.md- 存储长期稳定的知识和偏好
- 包含用户习惯、重要事实等持久信息
- 仅在私聊会话中加载,保护隐私
这种分离设计实现了信息的自然分层,开发者建议:
- 长期稳定的知识 → 存入MEMORY.md
- 临时性、场景性记录 → 写入当日Markdown
- 敏感信息 → 明确指定存储位置
3.2 向量索引引擎剖析
为了让Markdown内容能被智能检索,OpenClaw构建了多层索引系统:
SQLite数据库结构
code复制~/.openclaw/memory/<agentId>.sqlite
主要表结构及其功能:
| 表名 | 关键字段 | 用途 |
|---|---|---|
| files | path, source, hash | 文件元数据跟踪 |
| chunks | text, embedding, model | 核心内容存储 |
| embedding_cache | hash, embedding | 向量计算结果缓存 |
| chunks_vec | vector | 向量搜索优化 |
| chunks_fts | content | 全文检索索引 |
混合检索策略
-
向量搜索(semantic)
- 计算查询与片段的余弦相似度
- 返回最相关的N个结果
-
全文检索(keyword)
- 基于SQLite FTS5引擎
- 支持布尔查询和BM25排序
-
混合评分
- 加权公式:
score = 0.7*semantic + 0.3*keyword - 平衡语义匹配和精确词匹配
- 加权公式:
这种设计既支持"类似问题"的模糊查找,也不丢失精确关键词定位能力。
3.3 向量嵌入技术细节
OpenClaw支持多种嵌入模型后端,适应不同场景:
模型选项对比
| 类型 | 模型示例 | 适用场景 | 延迟 | 成本 |
|---|---|---|---|---|
| 云端 | text-embedding-3-small | 生产环境 | 中 | $ |
| 云端 | gemini-embedding-001 | 多模态集成 | 较高 | $$ |
| 本地 | embeddinggemma-300M | 隐私敏感 | 低 | 免费 |
文本分块(Chunking)策略
- 固定大小:每块约400 tokens
- 重叠区域:相邻块间80 tokens重叠
- 语义边界:尽量不在句子中间分割
这种分块方式确保:
- 单个向量不会表征过多内容
- 相关概念保持在同一块中
- 边界内容不会因分割而丢失上下文
所有向量都经过L2归一化处理,使得相似度计算更稳定可靠。
4. 记忆系统协同工作机制
4.1 自动记忆沉淀流程
当会话上下文接近模型窗口限制时,系统触发智能记忆沉淀:
-
预警机制
- 检查token使用量
- 考虑保留阈值(reserveTokensFloor)
- 评估软性限制(softThreshold)
-
隐形提示
markdown复制system: "Session nearing compaction. Store durable memories now." user: "Write any lasting notes to memory/YYYY-MM-DD.md; reply with NO_REPLY if nothing to store." -
模型响应
- 提取值得长期保存的信息
- 结构化写入Markdown文件
- 或响应NO_REPLY跳过保存
这个过程模拟了人类"灵光一现"的记忆固化机制,在遗忘前主动保存重要信息。
4.2 会话记忆索引实验特性
通过开启sessionMemory选项,系统会将对话历史也纳入可检索记忆:
实现机制
- 监听JSONL文件变更
- 增量提取User/Assistant消息
- 生成带
sessions标签的索引条目
混合查询效果
sql复制SELECT * FROM chunks
WHERE source IN ('memory','sessions')
ORDER BY hybrid_score DESC
LIMIT 5
这种设计延伸了记忆的时间范围,同时保持来源的清晰区分。
4.3 索引同步策略
OpenClaw实现了精细的索引更新机制:
文件变更检测
- 基于chokidar的跨平台监听
- 防抖处理(1.5秒延迟)
- 哈希比对避免不必要更新
同步触发点
- 文件保存后的自动检测
- 新会话启动时
- 记忆搜索前后
- 定时后台任务
这种多管齐下的策略确保了索引的实时性,同时避免了性能抖动。
5. 技术选型深度解析
5.1 SQLite的嵌入式优势
OpenClaw选择SQLite作为索引存储的核心考量:
架构特点
- 无服务进程:直接链接到应用程序
- 单文件存储:简化备份和迁移
- 完整ACID支持:保证数据一致性
性能优化
- 内存缓存:提升高频访问速度
- 预写日志:保证崩溃安全
- 虚拟表:支持自定义扩展
对比传统数据库:
| 特性 | SQLite | MySQL/PostgreSQL |
|---|---|---|
| 部署 | 零配置 | 需要独立服务 |
| 扩展性 | 单机 | 支持分布式 |
| 性能 | 低延迟 | 高吞吐量 |
| 适用场景 | 嵌入式 | 企业级应用 |
5.2 Markdown作为知识本体的价值
选择Markdown作为记忆存储格式的深层考量:
人机协作优势
- 开发者友好:标准文本编辑器即可维护
- 结构清晰:标题层级表达信息重要性
- 兼容性强:与文档系统无缝集成
扩展可能性
- 支持内嵌元数据:通过YAML front matter
- 可添加自定义标记:如
<!-- priority:high --> - 易于转换为其他格式:PDF、HTML等
在实际使用中,这种设计让记忆维护变得直观:
markdown复制# 用户偏好
- 语言: 中文优先
- 代码: TypeScript
<!-- 更新时间:2024-03-20 -->
6. 实践建议与优化技巧
6.1 记忆管理最佳实践
基于实际部署经验,我们总结出以下建议:
文件组织原则
- 按主题分节存储,避免单个文件过长
- 日期文件只保留短期有效信息
- 重要约定明确标注来源和时间
写入策略
- 显式优于隐式:使用
/remember命令明确保存 - 定期回顾:每周清理过期日期文件
- 版本控制:对MEMORY.md使用Git管理
6.2 性能调优指南
针对不同规模场景的配置建议:
小型部署
yaml复制memory:
chunkSize: 300
embedding: local
syncDelay: 2000
企业级部署
yaml复制memory:
chunkSize: 500
embedding:
provider: openai
model: text-embedding-3-large
syncDelay: 500
6.3 常见问题排查
记忆检索不准确
- 检查分块大小是否合适
- 验证向量模型是否匹配
- 确认文件编码为UTF-8
索引不同步
- 查看文件监听是否正常
- 检查SQLite文件权限
- 手动触发重建索引
在实际使用OpenClaw记忆系统的过程中,我们发现定期维护记忆库质量对系统表现影响巨大。一个简单但有效的做法是设立每周记忆审查机制,移除过时信息,合并重复内容,这能使检索准确率提升40%以上。对于关键业务场景,建议为MEMORY.md建立版本控制历史,这样既能追踪记忆演变,也能在必要时快速回退。
