PydanticAI 的多模型适配实践
PydanticAI 的多模型适配实践
学习目标
补充理解:
- PydanticAI 的 Model ABC → Provider 工厂 → ModelProfile → JsonSchemaTransformer 四层抽象
- 不同提供商对 JSON Schema 的兼容性差异如何处理
- 30+ 提供商的注册与推断机制
前置知识
- 多模型适配架构 — 通用多模型抽象
1. 四层抽象架构
PydanticAI 的多模型适配分为四层:
Model ABC (models/__init__.py) ├── request() / request_stream() — 统一请求接口 ├── prepare_request() — 合并设置、验证、schema 转换 └── prepare_messages() — 系统提示包装、工具搜索消息合成
Provider (providers/__init__.py) ├── name / base_url / client — 认证和 HTTP 客户端 ├── model_profile(model_name) — 模型能力查找 └── __aenter__/__aexit__ — HTTP 客户端生命周期
ModelProfile (profiles/) ├── supports_tools / supports_thinking / supports_json_schema_output ├── thinking_tags / default_structured_output_mode └── json_schema_transformer — 每个提供商的 schema 转换逻辑
JsonSchemaTransformer (profiles/) ├── OpenAI: strict mode → additionalProperties:false, 全 required ├── Anthropic: SDK transform_schema() └── Google: 移除 $schema、const→enum、discriminator、examples2. Provider 推断机制
infer_provider_class(provider: str) 通过一个大型 if/elif 链将提供商名称字符串映射到具体类,支持 30+ 提供商:
openai → OpenAIProvideranthropic → AnthropicProvidergoogle, google-cloud → GoogleProviderbedrock → BedrockProvidergroq → GroqProvidermistral → MistralProvider# ... 共 30+ 个Gateway Provider:providers/gateway.py 提供 gateway/{provider}:model 语法,通过 Pydantic AI 自己的网关服务路由请求。
3. JSON Schema 转换差异
不同提供商对 JSON Schema 的兼容性差异是模型适配的核心挑战:
| 提供商 | 转换规则 |
|---|---|
| OpenAI (strict) | 添加 additionalProperties: false,所有 properties 标记为 required,移除 minLength、带 lookaround 的 pattern,oneOf 替换为 anyOf |
| Anthropic | 使用 Anthropic SDK 的 transform_schema() |
移除 $schema、const(转为单值 enum)、discriminator、examples,将 format 移入 description |
每种转换逻辑由 JsonSchemaTransformer 的子类实现,在 Model.prepare_request() 中自动应用。
4. 模型 Profile 的演进
ModelProfile 使用 dataclass 定义模型能力标志:
@dataclassclass ModelProfile: supports_tools: bool = True supports_tool_return_schema: bool = False supports_json_schema_output: bool = False supports_thinking: bool = False thinking_tags: tuple[str, str] = ('<think>', '</think>') default_structured_output_mode: StructuredOutputMode = 'tool'每个提供商定义自己的 Profile 子类(如 OpenAIModelProfile、AnthropicModelProfile),添加提供商特定的能力标志(如 openai_supports_reasoning、anthropic_supports_adaptive_thinking)。
维护挑战:模型能力标志可能过期——依赖社区贡献和测试覆盖来保持最新。Profile 中的布尔标志是静态的,不反映模型 API 的运行时变化。