Vercel AI SDK 5加LangGraph,我连夜跑通说点真话
前端人,样式是真卷不动了
这话放这,可能有点扎心。但你看啊,现在出去面试,Vue React早就不算加分项了,人家问的是:流式断了你咋续?tool call炸了你咋修?Agent跑飞了你咋拦
我连夜把 Vercel AI SDK 5、LangChain 那套 Deep Agents 对 LangGraph、还有 Node 网关这波全扒了一遍
先给结论,不绕弯
前端 AI 全栈这事,真不是噱头。AI SDK 管脸,LangGraph 管脑,Node 管钱和门,三件套齐了,一个人是真能上线的
老全栈为啥玩不转 AI
以前的全栈,路由器加 CRUD 加个管理后台,完事
AI 应用完全是另一个物种。我替你数数,多了啥:
流。模型一个 token 一个 token 往外吐,你得边吐边渲染,断了还得续。以前等接口返回再渲染那套,直接卡死
tool。模型不再是回文本,是回”我要调哪个工具,参数是啥”。调完还得把结果塞回去再跑一轮。这叫 roundtrip,以前的前端哪见过这个
状态。Agent跑五分钟,中间调了八个工具,你刷新下页面,全没了。resumable streams、多步骤推理、消息管理,全是新坑
我当时第一反应:完了,又得加班学了
但好消息是,Vercel 那帮人比我们先撞墙。他们在 AI SDK 里把这堆脏活全包了。用 OpenCode 那帮人的原话:以前拿胶带粘的地方,人家全给了干净 API
AI SDK 5三件套,我一个个试了
先说大实话:AI SDK 就是个 TypeScript 统一层。npm i ai,换模型改两行,不用每个厂商重写一套
三件套,记住就行
Core,管生文本和调工具
import { generateText, streamText, tool } from 'ai';
import { z } from 'zod';
const result = await streamText({
model: 'xai/grok-4.6',
messages: convertToModelMessages(messages),
tools: {
weather: tool({
description: 'Get the weather in a location',
inputSchema: z.object({ city: z.string() }),
execute: async ({ city }) => `Weather in ${city}: sunny, 72°F`,
}),
},
});
generateText 跑单步,streamText 边跑边吐。generateObject 和 streamObject 直接回类型安全的 JSON,zod 一把梭,不用再 parse 祈祷
stopWhen,把单次请求变循环
默认调一次就停。加上 stopWhen,模型一直调 tool,直到满足条件,或者开始说人话才停
const result = await streamText({
model: openai('gpt-4o'),
messages,
tools: { /* 你的工具 */ },
prepareStep: async ({ stepNumber }) => {
if (stepNumber === 0) {
return { model: openai('gpt-4o-mini') };
}
},
stopWhen: stepCountIs(5),
});
这招贼实用。第一步用便宜模型探路,后面再上贵的。tool choice 还能强制指定用哪个,或者直接禁用。省钱全靠这了
tool流式,卡顿的解药
AI SDK 5 最香的就是这个。tool 参数还没收齐,前端就能先看到增量:
onInputDelta: ({ inputTextDelta, toolCallId }) => {
console.log('Tool input delta:', inputTextDelta);
},
onInputAvailable: ({ input, toolCallId }) => {
console.log('Tool input ready:', input);
},
以前 tool 没回来页面就干等,现在边收边渲染。体感差了一个时代
| 分工 | 谁干 | 抄啥 |
|---|---|---|
| 脸和手 | AI SDK | streamText、generateObject、tool流式、MCP发现、AI Gateway换模型 |
| 脑和腿 | LangGraph.js | StateGraph分支、重试、人工卡点、Deep Agents中间件 |
| 监控 | LangSmith | tracing、evals天天跑、deployment一键上 |
| 门和钱 | Node网关 | 鉴权、限流计费、MCP收敛、流转发 |
UI 那层更省事。React、Next.js、Vue、Svelte、Node 全支持,chat 和生成式 UI 全是现成 hooks。MCP也接上了,Vercel 上连 MCP server,发现工具直接调,模型走 AI Gateway,100多个模型不用管 key
深度再往下挖一层,AI SDK 5 真值钱的全是脏活:
// tool 修坏:参数缺了、类型错了,直接修别重跑整轮
// Nodejs 可跑,修一次省一次大模型调用
import { toolRepair } from './tool-repair';
const result = await streamText({
model: 'gpt-4o',
messages,
tools: { order: orderTool },
stopWhen: stepCountIs(5),
repairToolCall: async ({ toolCall, error }) => {
const fixed = toolRepair(toolCall, error);
return fixed ? { ...toolCall, args: fixed } : null;
},
});
// 消息管理:Agent跑五分钟,历史直接炸窗,先裁再发
// Nodejs 可跑,query 和 tool 结果分开记,别全塞 messages
import { trimMessages } from './messages';
const safeMessages = trimMessages(messages, { maxTokens: 8000, keepToolResults: 3 });
番外:我当时以为流式很简单
说实话,我一开始觉得不就是 SSE 吗,能有多难
结果 tool calling 一进来,全乱了。文本流、对象流、tool 流三股搅一起,断线重连、消息去重、tool 修坏,全是坑。AI SDK 值钱就值在这:人家替你踩完了
LangChain对LangGraph,别再二选一了
这俩的关系,2026年终于说清楚了
LangChain 是最快从 0 到能跑的 Agent。provider 无关,tool loop 现成,middleware 随便插。LangGraph 是编排 runtime,状态图、分支、人工介入、多智能体,全是它的活
关键一句:2025年10月之后,LangChain 的 create_agent 就是跑在 LangGraph runtime 上的。JS 侧也一样,@langchain/langgraph 就是同一套图 runtime,前端人不用换语言
// Nodejs 可跑:LangGraph.js 最小图,bun/node 直接跑
import { StateGraph, MessagesAnnotation, START, END } from '@langchain/langgraph';
const graph = new StateGraph(MessagesAnnotation)
.addNode('mock_llm', async (state) => {
return { messages: [{ role: 'ai', content: 'hello world' }] };
})
.addEdge(START, 'mock_llm')
.addEdge('mock_llm', END)
.compile();
await graph.invoke({ messages: [{ role: 'user', content: 'hi!' }] });
// Nodejs 可跑:Deep Agents JS 版,Todo + 求和 + 子 Agent 中间件一把开
// npm i deepagents @langchain/core
import { createDeepAgent } from 'deepagents';
const agent = createDeepAgent({
model: 'gpt-4o',
tools: [weatherTool],
middleware: ['todo', 'summarization', 'sub-agent'],
});
await agent.invoke({ messages: [{ role: 'user', content: '查三城天气再汇总' }] });
// Nodejs 可跑:LangSmith tracing, Bun 侧一行打开,决策链全落盘
process.env.LANGSMITH_TRACING = 'true';
process.env.LANGSMITH_API_KEY = process.env.LANGSMITH_API_KEY!;
咋选?抄作业就行:
简单 Agent,直接 create_agent,快。复杂工作流,分支、重试、人工卡点,直接 LangGraph。Deep Agents 扔进去当子 Agent 也行,反过来把 LangGraph 图塞进 create_deep_agent 当子 Agent也行,两边是通的
老的 AgentExecutor 已经 deprecated,只维护不更新了,还在用的,抽空迁了吧,别等爆雷
LangSmith 是标配。三件事:tracing看每次决策,evals给Agent打分,deployment一键上线。Jev-as-a-Judge那篇就是拿它跑的,500次改卷,Jev全对,方差低两个数量级。评估这事,以后是天天考,不是考一次
说白了,LangChain 管脸和手,LangGraph 管脑和腿,LangSmith 管监控。三件套,少一个都瘸
Node网关:钱和门,得有人看
模型 key 放前端?等于裸奔
流一断账单就炸,tool 被刷一晚上,第二天早上你就懂了。Node 网关不是炫技,是保命。三件事必须有:
鉴权。谁能调,调多少次,一天多少额度,全在网关卡。前端只拿短期 token
限流计费。按用户、按 key、按模型分级限。跑批的走闲时,交互的走高峰。计费对上,后面才敢收钱
MCP收敛。250个工具全扔给模型?context 直接炸。网关做动态发现,按需给,按权限给。Composio、Toolhouse那套就是干这个的,3行接25个动作,听着爽,用时记得收权限
直接上能跑的网关骨架,Bun/Node + Hono,复制就能启动:
// gateway.ts,bun gateway.ts 直接跑
// npm i hono @hono/node-server ai
import { Hono } from 'hono';
import { streamText, stepCountIs } from 'ai';
const app = new Hono();
const buckets = new Map<string, { count: number; resetAt: number }>();
// 1. 鉴权 + 限流:前端只带短期 token,key 全在服务端
app.use('/api/agent/*', async (c, next) => {
const token = c.req.header('x-agent-token');
if (token !== process.env.AGENT_TOKEN) return c.text('unauthorized', 401);
const uid = c.req.header('x-user-id') ?? 'anon';
const now = Date.now();
const slot = buckets.get(uid) ?? { count: 0, resetAt: now + 60_000 };
if (now > slot.resetAt) { slot.count = 0; slot.resetAt = now + 60_000; }
slot.count += 1;
buckets.set(uid, slot);
if (slot.count > 30) return c.text('rate limited, slow down', 429);
await next();
});
// 2. MCP 收敛:按步骤给工具,第一步只给搜索,第二步再给下单
const searchTools = { searchDocs: searchDocsTool };
const orderTools = { searchDocs: searchDocsTool, createOrder: createOrderTool };
// 3. 流转发 + 计费日志:边吐边记,token 和 tool 调用全落盘
app.post('/api/agent/chat', async (c) => {
const { messages, step = 0 } = await c.req.json();
const startedAt = Date.now();
const result = streamText({
model: step === 0 ? 'gpt-4o-mini' : 'gpt-4o',
messages: convertToModelMessages(messages),
tools: step === 0 ? searchTools : orderTools,
stopWhen: stepCountIs(5),
onFinish: async ({ usage, steps }) => {
console.log(JSON.stringify({
tookMs: Date.now() - startedAt,
inputTokens: usage.inputTokens,
outputTokens: usage.outputTokens,
toolCalls: steps.flatMap((s) => s.toolCalls ?? []).length,
}));
},
});
return result.toUIMessageStreamResponse();
});
export default app;
// Next Route Handler,App Router 下 app/api/agent/chat/route.ts
// 前端只调自家 /api,不碰模型 key
import { streamText } from 'ai';
export async function POST(req: Request) {
const { messages } = await req.json();
const result = streamText({
model: 'gpt-4o',
messages: convertToModelMessages(messages),
tools: { weather: weatherTool },
});
return result.toUIMessageStreamResponse();
}
// 前端 useChat,断线能续,tool 状态全有态,别只写 happy path
// npm i @ai-sdk/react
import { useChat } from '@ai-sdk/react';
const { messages, sendMessage, status } = useChat({ api: '/api/agent/chat' });
// status: submitted | streaming | ready | error
// tool-call: input-streaming | input-available | output-available | output-error
B站上那堆”从0手写Agent平台:Agent、RAG、MCP网关、计费、高可用”,为啥火?校招都开始考这个了。因为企业真被账单和安全搞怕了。你简历上写”调过大模型API”,面试官直接怼:Think-Execute循环呢?RAG呢?MCP呢?全是这三问
技术栈我建议:Bun/Node + Hono/Elysia,轻,快,TS一把梭。LangGraph 也有 JS 版,重编排一样能留在 TS 里,不用来回切 Python。各干各的,别拧巴
单句成节
网关省的钱,全是半夜不会被吵醒的觉
三条翻车实录,全是我和群友的血
第一条,流断了没续,页面卡死
tool 没回来,前端干等,用户狂点重试,后端被打爆。修法:AI SDK 的 resumable streams 接上,tool 状态机写全,in-progress、ready、error 全有态。别只写 happy path
第二条,工具全量扔,context 炸了
40多个工具一次性给模型,又慢又贵,还老调错。修法:动态发现 + 按步骤给。第一步只给搜索,第二步再给下单。prepareStep 里换模型也顺手做了,便宜的探路,贵的拍板
第三条,评估只跑一次,上线就翻
demo 时全对,一上线全错。修法:抄 LangChain 那套,固定数据集天天跑,Jev这种便宜裁判全量跑,贵的抽查。低置信转人工,别硬上。一个人也要有 CI,别裸奔上线
凌晨 2 点还在看 log,咖啡已经没用了。这种夜,我过过,不想你再过
那前端人,到底咋上车
三步,今晚就能动手:
先跑通 AI SDK 的 chatbot 模板,npm run dev,把流式和 tool 调通。别贪多,一个天气 tool 就够
再把 LangGraph 的 Deep Agents 接上,JS 这边 npm i deepagents @langchain/langgraph,Todo、Summarization、Sub-agent 三个 middleware 开一个试试。LangSmith tracing 打开,看一次完整决策链,比看十篇博客管用
生产清单我贴墙上了,抄走:abort 信号全链路透传、tool 状态机写全、评估固定数据集天天跑、低置信转人工、账单每天看一眼。少一条,半夜 pager 就教你做人
最后给 Node 加上门和钱。鉴权限流计费,三件先行。MCP 先接一个,后面再加。账单截图每天看一眼,比跑分重要
自查还是老三问:一个人能跑吗?多少钱?半夜会炸吗
答不上来就别急着辞职,先当副业跑。跑出第一个续费单,再说 All in 的事。我银行卡是真有感觉,第一个续费到账那晚,比发版成功还爽
最后一句能记住的话
前端没死,纯切图的活是真没了
以后就两种前端:会调样式的,和会调 Agent 的。后者贵得多,也累得多,但半夜睡得着,因为网关和评估都接好了
Vercel 管脸,LangGraph 管脑,Node 看门和钱。这三件凑齐,剩下的就是熬夜和账单了。而这,不就是独立开发者的日常吗
你最近在拿 AI SDK 还是 LangGraph?卡在哪了?评论区聊聊,我蹲着看
如果这篇对你有用,欢迎订阅本站 RSS,后续还有前端 AI 全栈系列,我把跑通的模板和账单都贴出来。
原创技术博客 · 开源项目分享 · AI全栈创作社区 idao.fun
参考资料
- Vercel AI SDK 文档{:rel=“nofollow noopener noreferrer” target=“_blank”}
- Vercel:AI SDK 5{:rel=“nofollow noopener noreferrer” target=“_blank”}
- LangChain:Deep Agents vs LangChain vs LangGraph{:rel=“nofollow noopener noreferrer” target=“_blank”}
- LangGraph.js 概览文档{:rel=“nofollow noopener noreferrer” target=“_blank”}
- Uvik:LangChain vs LangGraph 2026选型指南{:rel=“nofollow noopener noreferrer” target=“_blank”}
- AI SDK MCP 文档{:rel=“nofollow noopener noreferrer” target=“_blank”}