OpenClaw 大语言模型兼容层:一套接口驾驭 Anthropic/OpenAI/DeepSeek 等 10+ 模型

摘要:前两篇拆解了整体架构和消息通道层,本篇深入 Agent 最依赖的底层——模型兼容层。你将看到 OpenClaw 如何用一套统一的 Provider 抽象,同时接入 7 种不同的底层 API 协议,实现 OAuth/API Key 多认证体系、流式输出适配、模型降级 Fallback 和 Token 配额管理。


一、问题:LLM 世界的巴别塔

2026 年的 LLM 生态已经形成 7 种互不兼容的底层协议:

协议代表请求格式流式格式工具调用
anthropic-messagesClaude/v1/messagesSSE (message_start/content_block_delta/message_delta)tool_use 类型
openai-completionsGPT/DeepSeek/Qwen/Doubao/v1/chat/completionsSSE (choices[0].delta)tool_calls 数组
openai-responsesGPT-4o+/v1/responsesSSE (response.*.delta)function_call 类型
google-generative-aiGeminigenerateContentSSE + proto 编码functionCall 类型
github-copilotCopilot/chat/completionsSSEOpenAI 兼容
bedrock-converse-streamBedrockAWS SDK ConverseStream自定义流toolUse 对象
ollama本地模型/api/chatNDJSONOpenAI 兼容

如果不做统一抽象,每个模型接入都是一场噩梦。OpenClaw 的做法是:三层架构,把差异锁在中间层


二、三层架构:SDK → 适配层 → 配置层

驱动

封装

底层调用

SDK 层 —— 统一接口

pi-ai 库
Model / Api / StreamFn

适配层 —— 协议差异桥接

Extra Params
注入 temperature / cache / reasoning

StreamFn 包装链
cache trace → thinking blocks → toolCallId → logging

Provider 专项
Gemini turn ordering / Ollama native API

Fallback 路由
7 种 FailoverReason 自动分类

配置层 —— 声明式定义

Provider 注册
models-config.providers.ts

模型目录
id / contextWindow / cost / api

认证 Profile
auth.profiles.{id}.{mode}

Anthropic / OpenAI / Google / AWS / Ollama

核心原理① —— 层间单向依赖:配置层不知道适配层的存在,适配层不知道 SDK 细节。新增一个 Provider 只需要在配置层声明它的 baseUrlapi 协议、模型列表和成本参数,适配层自动根据 api 字段选择对应的参数注入策略。


三、Provider 抽象与模型发现

3.1 7 种 API 协议的一等公民

OpenClaw 没有走"全部伪装成 OpenAI"的路线,而是将 7 种协议都作为一等公民支持:

// 核心类型 —— 按协议类型驱动行为
export type ModelApi =
  | "openai-completions"       // GPT/DeepSeek/Qwen/Doubao/OpenRouter
  | "openai-responses"         // GPT-4o+ Responses
  | "anthropic-messages"       // Claude 原生
  | "google-generative-ai"     // Gemini 原生
  | "github-copilot"           // Copilot
  | "bedrock-converse-stream"  // Bedrock
  | "ollama";                  // 本地 Ollama(非 OpenAI 兼容端点)

3.2 模型发现:静态注册 + 动态扫描

补充

动态发现(本地模型)

Ollama: GET /api/tags

vLLM: GET /v1/models

Bedrock: AWS SDK list

首次使用时

resolveModel()
解析 model ID

是 OpenRouter?

任何 model ID 都可用

查 pi-ai ModelRegistry
→ 查用户 inline providers
→ 通用 fallback

启动时

ANTHROPIC_API_KEY

DEEPSEEK_API_KEY

OPENAI_API_KEY

未设置

resolveImplicitProviders()
遍历所有内置 Provider

检查环境变量

标记 anthropic 可用

标记 deepseek 可用

标记 openai 可用

跳过该 Provider

核心原理② —— 懒发现 + 饿加载:启动时只做廉价的"环境变量检查"(饿),昂贵的 API 调用(如 Ollama /api/tags)延迟到首次使用时。OpenRouter 是个特例——它的 model ID 是动态的,所以不做预校验。


四、认证体系:三种凭证的统一管理

OpenClaw 的认证体系用一个统一的数据结构覆盖三种凭证:

Cooldown 与试恢复

多级优先级链路

三种 AuthProfileCredential

API Key
{ type: api_key, key: string }

OAuth Token
{ type: oauth, clientId, secret, ... }

Bearer Token
{ type: token, token: string }

