有些模型配置问题不是模型 ID 错了,而是请求被送进了错误的“目录频道”。
NousResearch/hermes-agent issue #9146 讲的就是这个坑。
用户配置了一个 named custom provider,明确写了:
api_mode: anthropic_messages
但 Hermes 在 /model 切换时做模型校验,却没有把这个 api_mode 传下去。结果校验 /models endpoint 时缺少 Anthropic 所需的请求头,代理返回了 OpenAI catalog。
于是 Hermes 给出非常误导的提示:
⚠ Note: `glm-5-turbo` was not found in this provider's model listing.
Similar models: `gpt-5-pro`, `gpt-5.2-pro`
看起来像 glm-5-turbo 不存在。
实际是:
你拿 Anthropic 模型去 OpenAI 菜单里找,当然找不到。
复现场景:custom provider 明明写了 anthropic_messages
issue 里的配置大概是:
custom_providers:
- name: cch_anthropic
base_url: http://localhost:23000
api_key: "${CCH_API_KEY}"
api_mode: anthropic_messages
models:
glm-5-turbo:
context_length: 202752
然后切换模型:
/model custom:cch_anthropic:glm-5-turbo
预期行为:
Hermes 应该按 Anthropic Messages 模式校验模型目录。
实际行为:
Hermes 走了 OpenAI catalog 形态,返回 gpt-5-pro / gpt-5.2-pro 一类相似模型提示。
这会让用户误以为:
glm-5-turbo写错了;- provider 没注册;
- proxy 没暴露模型;
- Anthropic-compatible endpoint 不支持
/models; - 自定义 provider 配置没生效。
但真正断点在校验管线没有携带 api_mode。
根因一:validate_requested_model() 不接收 api_mode
issue 指出第一条根因:
switch_model() 通过 resolve_runtime_provider() 已经解析到了 api_mode
例如:
api_mode = "anthropic_messages"
但它没有把这个信息传给:
validate_requested_model()
于是后续链路:
validate_requested_model() -> probe_api_models()
根本不知道当前 provider 应该按 Anthropic Messages 协议去探测。
缺少 api_mode 后,也就无法加上必要的 Anthropic header。
例如:
anthropic-version
x-api-key
根因二:named custom provider 没被识别为 custom
第二个问题更细。
旧逻辑里,validate_requested_model() 判断 custom provider 时类似:
if normalized == "custom":
但 named custom provider 的 normalized 结果可能是:
custom:cch_anthropic
它不等于:
custom
于是 named custom provider 没走 custom 专属逻辑,而是落到 generic probe path。
这会进一步放大问题:
明明是 custom provider,却被普通 provider 路径处理。
根因三:generic fallback probe 也没传 api_mode
即使前两个问题修掉,如果 generic fallback 仍然这样调用:
fetch_api_models(api_key, base_url)
而没有传入:
api_mode
那么某些路径仍然会丢协议模式。
issue 中列出的受影响链路是:
switch_model() → validate_requested_model() → probe_api_models()
↘ fetch_api_models()
关键断点包括:
switch_model()解析了api_mode但丢掉;validate_requested_model()只认custom,不认custom:*;fetch_api_models(api_key, base_url)没有api_mode;probe_api_models()本身没有api_mode参数。
官方修复:让 api_mode 贯穿校验管线
维护者评论说明,问题已由:
- PR:
#15136 - commit:
647900e81
修复。
修复重点是:
api_mode is now threaded through the validation pipeline
也就是说,validate_requested_model() 会把 api_mode 传给 probe_api_models()。
然后根据不同模式使用正确认证头:
anthropic_messages:x-api-keyanthropic-version- 其他 OpenAI-compatible 模式:
Authorization: Bearer ...
这才是正确分流。
另一个重要修复:探测失败不再硬拒绝
评论还提到一个很实用的改动:
当自定义 endpoint 的 /models 无法探测时,比如:
- Cloudflare 403;
- proxy 不实现 Models API;
- 私有代理只支持 chat/completions;
- 网络策略拦截;
Hermes 现在会:
persist model with warning
而不是直接 hard reject。
这对自定义 provider 很重要。
因为很多代理服务并不完整实现 /models,但模型调用本身可以工作。
如果 /models 失败就禁止切换,用户会被卡死在“校验门口”。
这类问题为什么高频出现在 OpenAI-compatible / Anthropic-compatible 代理里?
因为“兼容”不等于“协议完全一样”。
OpenAI-compatible 常见:
Authorization: Bearer sk-...
Anthropic Messages 常见:
x-api-key: ...
anthropic-version: 2023-06-01
请求 body、路径、模型 catalog 形态也可能不同。
当一个系统同时支持:
- OpenAI-compatible;
- Anthropic Messages;
- custom provider;
- proxy endpoint;
- named custom provider;
就必须把 api_mode 作为运行时事实贯穿到底。
只在 config 里写了 api_mode 不够。
每个校验、探测、调用、报错路径都要知道它。
用户如何排查这个坑?
如果你看到这种警告:
model not found
Similar models: gpt-5-pro, gpt-5.2-pro
但你配置的是 Anthropic-compatible provider,就要警惕:
是不是校验跑去了 OpenAI catalog?
可以按这个顺序查。
1. 确认 provider 配置
custom_providers:
- name: cch_anthropic
api_mode: anthropic_messages
2. 确认 model switch 写法
/model custom:cch_anthropic:glm-5-turbo
3. 看错误里的相似模型
如果相似模型都是 OpenAI catalog 风格,比如:
gpt-5-pro
gpt-5.2-pro
但你预期 Anthropic catalog,那就说明 catalog 可能串台。
4. 升级到包含 #15136 的版本
重点确认 api_mode 是否已经贯穿:
validate_requested_model -> probe_api_models -> fetch_api_models
和 DeepAI API 中转站的关系
DeepAI API 中转站主要提供 OpenAI-compatible API 入口。
如果你使用的是 OpenAI-compatible 模式,那么通常关注:
- base URL;
- API key;
- model name;
- Authorization header;
/v1/chat/completions或相关兼容接口。
但 #9146 的核心是 Hermes 自定义 provider 的 api_mode 没有传到模型校验管线,导致 Anthropic Messages provider 被当成 OpenAI catalog 校验。
因此不要把这个问题归咎于 DeepAI。
准确边界是:
DeepAI 负责 OpenAI-compatible API 服务;Hermes 负责把 provider 的 api_mode 正确传到校验和调用链路。
如果你用 DeepAI 作为 OpenAI-compatible 入口,通常不需要 anthropic_messages;如果你接的是 Anthropic-compatible proxy,就必须确保 Hermes 的 api_mode 在每条路径里都没有丢。
FAQ
为什么我配置了 api_mode: anthropic_messages,Hermes 还提示类似 gpt-5-pro?
因为旧版本中模型校验管线没有接收/传递 api_mode,可能按 OpenAI catalog 去探测 /models。
这是模型 ID 写错了吗?
不一定。glm-5-turbo 可能没错,错的是校验时用了错误的 provider catalog。
named custom provider 为什么容易踩坑?
因为旧逻辑只判断 normalized == "custom",而 custom:cch_anthropic 不等于 custom,所以会落到 generic probe path。
修复点是什么?
让 api_mode 贯穿 validate_requested_model()、probe_api_models()、fetch_api_models(),并根据 anthropic_messages 使用 x-api-key + anthropic-version。
DeepAI 能解决这个问题吗?
不能。这是 Hermes provider validation pipeline 的问题,不是 DeepAI API 问题。
总结
#9146 的核心教训是:
provider 的 api_mode 不是配置注释,而是必须贯穿运行时的协议事实。
如果 api_mode: anthropic_messages 在 /model 校验时丢失,Hermes 就可能拿 Anthropic 模型去 OpenAI catalog 里找,最后给出一堆误导性的相似模型。
对 Agent 框架来说,模型切换不是简单字符串拼接。只要支持 custom provider,就必须把协议模式、认证头、catalog 探测和 fallback 行为作为一条完整链路来设计。