OpenClaw 更新后突然不回复了?一个被忽略的 max_tokens 把整个上下文窗口吃光了
前几天我的 OpenClaw 一直跑得好好的,结果某次更新之后,agent 突然就不回复了,每次调用都直接报错。折腾了一下午,最后发现是一个挺隐蔽的配置问题——新版本会把模型的整个上下文窗口当成输出预算,留给输入的空间几乎为零。这篇文章把完整的排查过程记录下来,遇到同样问题的朋友可以直接照着修。
一、现象:报错信息长什么样
日志里反复刷这样一段错误:
Context overflow: prompt too large for the model. 400 This endpoint's maximum context length is 262144 tokens. However, you requested about 277736 tokens (7651 of text input, 7941 of tool input, 262144 in the output).
注意这三个数字,它们是破案的全部线索:
-
文本输入:7651 -
工具输入:7941 -
输出预算:262144 ← 问题就在这
输入加起来才一万五千 token,根本不多。但 262144 in the output 意味着请求把模型整个上下文窗口(262144)都预留给了输出,于是输入再小也会溢出。
二、走过的弯路
最开始我以为是会话太长,于是:
-
用 /new开新会话 —— 没用 -
用 /reset重置 —— 还是报同样的错 -
把 OpenClaw 更新到更新的版本 —— 依旧失败
关键判断点在这里:新会话已经把输入清空了,但报错里输出依然是 262144。 这说明问题和会话长短完全无关——输出预算是被写死成满窗口的,开多少次新会话都没用。
三、定位根因
这其实是 OpenClaw 某次更新引入的回归(我这边是 5 月 21 日还正常,更新到 2026.5.22 之后开始出问题)。它在调用模型时,把 max_tokens 直接设成了模型完整的 contextWindow,没有减去已经用掉的输入 token。正确的算法本应是:
max_tokens = 模型上下文窗口 − 已用输入 token
但出问题的版本没做这个减法,于是输出预算永远等于满窗口。
另一个容易踩的坑: 我一开始改的是 settings.yaml,改了好几遍都没生效。后来用下面这条命令才发现,真正被加载的配置文件根本不是它:
openclaw config validate
Config valid: ~\.openclaw\openclaw.json
实际生效的是 openclaw.json。打开它,看到 models 这一段每个模型都是空对象:
"models": { "openrouter/openai/gpt-oss-120b:free": {}, "openrouter/qwen/qwen3-next-80b-a3b-instruct:free": {}, "openrouter/nvidia/nemotron-3-super-120b-a12b:free": {} }
空对象 {} 意味着没给任何模型设输出上限,于是全部回落到满窗口。而且因为配了 fallback 链,主模型失败后会一路降级到最后一个,所以每个模型都得修,否则换一个还是炸。
四、踩坑:字段名不对
第一反应是给每个模型加 maxTokens,结果 reload 直接报错——这个字段在模型这一层根本不被 schema 识别:
config reload skipped (invalid config): Unrecognized key: "maxTokens"
关键点来了:这个版本的模型级配置走的是 params 透传,也就是把参数原样传给底层 API。所以输出上限要写成 API 真正认识的参数名 max_tokens,并且塞进 params 里。
五、最终解决方案
把 openclaw.json 里的 models 段改成下面这样,给每个模型用 params.max_tokens 显式锁死输出上限:
"models": { "openrouter/openai/gpt-oss-120b:free": { "params": { "max_tokens": 8192 } }, "openrouter/qwen/qwen3-next-80b-a3b-instruct:free": { "params": { "max_tokens": 8192 } }, "openrouter/nvidia/nemotron-3-super-120b-a12b:free": { "params": { "max_tokens": 8192 } } }
也可以用命令行逐个设置(注意带点号的 key 要加引号):
openclaw config set models."openrouter/nvidia/nemotron-3-super-120b-a12b:free".params.max_tokens 8192
改完执行三步收尾:
openclaw config validate
确认配置合法; -
确认 8192是纯数字而不是字符串"8192"(有版本会把它误存成字符串,触发 expected number 校验失败); - 重启 OpenClaw 网关进程
——注意是重启进程,不是在聊天里 /new。改配置文件后只有重启网关才会重新加载。
8192 这个值给输出留得很充裕,同时把 25 万以上的空间留给输入,绰绰有余。如果你确实需要更长的输出,调到 16384 或 32768 都安全,只要别接近 262144 就不会再触发这个 bug。
六、三个避坑要点
1. 认准真正生效的配置文件。 用 openclaw config validate 确认路径,别在没被加载的 settings.yaml 上白费功夫,实际读的是 openclaw.json。
2. 字段名要用 API 认的那个。 模型层不认 maxTokens,要走 params.max_tokens 透传。
3. fallback 链上的模型都要设。 否则主模型失败后降级到下一个,照样溢出。
显式锁死 max_tokens 的好处是,它绕过了那段有问题的自动计算逻辑,以后即使再更新版本也能一直保护你,不用每次重新折腾。如果哪天更新后又冒出 context overflow,先跑一遍 validate 看看那个数值有没有被改回字符串就行。
—— 全文完 ——
夜雨聆风