① 环境变量
DEEPSEEK_API_KEY → deepseek

② CLI Credential Store
macOS Keychain → 文件

③ Gateway Credentials
env-first / config-first

④ Auth Profiles
openclaw.json auth.profiles

profile cooldown
遇到 billing/rate_limit 错误时冷却

primary probe
冷却期间定时探测主模型

平台级差异举例:

  • macOS 原生:通过 security find-generic-password 读取 Keychain 中 Claude CLI 的 OAuth token
  • Codex CLI~/.codex/auth.json → macOS Keychain → GSM/LSA(Windows)
  • Qwen Portal~/.qwen/oauth_creds.json 或通过 PKCE OAuth 获取 Google 账号的 token

五、模型降级与 Fallback

这是生产环境最需要的保障能力。当主模型出问题时,系统自动切换到备选模型:

billing / auth / rate_limit

timeout / model_not_found

format / overflow

找到可用模型

全部失败

Agent 发起推理

runWithModelFallback()

① 尝试主模型
deepseek-chat

成功?

返回结果

② resolveFailoverReasonFromError()
自动分类错误类型

错误类型?

③ 标记 profile cooldown

跳过 cooldown

不 fallback
格式错误无意义重试

④ resolveFallbackCandidates()
primary → fallbacks → configured default

⑤ 逐个尝试备选模型
跳过 cooldown 中的 profile

返回最终错误

Failover 错误分类是基于 HTTP 状态码和错误文本自动完成的:

FailoverReasonHTTP Status触发条件
billing402 / 429 (quota)余额不足 / 配额用完
rate_limit429频率限制
auth401 / 403认证失败
timeout-请求超时 / 连接中断
model_not_found404模型不存在或已下线
format400请求格式错误

六、流式输出适配:五层包装链

不同 Provider 的 SSE 事件格式互不兼容。OpenClaw 通过一个五层 StreamFn 包装链统一处理:

原始 SSE 流
provider 原生格式

① Cache Trace
注入 cache 控制参数

② Thinking Blocks
剥离 reasoning 标记

③ ToolCallId 清洗
统一 tool_use → tool_result 格式

④ Payload Logging
可选:记录完整 payload

⑤ Output
标准化 Agent 事件流

Ollama 的特殊处理:不走 OpenAI 兼容端点,而是用自定义 createOllamaStreamFn() 直接调用 Ollama 原生 /api/chat API(NDJSON 格式),从源头避免了协议伪装带来的字段丢失问题。


七、Token 配额管理

OpenClaw 的 Token 统计有三层:

管控:三段防线

累积:多轮工具调用的正确加法

采集:一个 normalize 吃遍所有 Provider

normalizeUsage(raw)
统一 15+ 种字段名变体

output: inputTokens / promptTokens / input_tokens / input
→ 归一化为 NormalizedUsage

UsageAccumulator
缓存区存 lastXxx 而非累加
避免 Anthropic cache tokens 膨胀

① Context Window Guard
硬下限 16K, 告警线 32K

② Compaction
按 token 比例分片 + 自动压缩

③ Provider 用量查询
Anthropic/Gemini/Copilot 等独立 API

核心原理⑤ —— cache token 的正确统计:Anthropic 的 cache_read_tokens 和 cache_write_tokens 如果在多轮工具调用中直接累加会产生极大偏差。OpenClaw 用 lastCacheRead/lastCacheWrite 只在最后一轮保留最新值,避免同一次 API 调用的缓存 tokens 被重复计算。


八、总结

模型兼容层

三层架构

pi-ai SDK 层

适配层 包装链

配置层 声明式

7 种协议一等公民

anthropic-messages

openai-completions/responses

google-generative-ai

bedrock / ollama

多认证链路

API Key + OAuth + Token

环境变量 → Keychain → Profile

Cooldown + 定时探测

智能 Fallback

7 类 FailoverReason

自动分类错误

逐个尝试备选链

Token 管控

15+ 字段归一化

lastXxx 防膨胀

三段防线保护

OpenClaw 的模型兼容层设计哲学是:不做最低公分母——不把 Chi Naul 和 Qwen 伪装成 OpenAI,而是让它们各自以原生协议接入,只在 Agent 视角暴露出统一的抽象。这也是为什么它支持的 7 种协议中,每一种的功能完整度都基本达到 100%。


上一篇消息通道抽象层:一套接口驾驭 10+ 平台
下一篇预告《持久化存储体系:会话存储、配置备份与凭证管理的多层设计》

更多推荐