ARTICLE · INTELLIGENCE

战地情报 · 详情页

来自尧图项目组的一线实战观察与深度解析

为什么Claude请求总被拒?HaloWebUI兼容AnyRouter中转站的原理与修复方案

为什么Claude请求总被拒?HaloWebUI兼容AnyRouter中转站的原理与修复方案

【免费下载链接】HaloWebUI

基于官方OpenWebUI,汉化界面提高中文使用体验,增加了模型计费和用量统计

项目地址:https://gitcode.com/gh_mirrors/ha/HaloWebUI
点击查看免费下载

使用 HaloWebUI(基于 Open WebUI 深度定制的自托管 AI 平台)接入 AnyRouter 中转站时,不少用户会遇到 Claude 请求被拒绝的问题:密钥、请求头都正确,claude-opus-4-6却始终返回invalid claude code request。HaloWebUI 针对这一场景做了自动兼容处理,本文将讲清原理与修复方案。

1. 症状:Claude 请求被拒长什么样

在 HaloWebUI 中配置了 AnyRouter 作为 Anthropic 代理地址后,向claude-opus-4-6发起对话,后端调用POST /v1/messages时会收到如下报错:

invalid claude code request

注意两个容易误判的点:

  • API Key 有效、x-api-key等请求头正常,依然会被拒;
  • 换用普通 OpenAI 兼容格式转换后的 payload 发送,同样被拒。

这说明问题不在密钥,而在请求体的"形状"不符合中转站的校验规则。

2. 原理:为什么 AnyRouter 会拒绝普通请求

2.1 中转站用 Claude Code 规则校验高级模型

观察发现:AnyRouter 对claude-opus-4-6这类高级模型,会按照Claude Code(CC)CLI 请求的格式规则做请求体校验。也就是说,它要求你的请求"看起来"像一个真正的 Claude Code 客户端发出来的,而不是普通的第三方 OpenAI 兼容转换请求。

普通的 WebUI 请求缺少 CC 特征(特定请求头、system 签名、user_id 格式等),就会被中转站直接判定为invalid claude code request并拒绝。

2.2 HaloWebUI 的判断逻辑

兼容逻辑位于后端路由 anthropic.py,核心是两个判断函数:

  • 是否 AnyRouter 地址:_is_anyrouter_url解析 base URL 的 host,只要 host 中包含anyrouter就命中(见 anthropic.py#L689-L695);
  • 是否需要 CC 格式:_needs_cc_format在命中 AnyRouter 的前提下,只要模型名包含opus或sonnet就启用 CC 请求格式(见 anthropic.py#L704-L709)。

也就是说,claude-haiku-4-5等轻量模型走普通通道,claude-opus-4-6、claude-sonnet-4-6等高级模型自动切换到 CC 兼容通道。

2.3 自动改写:请求会被加上哪些 CC 特征

命中条件后,_apply_cc_format会在转发前自动对请求做归一化(见 anthropic.py#L715-L768):

项目处理内容
识别请求头注入x-app: cli和 CC 风格的User-Agent(claude-cli/...)
system 签名system[0]强制设为 CC agent 提示词You are a Claude agent, built on Anthropic's Claude Agent SDK.,原有 system 内容整体后移保留
user_id 格式改写为 CC 格式的user_<sha256>_account__session_<uuid>,accountUuid 保持为空(伪造的账号 UUID 会被 AnyRouter 拒绝)
thinking 模式统一为adaptive(CC 客户端的行为,而不是带 budget 的enabled)
max_tokens未设置时补 CC 默认值 32000
URL 参数追加?beta=true

这套逻辑在流式与非流式两条请求链路中都会生效,并对工具名做了 CC 工具集映射(_apply_cc_tool_names),保证工具调用场景也能通过校验。

3. 修复方案:全自动兼容,无需手动配置

对用户来说,修复是零配置的——只要 base URL 指向 AnyRouter,系统就自动完成上述归一化,不需要手动开启任何 "Claude Code 指纹" 之类的开关。

另外还有一个常见坑:模型 ID不会被改写。早期思路是把claude-opus-4-6重写成带日期的完整别名(如claude-opus-4-6-20250918),但 HaloWebUI 默认保留用户配置的原始模型 ID(_resolve_proxy_model_alias,见 anthropic.py#L910-L919),因为很多中转站只暴露短别名或自己的自定义后缀,盲目改写反而会报"模型不存在"。

4. 如何验证修复是否生效

  • 单元测试:项目内置了针对该场景的测试,覆盖 AnyRouter 识别、模型判断与 CC 格式改写,见 test_anthropic_proxy_compat.py;
  • 排查文档:完整的问题记录(症状、根因、修复细节与维护提示)写在 TROUBLESHOOTING.md 的 "Anthropic Proxy: Anyrouter + claude-opus-4-6" 一节,建议排障时优先查阅;
  • 日志确认:命中兼容逻辑后,后端会输出[ANTHROPIC CC] Applied CC format: model=...日志,说明请求已按 CC 格式转发。

💡 维护提示:如果你后续要重构 Anthropic payload 转换逻辑,请务必保留这段 AnyRouter 专用归一化,否则claude-opus-4-6的invalid claude code request问题会再次出现。

5. 小结

  • 问题本质:AnyRouter 对高级模型按 Claude Code 请求规则做校验,普通 WebUI 请求因缺少 CC 特征被拒;
  • HaloWebUI 方案:自动识别 AnyRouter 地址 + 高级模型,注入 CC 请求头、system 签名、user_id 格式等特征,并保留原始模型 ID;
  • 用户体验:无需任何手动开关,配置好代理地址即可直接对话;
  • 延伸阅读:平台整体架构与部署方式可参考 README.md,Claude 连接的前端配置入口见 Connections.svelte。

【免费下载链接】HaloWebUI

基于官方OpenWebUI,汉化界面提高中文使用体验,增加了模型计费和用量统计

项目地址:https://gitcode.com/gh_mirrors/ha/HaloWebUI
点击查看免费下载

相关推荐

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

RELATED READING

延伸阅读

更多一线实战笔记与深度复盘,助您持续精进