如果一个 TypeScript 项目要同时接 OpenAI、Anthropic 和 Google,常见做法是自己写一层适配器,把各家 SDK 的调用参数和返回结构抹平。vercel/ai 的 README 给出的方案是把这层抽象直接放进工具包:同一个 generateText,model 参数既可以写成 'anthropic/claude-opus-4.6' 这样的字符串,也可以换成 anthropic('claude-opus-4-6') 这类 SDK 实例。

AI SDK 的自我描述是 provider-agnostic TypeScript toolkit,用于构建 AI-powered applications and agents,明确列出的 UI 框架是 Next.js、React、Svelte、Vue、Angular,runtime 提到 Node.js。安装门槛写得很具体:Node.js 22+,以及 npm 或其他包管理器,主包安装命令是 npm install ai。

两条 Provider 接入路径

README 的 Unified Provider Architecture 一节给出两条路径。默认情况下 AI SDK 使用 Vercel AI Gateway,因此只需传一个模型字符串:

const result = await generateText({
  model: 'anthropic/claude-opus-4.6',
  prompt: 'Hello!',
});

也可以绕过 Gateway 直连 provider,安装对应 SDK 包(README 举的例子是 @ai-sdk/openai、@ai-sdk/anthropic、@ai-sdk/google),再按 provider 包裹模型名:

import { anthropic } from '@ai-sdk/anthropic';

const result = await generateText({
  model: anthropic('claude-opus-4-6'),
  prompt: 'Hello!',
});

从工程角度看,这两条路径的差别不只是用不用网关。字符串形式把 provider 选择推迟到运行时配置,模型名以 provider/model 的形式出现;SDK 形式把 provider 变成 import 的模块,构造过程落在代码里。前者适合模型需要可切换、凭据集中管理的场景,后者适合需要 provider 特有参数或不想引入中间层的场景。README 没有说明两条路径在能力覆盖上是否完全等价,这一点在接入前需要自行验证。

结构化输出与类型系统

README 的结构化数据示例把 zod schema 直接交给 Output.object:

const { output } = await generateText({
  model: 'openai/gpt-5.4',
  output: Output.object({
    schema: z.object({
      recipe: z.object({
        name: z.string(),
        ingredients: z.array(z.object({ name: z.string(), amount: z.string() })),
        steps: z.array(z.string()),
      }),
    }),
  }),
  prompt: 'Generate a lasagna recipe.',
});

这里值得注意的不是支持结构化输出本身,而是 schema 作为调用参数出现:模型输出的形状与 TypeScript 的类型描述共用同一份定义。对表单填充、配置生成这类任务,这比在调用之后再做一次解析加校验更容易收敛。

Agent 定义与 UI 消息类型是同一套

README 的 Agent 示例用 ToolLoopAgent 定义 agent,tools 字段里放具体工具。两个例子分别是 openai.tools.localShell(execute 中通过沙箱执行命令,示例注释指向 Vercel Sandbox)和 openai.tools.imageGeneration({ partialImages: 3 })。

关键连接点在类型导出上:

export type ImageGenerationAgentMessage = InferAgentUIMessage;

这个类型在 Next.js App Router 的 route handler 里被 createAgentUIStreamResponse 使用,在前端则被 useChat() 使用。也就是说,agent 定义在服务端,消息类型推导到客户端,两端共用。

前端渲染逻辑同样值得看:messages 中每条消息有 parts 数组,遍历时按 part.type 分支,'text' 渲染文本,'tool-generateImage' 渲染工具调用视图。工具视图组件接收 UIToolInvocation,并按 invocation.state 分支,示例处理了 'input-available' 和 'output-available' 两个状态,图像结果在示例中以 base64 数据放进 img 标签。

对做生成式 UI 的团队来说,这个结构说明了一件事:工具调用的中间状态被建模成消息的一部分,而不是藏在某个 loading 变量里。这直接决定 UI 能表达什么——参数已就绪但结果未返回,和结果已返回,是两个可以分别处理的状态。

README 里没有回答的部分

以下内容在当前 README 中并未展开。如果有实际依赖,需要到文档或源码确认,不能从给出的示例外推:

  • 不同 provider 之间工具调用能力如何归一化。示例中的 localShell 和 imageGeneration 都来自 openai.tools,README 没有说明其他 provider 是否有对等实现。
  • ToolLoopAgent 的循环终止条件、步数上限、错误重试策略。
  • Vercel AI Gateway 与直连 provider 在鉴权、配额、计费上的具体差异。
  • 流式传输的协议细节,以及 createAgentUIStreamResponse 返回的数据格式。
  • Angular 在 UI 集成中的位置。框架支持列表包含 Angular,但 UI 集成一节明确列出的是 Next.js、React、Svelte、Vue,并说明 hooks 是 framework agnostic。

另外,README 建议使用 coding agents 的团队把 AI SDK skill 加进仓库(npx skills add vercel/ai),对象是 Claude Code、Cursor 这类工具。这个入口本身说明项目把让编码代理理解 SDK 用法当作安装流程的一部分。

评估同类工具包时的检查项

如果正在对比 AI 工具包,可以从这份 README 中提取几个可验证的问题:

  1. 统一抽象覆盖到哪一层。AI SDK 覆盖模型调用(generateText)和结构化输出(Output.object),更细的 provider 专有参数是否可透传,需要验证。
  2. 类型是否从服务端贯通到客户端。这里给出的答案是 InferAgentUIMessage 加 useChat。
  3. 工具调用状态是否可渲染。看 UIToolInvocation 的状态分支与消息 parts 的组织方式。
  4. 默认接入路径是否引入额外依赖。默认走 Vercel AI Gateway,会影响部署与凭据管理方式。
  5. 运行时要求。README 写明 Node.js 22+。

README 也说明了作者信息:由 Vercel 和 Next.js 团队成员创建,接受开源社区贡献。真正决定是否采用的,仍然是上面这些具体机制能否对上现有架构——尤其是工具调用和 provider 差异这两块,README 只给了入口,没有给结论。