Codex context_length_exceeded 上下文超限处理
这个错误一般出现在两类场景:一是用 Codex/Codex CLI 处理一个比较大的项目,连续追问很多轮之后突然失败;二是通过 API 把代码、日志、需求文档一股脑塞进去,请求直接返回 context_length_exceeded。遇到后先不要急着改模型,优先查本次请求到底带了多少内容,尤其是隐藏的历史对话、自动附带的文件上下文和日志。
错误现象
典型报错大概长这样:
### token云桥中转 0029.org ###
{
"error": {
"message": "This model's maximum context length is exceeded.",
"type": "invalid_request_error",
"code": "context_length_exceeded"
}
}
在命令行工具里可能不会完整打印 JSON,而是显示类似:
Error: context_length_exceeded
Request exceeds the model context window
如果你是在 Codex 里让它分析整个仓库,或者把 node_modules、构建产物、长日志一起带进去了,这个错误非常常见。它不是网络问题,也不是鉴权问题,本质就是“输入内容 + 历史消息 + 预期输出”超过了模型可处理的上下文窗口。
先判断是不是上下文真的过大
排查顺序建议按下面来,不要一上来就换 Key 或重装工具。
- 看最近一次请求是否附带了大量文件内容。
- 看会话是否已经持续很多轮,历史消息被自动带上。
- 看是否把完整日志、完整 SQL dump、完整接口返回直接贴进去了。
- 看工具配置里是否开启了“自动读取整个项目”之类的能力。
- 看
max_tokens或输出长度设置是否过大,输出预算也会占上下文。
如果是 API 调用,可以先把请求体落盘看一下大小:
cat request.json | wc -c
cat request.json | jq '.messages | length'
如果某一条 content 特别长,可以快速找出来:
cat request.json | jq -r '.messages[] | [.role, (.content | tostring | length)] | @tsv'
这个命令虽然不能精确计算 token,但足够定位是哪段内容过大。中文、代码、JSON 的 token 密度不同,最终还是以实际请求结果为准。
常见原因
1. 把整个仓库都塞给 Codex
很多人会直接说“帮我分析这个项目所有问题”,工具为了完成任务可能会扫描大量文件。小项目问题不大,前端项目、Java 单体、微服务仓库很容易超限。
先看目录大小和大文件:
du -sh .
find . -type f -size +200k | sort | head -50
常见不该进入上下文的目录包括:
node_modules
dist
build
target
.idea
.git
coverage
logs
tmp
2. 会话历史太长
连续让 Codex 改需求、修 bug、解释代码,十几轮之后即使每轮都不长,累计历史也可能超限。很多工具默认会把历史消息带上,表面上你只发了一句话,实际请求体里带了前面大量内容。
3. 日志没有截断
线上日志、测试失败堆栈、CI 输出经常非常长。尤其是重复异常、依赖安装日志、构建 warning,信息量不高但占上下文很厉害。
4. 输出预算设置过大
有些 SDK 或封装会把 max_tokens 设置得很高。上下文窗口不是只算输入,也要给输出预留空间。输入已经很满时,再要求很长输出,就容易触发超限。
逐步修复
第一步:缩小任务范围
不要让 Codex 一次读完整项目,改成明确文件和目标。例如不要写:
分析这个仓库的所有问题并修复
改成:
只分析 src/user/service/UserService.java 和 src/user/controller/UserController.java,
定位登录失败时返回 500 的原因,先不要修改其它文件。
如果是 API,把无关文件内容从请求里删掉,只保留和问题相关的入口、调用链、错误日志。
第二步:增加忽略规则
如果你用的是命令行或编辑器插件,优先配置忽略目录。不同工具配置名不完全一样,但思路一致:不要让依赖、构建产物、缓存文件进入上下文。
cat > .codexignore <<'EOF'
node_modules/
dist/
build/
target/
.git/
coverage/
logs/
*.log
*.min.js
package-lock.json
pnpm-lock.yaml
EOF
如果工具不识别 .codexignore,也可以在提示词里明确限制读取范围,但配置文件更稳。
第三步:重开会话
如果已经聊了很多轮,最省事的办法是新开一个会话,把当前结论整理成短摘要,再继续。不要把旧对话全部复制过去。
当前已确认:
1. 登录接口 /api/login 返回 500。
2. 错误发生在 UserService.validatePassword。
3. 相关文件只有 UserController.java、UserService.java、PasswordUtil.java。
请基于这三个文件继续排查。
这个做法比在旧会话里继续压榨上下文稳定得多。
第四步:截断日志
日志只保留关键部分:异常头、第一段业务堆栈、触发参数、时间点附近上下文。可以用命令先裁剪:
grep -n "Exception\|ERROR\|Caused by" app.log | tail -80
如果要看异常前后几行:
grep -n -C 5 "NullPointerException" app.log | head -120
不要把几十万行日志直接贴进去。Codex 更需要的是“哪里报错、调用链是什么、输入是什么”。
第五步:调整输出长度
API 调用时,把输出 token 控制在合理范围。例如先让它只给排查结论,不要一次生成完整改造方案、测试用例和文档。
{
"model": "your-codex-model",
"messages": [
{
"role": "user",
"content": "只根据下面代码定位原因,输出不超过 800 字。"
}
],
"max_tokens": 1000
}
如果你接入的是中转服务,也要看中转层有没有额外拼接系统提示词、审计信息或历史消息。我自己排查这类问题时,会优先选能看到请求日志和错误详情的平台,比如 token云桥AI中转站 0029.org,至少方便确认到底是模型限额、请求体过大,还是客户端封装出了问题。
修复后的验证方式
修完不要只看“不报错”就结束,建议做三次验证。
1. 小上下文请求验证
curl -s -X POST "$API_BASE/v1/chat/completions" \
-H "Authorization: Bearer $API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "your-codex-model",
"messages": [
{"role": "user", "content": "只回复 ok"}
],
"max_tokens": 20
}'
这一步用于确认 Key、地址、网络都正常。
2. 相关文件请求验证
只带一两个关键文件,确认 Codex 能正常分析:
python3 - <<'PY'
from pathlib import Path
files = [
"src/user/service/UserService.java",
"src/user/controller/UserController.java"
]
for f in files:
p = Path(f)
print(f"===== {f} =====")
print(p.read_text(encoding="utf-8")[:12000])
PY
如果这里正常,说明问题大概率已经从“上下文超限”降到具体代码分析层面。
3. 长会话回归验证
连续追问两三轮,观察是否再次出现超限。如果第三轮又报错,说明工具仍在自动累积过多历史,需要进一步减少历史保留或直接分任务处理。
避免复发的习惯
- 每次只让 Codex 处理一个明确问题,不要同时要求分析、重构、写测试、写文档。
- 项目根目录维护忽略文件,排除依赖目录、构建目录和日志。
- 超过五六轮的复杂排查,及时总结后新开会话。
- 日志只贴关键片段,重复内容先用命令过滤。
- API 调用时记录请求体大小、消息数量和输出 token 设置。
- 把大文件拆成模块摘要,不要直接塞完整文件。
总结
context_length_exceeded 不是玄学错误,基本就是上下文装太多了。处理思路很固定:先确认请求里到底带了什么,再删无关文件、截断日志、重开会话、降低输出长度。Codex 做代码排查时,给它“少量关键文件 + 明确问题 + 精简日志”,通常比把整个项目扔进去效果更稳,也更不容易再次超限。
408

被折叠的 条评论
为什么被折叠?



