摘要
Runtime LLM Facade 已按 LLM_TIMEOUT 对单次上游 HTTP 快速失败/超时返回,但 guest 内 Codex 配置了很高的重试次数。上游持续异常时,Codex 会反复重试,整条 ac run --prompt 长时间挂起,CLI 无法在合理时间内非 0 退出,也难以给出可诊断的上游错误信息。
现象
对 provider: codex 的 agent 执行:
ac run <agent> --prompt '...'
当上游(经 Runtime LLM Facade)出现断连、读超时、HTTP 503、畸形响应等时:
- Facade 单次调用能按
LLM_TIMEOUT 较快返回错误;
- 整次 CLI / run 仍会长时间挂起;
- 用户侧更像“卡住”,而不是快速失败并看到清晰的上游错误。
对照:上游返回 HTTP 429 时,Codex 会较快放弃重试,CLI 能较快非 0 退出。
预期行为
LLM 上游持续不可用或明确失败时:
- 整条
ac run --prompt 应在有界时间内结束(受 LLM_TIMEOUT + 有限重试预算约束);
- CLI 非 0 退出;
- 错误信息能说明是上游超时、5xx、断连或响应无法解析。
实际行为
| 上游故障 |
Facade 单次 |
整条 CLI / run |
| 断连 |
约在 LLM_TIMEOUT 内失败 |
长时间挂起 |
延迟超过 LLM_TIMEOUT |
客户端超时 |
长时间挂起 |
| 503 |
透传 503 |
长时间挂起 |
| 畸形响应 |
快速失败/透传 |
长时间挂起 |
| 429 |
透传 429 |
较快非 0 退出 |
根因
调用链:ac run --prompt → guest Codex → Runtime LLM Facade → 上游 LLM
- Facade:按
LLM_TIMEOUT 发起单次 HTTP,不重试;网络错误返回 502,非 2xx 透传。
- Codex 运行时配置(
WriteCodexRuntimeConfig)写死了较高重试:
request_max_retries = 30
stream_max_retries = 50
stream_idle_timeout_ms = 120000
因此 Facade 已经“快失败”,但 Codex 把多数上游失败当成可重试错误,在 guest 侧把延迟放大了几十倍。再加上 agent 默认超时很长、CLI 前台 run 无整体 deadline,最终表现为整次执行被重试拖死。
Daemon 对 429 与 503 都是透传;差异主要在 Codex:429 会较快停重试,503/断连/畸形响应会长时间重试。
影响
- 上游异常时 CLI 像卡死,体验差、难排查;
- 异常上游会被重试打满,放大错误流量。
建议方向
- 下调或可配置 Codex 的
request_max_retries / stream_max_retries / stream_idle_timeout_ms;
- 对明确不可恢复错误快速失败,并与 429 的失败策略对齐;
- 为 prompt run 增加合理的 run/agent 级 timeout;
- CLI
run --prompt 增加可选整体 deadline。
摘要
Runtime LLM Facade 已按
LLM_TIMEOUT对单次上游 HTTP 快速失败/超时返回,但 guest 内 Codex 配置了很高的重试次数。上游持续异常时,Codex 会反复重试,整条ac run --prompt长时间挂起,CLI 无法在合理时间内非 0 退出,也难以给出可诊断的上游错误信息。现象
对
provider: codex的 agent 执行:当上游(经 Runtime LLM Facade)出现断连、读超时、HTTP 503、畸形响应等时:
LLM_TIMEOUT较快返回错误;对照:上游返回 HTTP 429 时,Codex 会较快放弃重试,CLI 能较快非 0 退出。
预期行为
LLM 上游持续不可用或明确失败时:
ac run --prompt应在有界时间内结束(受LLM_TIMEOUT+ 有限重试预算约束);实际行为
LLM_TIMEOUT内失败LLM_TIMEOUT根因
调用链:
ac run --prompt→ guest Codex → Runtime LLM Facade → 上游 LLMLLM_TIMEOUT发起单次 HTTP,不重试;网络错误返回 502,非 2xx 透传。WriteCodexRuntimeConfig)写死了较高重试:因此 Facade 已经“快失败”,但 Codex 把多数上游失败当成可重试错误,在 guest 侧把延迟放大了几十倍。再加上 agent 默认超时很长、CLI 前台 run 无整体 deadline,最终表现为整次执行被重试拖死。
Daemon 对 429 与 503 都是透传;差异主要在 Codex:429 会较快停重试,503/断连/畸形响应会长时间重试。
影响
建议方向
request_max_retries/stream_max_retries/stream_idle_timeout_ms;run --prompt增加可选整体 deadline。