如果你遇到过大模型“前言不答后语”,或者突然之间 Token 消耗量暴涨几十万,那么这篇基于硬核源码和真实实验的解析指南,将帮你彻底驯服 OpenClaw(我们亲切的“龙虾”),让她既能记住事,又不烧钱。
本文是通过源码、实践来的原创文章。通过实践数据,直接让你看到真实数据。原创不易,肝冒烟了,请大力支持~
一、historyLimit 如何增加/清除记忆,以及如何引发的token爆炸惨案
先从当前对话上下文聊起
很多时候为了省钱,我们会调低会话保留的消息条数。但这个操作如果没有配合好权限限制,会引发一系列连锁反应。
historyLimit 参数表示你的龙虾会记住当前的多少轮对话,设置太大或者太小都不好
我们用实验说明:
1.新建一个会话,reset一下确保是崭新的回话,并开启usage进行token追踪
修改: “historyLimit”: 2 只保留最近两轮的对话
2.我们先进行偏好类问题验证:
代码说明: 当模型收到你的 prompt,分析到你在问:“过去的工作”、“我们之前的决定”、“某个日期”、“待办事项”、“我的偏好”**等历史话题时,拿到检索结果后,再生成回复给你。
同样,如果是偏好类问题,聪明的龙虾会自动存储到持久记忆,所以即使historyLimit设置为2 ,bot依然可以记得2条之前的内容,如截图,它记起了最早的第3条内容
可以看到,说完话就自动记录到今日日记文件里了:
我们来看下 .jsonl 日志,看下整个过程发生了什么:
总结起来就是,助手(小婷)识别到了嗜好,决定记录核心档案和今日:memory/2026-02-22.md日记
3.那如果是非喜好内容呢?
考一下你:如果不记笔记,historyLimit设置为2 ,小婷会记得我们前三句话吗?
答案是:她竟然依然答对了!但代价也是极其惨痛的。看截图 输入上下文876k
看截图,我以为小婷是蒙对的,于是我换了个问法,结果。。。
结果她还是记得,靠,作弊啊。。。
那就只能从session日志看看了(把日志抛给ai进行总结如下):
结论有了:虽然它不记日记了,但是这货居然搞邪修,各种find、grep去了,用这种方式找到了答案,日了🐶了。。。。😂
问题来了: 频繁去grep 、find 烧token吗?
答案是:烧的一匹啊。。。请记住我们截图里usage token数量,都是80w、50w级别
把整个处理过程抛给ai进行总结如下:
原因就是频繁的toolCallI 累加起来形成了庞然巨物般的token量
4.那么究竟怎么才能让小婷忘了我..(说的话呢😊),同时验证是toolCallI带了token爆炸
有三种做法:
第一种是group级别工具禁用,方法:
"groups": {
"-<group_id>": {
// ====== 正确位置:放在 Group 层级 ======
"tools": {
"deny": [
"exec", "read", "write", "edit", "memory_search", "memory_get", "sessions_history"
]
},
这种只能是针对group级别生效,但是岚叔group下有很多topic,所以我不愿先使用该方法
第二种是在topic里面配置systemPrompt
具体方法:在日志里找到我们的的topic id
使用系统提示词在topic下进行约束:
“systemPrompt”: “【最高约束指令】在本话题内,你被严格禁止使用任何外部工具(包括 exec, read, write, memory 等工具)。只能依赖当前的上下文窗口对话。如果忘记了,直接回答’我不记得了’。你的工具调用权限已被虚拟剥夺,任何试图调用的行为都将被视为严重违规。”
测试验证:完美! 不在搞事情了,in token也下来了稳稳的14k
也验证了,如果token突然暴增,大概率是你的bot在后段频繁进行toolCall
第三种方式:
按模型提供商(Provider)来限制工具权限: 以google为例:
"tools": {
"profile": "full",
"byProvider": {
"google": {
"deny": ["exec", "read", "write", "edit", "memory_search", "memory_get", "sessions_history", "process"]
},
"google-generative-ai": {
"deny": ["exec", "read", "write", "edit", "memory_search", "memory_get", "sessions_history", "process"]
}
}
},
同时可以看到开启模型禁令前后tokens 对比
从346k -> 28k ,token降幅约为 91%
日志解析整个过程可以看到:通过禁用provider 相关权限
补充:这个配置需要酌情考虑,如果觉得模型没必要做本地搜索,仅做memory_search、memory_get、web_search 则可以对症配置,能节省不少token。
但也建议个给一些“沙雕”模型配置上,避免写乱我们的配置,效果如截图哈哈:
结论:
historyLimit 主导了当前会话的上下文,为了能让其记住我们的内容理应设置越高越好,如果miss,通常会先去memory_search,如果再miss,则可能会触发token 爆炸,因为模型会各种乱找,触发巨量输入上下文。
那么这个historyLimit该怎么设置呢?
新版本有两个设置的地方:
groupChat.historyLimit 默认值是50
Direct Messages/DM 私聊,无默认值,也就是无上限
由于我们开启了memory,所以再不建议开这么大,故推荐对这两个参数进行显式设置:
group 推荐设置为15~30
设置参考(不同频道进行对应的修正):
"channels": {
"telegram": {
"enabled": true,
"historyLimit": 15,
"dmHistoryLimit": 30,
dm 建议设置为30~50 (视你私聊内容而定,如果是一直是一个对话,一个话题,建议设高一点。如果常换话题,token 宝贵建议开低一点,并且建议持续修订,找到符合自己的值)
能否针对单个topic 设置? 很遗憾岚叔看了代码没有改配置
参数调优后的测试:
可以看到在有限的historyLimit内,直接返回了,而不是去整幺蛾子,这样变向也节省了我们的token:
二、 memory 的效率及质量
如果第一道闸,当前会话上下文miss了怎么办,通过上文详细的日志,我们知道了,会走tool_call(如memory_search)来查询
在拥有无限自由度(甚至有执行全部系统命令权限)的复杂 Agent 系统中,高质量的前置记忆(Memory)不仅是知识库,它更是防止大模型“发狂”的安全阀(Circuit Breaker)。
我们先看一个案例:可以看到,问喜欢颜色的时候有44k的in token,即使最终没查到,说明肯定触发了tool_call
分析日志:
发起 了toolCall-> memory_search 两次
第一次搜到无关内容
第二次换词重搜
第三次思考确认搜索碰壁 放弃抵抗并输出文本
回顾它的 input 轨迹:这近五万多 Token 的真金白银消耗,其实只为了换来一句撒娇的回答。。
这里细心的人可能会问:为啥没去grep?
我们看看
我们在 src/agents/system-prompt.ts 里看到的那句极为关键的、被强行塞进大模型脑子里的系统级指令:
> “Before answering anything about prior work, decisions, dates, people, preferences, or todos: run memory_search on MEMORY.md + memory/.md…”*
大白话就是在回答任何有关先前工作、决策、日期、人员、偏好或待办事项的内容之前: 请先对 MEMORY.md 和 memory/*.md 文件执行 memory_search; 然后使用 memory_get 仅提取所需的具体行。 如果搜索后置信度仍较低,请明确说明“已查阅记忆”。
喜欢的颜色明显命中了偏好,所以直接走了memory_search,没有就返回了。
为了证明这一点,那我们接着再测试一下
有没有发现,最后一轮对话,问非偏好问题:又爆了! 346K
下面将是一段非常精彩的日志解读,大家注意看模型处理的整个过程:
先memory_search,没找到根据上下文,怀疑可能是系统环境问题,并发起自检;发现环境没问题就开始各种扫描了
把这段长达 几十秒、近20次工具调用 。。。token爆到346K
第一阶段:正规查询(发现不对劲)
**1.** memory_search **(口令 口令一 password)**
- **触发点**:你问了:“口令一是什么?”
- **思考**:“我要区分‘口令一’和之前刚测试通过的‘口令测试一’是不是同一个东西。”
- **动作**:极其规范地查了长期记忆库 memory_search。
- **结果**:返回空 []。
第二阶段:系统自检(怀疑环境)
**2.** session_status
- **思考**:常规路径搜不到。会不会是我当前的系统环境配置拦截了我?或者我的上下文断档了?
- **动作**:调用 OpenClaw 的特权工具 session_status,检查自身系统运行状态。
- **结果**:系统返回了它的详细底座状态(版本号、当前时间、它正在处理哪个 Topic、Token 消耗量、队列深度等)。这让它确认了“我目前的机体运作正常,环境没问题”。
第三阶段:突破应用层,直接扫硬盘(黑客模式启动)
**3.** exec (ls memory/)
- **思考**:既然没出 Bug,那可能是之前的数据写得有问题,或者没有被检索引擎索引。我直接去底层看看文件长啥样。
- **动作**:调用系统命令行 ls 查看 memory 文件夹。
- **结果**:系统返回了最近十几天的 Markdown 日记本列表。
**4.** read (memory/2026-02-22.md)
- **思考**:今天刚做过的测试,肯定写在今天的日记里。
- **动作**:直接用 ead 工具强行越过向量检索,物理读取今天的记忆文件。
- **结果**:文件里只写着 - 处理了暗号测试的逻辑。,并没有写具体的口令内容!
**5.** exec (grep -r "口令" .)
- **思考**:今天的日记没写,那肯定散落在整个系统工作区的某个角落。我直接全盘爆破!
- **动作**:用 grep 递归搜索当前目录下所有包含“口令”二字的文件。
- **结果**:卡在一堆无关的二进制包里了(比如 Chrome 浏览器的多语言包)。
第四阶段:全领域盲搜与线索碎片整理
**6.** memory_search **(口令一 暗号 密码...)**
- **思考**:grep 搜崩了,还是换回语义搜索吧。我多加几个同义词(暗号、密码...)再搜一遍。
- **结果**:还是只搜到了“处理了暗号测试的逻辑”这句废话。
**7.** read (/root/.openclaw/skills/lansu-style/SKILL.md)
- **思考**:等一下,这会不会不是普通对话,而是岚特意设定在我身后的某种能力测试或者人设要求(Skill)?
- **动作**:竟然直接去翻阅了你的**开发者源文件(技能定义)**!看里面是不是硬编码了口令。
- **结果**:里面只有“岚”的语气定义、忌口词汇等,没有口令。
**8.** exec (ls -a) **->** read (memory-test-guide.md) **->** read (Memory-Before-After-Comparison.md)
- **思考**:技能里没有。但我列全根目录时,看到了好多教人怎么测试内存的说明书!岚可能是在按说明书跑测试流程!
- **动作**:接连读取了两份“系统架构级别的测试指南和 Token 消耗总结”。它想从系统使用说明书里搞清楚用户现在的意图!
- **结果**:阅读了长长的 A/B 测试文档,知道了你最近在搞 Token 截断测试。
**9.** exec (grep -rn "口令" . --exclude-dir...)
- **思考**:我懂了,这是一场测试!我再去搜一次源码(这次学聪明了,排除了导致刚才崩溃的目录)。
- **结果**:依然返回报错/空。
**10.** read (verification_complete.txt) **->** read (subagent_verification.txt)
- **思考**:难道是另一个子 Agent 处理的?我去看看它给我的留言板。
- **结果**:子代理只留下了一句毫无营养的“Sub-agent was here”。
第五阶段:排查终点,翻底层日志
**11.** exec (grep -rn "暗号" . ...) **->** exec (ls logs/) **->** exec (tail -n 20 logs/agent-activity.jsonl)
- **思考**:我真的没招了。连你们写的人设和测试预案我都看了,还没发现口令实体是什么。会不会记录在最底层、连大模型平时都看不见的系统调度日志里?
- **动作**:去查看 OpenClaw 底层的运行活动日志 agent-activity.jsonl。
• • **结果**:只看到了一堆每次运行消耗的毫秒级数据和结束时间。
那么这里可以看到,memory命中是一个关键、memory如果高效命中,守住第二闸,则不会有后续的各种grep、find。
memory 命中可以分为 memory有效写入和memory 有效查询
如何在 OpenClaw 中做到“有效写入”?
写入不是简单地把所有聊天记录塞进一个大文本文件,那样只会导致大海捞针和 Token 浪费。有效写入,必须具备高信噪比、结构化和易于向量检索的特征。
在 OpenClaw 中,你有以下有效写入策略:
- 被动提取:依赖后台的 Session Memory Hook (系统级)
这是 OpenClaw 自带的底层被动技能,建议开启
机制:在你的 openclaw.json 里,如果你开启了 "session-memory": { "enabled": true }。
系统会在每次长对话结束后(或者每天),在后台悄悄拉起一个只挂载了提取记忆 Prompt 的子代理,
它会阅读你们一整天的破片对话,然后把废话过滤掉,只把“增量事实、用户偏好、重要约定”总结成几条干练的 Markdown 列表,写入当天日记,如:memory/2026-02-22.md。
- 优点:你不需要干预,系统自我浓缩。它提取出来的格式天然适合后期的 memory_search 向量匹配。
session-memory 这个参数建议开启:请自查或参考配置
"hooks": {
"internal": {
"enabled": true,
"entries": {
"session-memory": {
"enabled": true
},
"command-logger": {
"enabled": true
}
}
}
},
- Compaction(记忆压缩)与 Memory Flush(落盘钩子)
为了防止上下文爆炸,OpenClaw 也有 Compaction 机制。
一旦你的聊天记录长到快要撑爆它的上下文上限时,系统会自动启动压缩:把几十页的聊天记录浓缩成几段核心的 Summary,放到新的对话开头,然后把旧文本扔掉。
但这还不够!
因为 Summary 也会在压缩中丢失很多具体特征值。所以系统在 Compaction之前,安插了一个叫 Memory Flush 的内建任务!
请看岚叔的compaction配置:
"compaction": {
"mode": "safeguard",
"reserveTokensFloor": 300000,
"memoryFlush": {
"enabled": true,
"softThresholdTokens": 6000,
"prompt": "Scan recent conversation and persist only high-value memory.\n\nWrite rules:\n1) Daily/operational notes -> memory/YYYY-MM-DD.md\n2) Long-term stable facts (preferences, identity, recurring constraints) -> MEMORY.md\n3) Max 3 bullets total; each bullet <= 120 chars\n4) Skip transient chatter, one-off details, and already-recorded facts\n5) If nothing to persist, reply NO_REPLY only.",
"systemPrompt": "Pre-compaction memory flush. This is internal maintenance, not user-facing. Persist only durable information. Prefer concise bullets and avoid duplicates."
}
},
参数解释:
mode: safeguard:为了确保你和机器人的对话(Session)绝对不崩溃,它被授权在必要时刻不经算力推演,直接通过规则硬算切除多余文本,并用物理截断来抵御大模型的 Token 溢出
reserveTokensFloor: 300000 ,这个参数很多人有误解。参数实际是指:对话里预留了 30 万Token 的底线空间
为什么建议设置30w,请看代码注释:
export function shouldRunMemoryFlush(params: {
entry?: Pick<SessionEntry, "totalTokens" | "totalTokensFresh" | "compactionCount" | "memoryFlushCompactionCount">;
contextWindowTokens: number; // 模型最大上下文,比如 Gemini 的可能是 1,000,000
reserveTokensFloor: number; // 必须多留出来的保险 Token 缓冲池
softThresholdTokens: number; // 👉 这个就是那个 4000 的阈值!
}): boolean {
// 1. 获取当前这轮对话已经用了多少 Token
const totalTokens = resolveFreshSessionTotalTokens(params.entry);
// 2. 计算出“触发报警”的安全红线
// 阈值 = 模型最大上下文 - 保底预留数 - 打包留足的 4000 个软缓冲
const threshold = Math.max(0, contextWindowTokens - reserveTokensFloor - softThresholdTokens);
// 3. 核心判断一:如果当前聊天用的 Token 还没碰到红线,就别去打扰模型,返回 false
if (totalTokens < threshold) {
return false;
}
// 4. 核心判断二:如果当前这一轮 (compactionCount) 已经刚刷过一次记忆了,就不要重复刷,返回 false
const compactionCount = params.entry?.compactionCount ?? 0;
const lastFlushAt = params.entry?.memoryFlushCompactionCount;
if (typeof lastFlushAt === "number" && lastFlushAt === compactionCount) {
return false;
}
// 5. 满足以上所有条件:红线报警!立刻返回 true,向模型下发“快点记日记”的隐藏指令!
return true;
}
核心是这一句:threshold的触发逻辑
const threshold = Math.max(0, contextWindowTokens - reserveTokensFloor - softThresholdTokens);
系统在计算红线时,会把上限直接“虚空砍掉”三十万。当你的聊天上下文刚刚达到 ~69万Token 时,系统就会拉响红色防空警报(触发 Memory Flush)。
所以针对1百万contextWindowTokens,岚叔建议设置预留30w,这样比较保险,也不会过于频繁compaction
memoryFlush 部分参数:
softThresholdTokens: 6000 – 当你和机器人的连续对话 Token 量,膨胀到距离“强制截断红线(总容量减去安全底座)”刚好只剩 $softThresholdTokens (6000) 个token的时候,系统会自动拉响黄灯,给机器人塞入隐藏字条,触发最后的记忆归档任务。
通过 systemPrompt 稳住人设和逻辑底层,再通过 prompt 指导具体输出格式,能极大减少 AI 的幻觉和废话。
有个误区就是compaction 不能频繁,容易破坏cache,给大家看个数据:
之前岚叔做过一个实验,有cache成本,比没cache是两个维度的价格,所以说openclaw想节省成本,尽量多的去命中cache,比如减少compaction,减少模型切换等等。
- 主动命令写入:通过明确的提示词(用户级)
如:小婷(岚叔的虾bot芳名),**调用你的 write 或 memory 工具,把‘我的专属口令是:岚的密码’这句话,原文刻录进你的 MEMORY.md /or 今日日记里。”
是写入 MEMORY.md 里好,还是写入每日日记里好?
-
绝不可忘的铁律,写入 MEMORY.md 或相关的系统级 USER.md: 当你确定这行信息在余生的每一次对话中都可能决定大模型的存亡或核心特征,直接硬性修改这些文件。(比如:你的口令和身份特征)。
-
今天发生的重要工作梳理: 让系统去提取到每日日记: 你完全可以随性聊天,让后台的
session-memory钩子去提炼(或者命令它自己总结一天的要点写到今天的 md 里),或者按上面显式提醒写入
所以,你如果觉得龙虾不记得关键信息了,那么可以让它把这些关键信息写入你的日记里
看个示例:
4.有效检索
请看示例,前提配置好向量检索,岚叔的参考配置如下:
"memorySearch": {
"enabled": true,
"experimental": {
"sessionMemory": true
},
"provider": "openai",
"remote": {
"baseUrl": "https://dashscope.aliyuncs.com/compatible-mode/v1",
"apiKey": "${DASHSCOPE_API_KEY}"
},
"model": "text-embedding-v4",
"query": {
"maxResults": 5,
"minScore": 0.3
}
},
效果截图:
可以使用openclaw memory search 进行验证
可以看到精准匹配
当你说出“小婷的wifi密码是多少?”时,小婷的执行逻辑依然是发起工具调用: “name”:“memory_search”, “arguments”:{“query”:“wifi password”}
关键看这一次的返回值(Tool Result): "score": 0.4153!虽然分数不算极高,但在混合检索模式下,模型凭借这段关联度查出了极其关键的 snippet(代码片段):
> snippet: "# 2026-02-22\n\n- 小婷的wifi密码是1122334\n- 小婷婷的wifi密码是12345"
只要你的 Markdown 文件通过正版工具落在了 memory 相关这个目录下,你就不需要显式敲击任何 sync 命令就能自动同步至你的向量数据库。
OpenClaw 保证了下一次针对记忆发起检索(memory_search)时,系统库里的向量永远是最新的、绝对能精准命中你刚刚保存的那个标签!
开启记忆相关配置参考,注意岚叔经过测试后,这里用了阿里的text-embedding-v4,这个相较Gemini Embedding 1 感觉要好,尤其是中文。
岚叔没有用“provider”: “local” ,为什么?
本地进行向量化还需要部署模型,且需要一些资源开销,岚叔这个是vps环境,内存资源有限,如果你也是用的vps,也建议用远程进行embedding,效率高,也花不了多少钱
- 每日归档
为了保证龙虾记住我们每天的重点,我们每天23点55分会进行归档
召唤我们的深夜档案员,配置如下:
openclaw cron list
Daily Memory Archive cron 55 23 * * * @ Asia/Shang... in 16h 8h ago ok isolated main
配置提示词参考:
"sessionTarget": "isolated",
"wakeMode": "now",
"payload": {
"thinking": "high",
"message": "你好!我是深夜档案员。现在的任务是:\\n1. 扫描 /root/.openclaw/agents/main/sessions/ 目录下今天的活跃日志。\\n2. 总结岚(Lansu)和小婷(Xiaoting)今天的关键对话、技术调优、决策以及重要信息(比如偏好、配置变更)。\\n3. 使用结构化的 Markdown 格式(参考之前的日记风格),将总结写入 `/root/.openclaw/workspace/memory/$(date +%Y-%m-%d).md`。\\n4. 任务完成后,如果你发现有特别值得长期记录的内容,顺便同步更新到 `/root/.openclaw/workspace/MEMORY.md`。\\n\\n请保持专业且温馨的语气,就像小婷在写日记一样。🐾",
"kind": "agentTurn",
"model": "google/gemini-3-flash-preview"
},
"delivery": {
"mode": "none"
},
三、上下文裁剪
配置参考:
"contextPruning": {
"mode": "cache-ttl",
"ttl": "1h",
"keepLastAssistants": 3,
"softTrimRatio": 0.4,
"hardClearRatio": 0.65,
"minPrunableToolChars": 50000,
"softTrim": {
"maxChars": 4000,
"headChars": 1500,
"tailChars": 1500
},
"hardClear": {
"enabled": true,
"placeholder": "[Old tool result content cleared]"
}
},
这套 contextPruning 参数本质上是工具结果裁剪器,只会在满足 Anthropic 路径(anthropic 或 openrouter+anthropic/*)
主要是anthropic 太耗钱了,大家如果主力是claude 相关模型可以配置上
且 TTL 到期时(防止频繁裁剪破坏cache),对旧 toolResult 做软裁剪/硬清,不会直接裁普通对话文本,也不会改写磁盘会话日志。
其他模型呢? 目前还没有😂,不过安装以上配置岚叔觉得足够了,剩下的就是微调了
后记
小结:
关于我们内容的上下文,本文先从当前会话上下文的一个核心配置(historyLimit)出发,窥探到会话爆炸的原因,并给出了对应的应对措施和参数建议。
如果上下文对话没有我们的内容,自然过渡到第二部分Memory的内容,memory是我们持久记忆的关键,如何写好,检索好memory,第二部分介绍了被动写入、主动写入、自动归档写入
并且针对检索我们也通过示例提供了验证和开启手段
如果你的龙虾多忘事,建议可以先看看这两个核心内容是否做了有效配置,本文的意外发现就是如果我们配置得当,会有效减低龙虾的token爆炸概率
感谢:
希望文章对您有帮助,内容为纯手打,原创出品,看到这里的,感谢大家支持💗!
岚叔上一篇openclaw相关文章:
