龙虾-OpenClaw一文详细了解-手搓OpenClaw-7 记忆系统II
·

0. 为什么要手搓 OpenClaw
OpenClaw 很强,但完整工程体量也很大。对于大多数开发者来说,直接阅读全量代码会有三个痛点:
- 模块多:Gateway、Agent、Tools、Sessions、Channels 互相耦合
- 路径长:一条消息从输入到回复,跨越多个子系统
- 调试难:没有自己的“最小版本”,很难定位问题
所以这个系列采用一个更实用的学习路径:
先做最小闭环,再逐步补齐能力。
代码地址: 代码下载
1. 目标
用 Python 从 0 到 1 复现 OpenClaw 的核心能力:
- Agent Loop(工具调用 + 多轮推理)
- Session 与并发隔离
- 记忆系统(短期 + 长期)
- Skills 系统(分层加载)
- Web/Telegram 等渠道接入
第一篇的阶段目标是:
- 跑起 FastAPI 服务
- 打通一个最小
/v1/chat对话接口 - 具备会话隔离与并发控制(每会话锁 + 全局信号量)
2. 目标架构
3. 本篇目标
在第 6 篇“能写能存”的基础上,完成“能找能用”:
- 记忆可按 query 召回(
recall) - 记忆可在会话启动时自动注入(
boot_context) - 对压缩摘要做长期归档,避免历史断层
4. 为什么要单独做记忆
只解决“写入”不解决“召回”,长期记忆就是冷数据仓库。
真正有价值的是让 Agent 在正确时机拿到正确记忆,并且不把上下文撑爆。
5. 关键实现一:召回接口
文件:openclaw_py/app/memory/manager.py
def recall(self, query: str, top_k: int | None = None) -> str:
all_entries = self.store.list_all()
if normalized_query in {"", "*", "all", "everything"}:
return "\n".join(f"- {k}: {v}" for k, v in all_entries.items())
query_terms = [t for t in re.split(r"\s+", normalized_query) if t]
for key, value in all_entries.items():
haystack = f"{key} {value}".lower()
score = sum(1 for term in query_terms if term in haystack)
当前是轻量关键词检索,优点是简单稳定、零外部依赖。
缺点是语义召回能力有限,这正是第 8 篇 RAG 的升级点。
6. 关键实现二:会话启动自动注入
文件:openclaw_py/app/core/agent.py
memory_snapshot = self.memory.boot_context(
max_chars=settings.long_term_memory_bootstrap_chars,
)
if memory_snapshot:
self.history.append({"role": "system", "content": memory_snapshot})
这一步让 Agent 在每个 session 起始就具备“基本人设与长期偏好”。
同时通过字符预算限制,避免注入过长。
7. 关键实现三:压缩摘要归档到长期记忆日志
文件:openclaw_py/app/core/agent.py
summary = self._compact_messages(head)
if not summary.strip():
return
self.memory.store.append_compaction_summary(summary)
压缩不是“删除历史”,而是“把历史迁移到更便宜的层”。
这样即便主上下文被压缩,排查和追溯仍有 daily log 可用。
8. 与 OpenClaw 的对齐点
MEMORY.md作为默认长期记忆入口文件- 记忆文件纳入 bootstrap 体系(与
AGENTS.md同类) - 通过“主记忆 + 记忆目录日志”分层管理,控制上下文体积
源码参考(OpenClaw):
repos/openclaw/src/hooks/bundled/bootstrap-extra-files/HOOK.md
Only recognized bootstrap basenames are loaded
(`AGENTS.md`, ..., `MEMORY.md`, `memory.md`).
9. 下一篇衔接
第 8 篇把当前关键词召回升级为 RAG:
- BM25 召回
- 向量召回
- 融合重排(RRF / rerank)
- 引用片段可解释输出
10. 支持一下
如果这篇对你有帮助,欢迎点赞、收藏、关注。
有余力的话欢迎打赏支持,我会抽时间多多写博客。
更多推荐


所有评论(0)