LangGraph.js - 快速入门¶
简介¶
在本快速入门指南中,你将开始使用一个简单的 Reason + Act Agent (通常称为 ReAct Agent),它可以使用 Tavily Search API 搜索网络。代码是完全可配置的。你可以
- 替换组件
- 自定义执行流程
- 使用自定义代码或工具扩展它
- 更改正在使用的大型语言模型 (LLM) 和提供商
前提条件¶
要继续学习,你需要具备以下条件
- NodeJS 18 或更高版本
- 一个 Tavily 账户和 API 密钥
- 一个 OpenAI 开发者平台 账户和 API 密钥
首先为项目创建一个新文件夹。打开你的终端并运行以下代码
你还需要安装一些依赖项来创建一个 agent
- langchain/langgraph 包含了用于组装 agent 的构建块
- langchain/openai 使你的 agent 能够使用 OpenAI 的 LLM
- langchain/community 包含了 Tavily 集成,为你的 agent 提供搜索能力
你可以使用以下 npm 命令在你的终端中安装这些依赖项
LangSmith¶
(可选)设置 LangSmith 以获得一流的可观测性。设置很简单 - 将以下变量添加到你的环境,并使用你的 API 密钥更新 LANGCHAIN_API_KEY
值。
// Optional, add tracing in LangSmith
// process.env.LANGCHAIN_API_KEY = "ls__...";
// process.env.LANGCHAIN_CALLBACKS_BACKGROUND = "true";
// process.env.LANGCHAIN_TRACING_V2 = "true";
// process.env.LANGCHAIN_PROJECT = "Quickstart: LangGraphJS";
使用 LangGraph 创建你的第一个 Agent¶
创建一个名为 agent.ts
的文件(Reason + Act Agent 的缩写),并将以下 TypeScript 代码添加到其中。
确保你更新文件顶部的环境变量以包含你的 API 密钥。如果你不这样做,OpenAI 和 Tavily API 调用将产生错误,并且你的 agent 将无法正常工作。
一旦你添加了你的 API 密钥,保存文件并使用以下命令运行代码
// agent.ts
// IMPORTANT - Add your API keys here. Be careful not to publish them.
process.env.OPENAI_API_KEY = "sk-...";
process.env.TAVILY_API_KEY = "tvly-...";
import { TavilySearchResults } from "@langchain/community/tools/tavily_search";
import { ChatOpenAI } from "@langchain/openai";
import { MemorySaver } from "@langchain/langgraph";
import { HumanMessage } from "@langchain/core/messages";
import { createReactAgent } from "@langchain/langgraph/prebuilt";
// Define the tools for the agent to use
const agentTools = [new TavilySearchResults({ maxResults: 3 })];
const agentModel = new ChatOpenAI({ temperature: 0 });
// Initialize memory to persist state between graph runs
const agentCheckpointer = new MemorySaver();
const agent = createReactAgent({
llm: agentModel,
tools: agentTools,
checkpointSaver: agentCheckpointer,
});
// Now it's time to use!
const agentFinalState = await agent.invoke(
{ messages: [new HumanMessage("what is the current weather in sf")] },
{ configurable: { thread_id: "42" } },
);
console.log(
agentFinalState.messages[agentFinalState.messages.length - 1].content,
);
const agentNextState = await agent.invoke(
{ messages: [new HumanMessage("what about ny")] },
{ configurable: { thread_id: "42" } },
);
console.log(
agentNextState.messages[agentNextState.messages.length - 1].content,
);
The current weather in San Francisco is as follows:
- Temperature: 82.0°F (27.8°C)
- Condition: Sunny
- Wind: 11.9 mph from the NW
- Humidity: 41%
- Pressure: 29.98 in
- Visibility: 9.0 miles
- UV Index: 6.0
For more details, you can visit [Weather in San Francisco](https://www.weatherapi.com/).
The current weather in New York is as follows:
- Temperature: 84.0°F (28.9°C)
- Condition: Sunny
- Wind: 2.2 mph from SSE
- Humidity: 57%
- Pressure: 29.89 in
- Precipitation: 0.01 in
- Visibility: 9.0 miles
- UV Index: 6.0
For more details, you can visit [Weather in New York](https://www.weatherapi.com/).
它如何工作?¶
createReactAgent 构造函数让你在一行代码中创建一个简单的、使用工具的 LangGraph agent。这是一个图的可视化表示
// Note: tslab only works inside a jupyter notebook. Don't worry about running this code yourself!
import * as tslab from "tslab";
const graph = agent.getGraph();
const image = await graph.drawMermaidPng();
const arrayBuffer = await image.arrayBuffer();
await tslab.display.png(new Uint8Array(arrayBuffer));
自定义 Agent 行为¶
createReactAgent 对于简单的 agent 来说可能很棒,但有时你需要更强大的功能。
当你需要对 agent 的行为进行细粒度控制时,LangGraph 真正发挥作用。以下代码创建了一个与上面示例行为相同的 agent,但你可以清楚地看到执行逻辑以及如何自定义它。
更新你的 agent.ts
文件中的代码以匹配下面的示例。再次强调,请务必更新顶部的环境变量。
在你更新了你的环境变量并保存文件后,你可以使用与之前相同的命令运行它
// agent.ts
// IMPORTANT - Add your API keys here. Be careful not to publish them.
process.env.OPENAI_API_KEY = "sk-...";
process.env.TAVILY_API_KEY = "tvly-...";
import { TavilySearchResults } from "@langchain/community/tools/tavily_search";
import { ChatOpenAI } from "@langchain/openai";
import { HumanMessage, AIMessage } from "@langchain/core/messages";
import { ToolNode } from "@langchain/langgraph/prebuilt";
import { StateGraph, MessagesAnnotation } from "@langchain/langgraph";
// Define the tools for the agent to use
const tools = [new TavilySearchResults({ maxResults: 3 })];
const toolNode = new ToolNode(tools);
// Create a model and give it access to the tools
const model = new ChatOpenAI({
model: "gpt-4o-mini",
temperature: 0,
}).bindTools(tools);
// Define the function that determines whether to continue or not
function shouldContinue({ messages }: typeof MessagesAnnotation.State) {
const lastMessage = messages[messages.length - 1] as AIMessage;
// If the LLM makes a tool call, then we route to the "tools" node
if (lastMessage.tool_calls?.length) {
return "tools";
}
// Otherwise, we stop (reply to the user) using the special "__end__" node
return "__end__";
}
// Define the function that calls the model
async function callModel(state: typeof MessagesAnnotation.State) {
const response = await model.invoke(state.messages);
// We return a list, because this will get added to the existing list
return { messages: [response] };
}
// Define a new graph
const workflow = new StateGraph(MessagesAnnotation)
.addNode("agent", callModel)
.addEdge("__start__", "agent") // __start__ is a special name for the entrypoint
.addNode("tools", toolNode)
.addEdge("tools", "agent")
.addConditionalEdges("agent", shouldContinue);
// Finally, we compile it into a LangChain Runnable.
const app = workflow.compile();
// Use the agent
const finalState = await app.invoke({
messages: [new HumanMessage("what is the weather in sf")],
});
console.log(finalState.messages[finalState.messages.length - 1].content);
const nextState = await app.invoke({
// Including the messages from the previous run gives the LLM context.
// This way it knows we're asking about the weather in NY
messages: [...finalState.messages, new HumanMessage("what about ny")],
});
console.log(nextState.messages[nextState.messages.length - 1].content);
在我们 ReAct Agent 的这个版本中,发生了一些新的事情。
ToolNode
使 LLM 能够使用工具。在这个例子中,我们创建了一个 shouldContinue
函数并将其传递给 addConditionalEdge
,以便我们的 ReAct Agent 可以调用工具或响应请求。
注解 (Annotations) 是 LangGraph 中图状态的表示方式。我们正在使用 MessagesAnnotation
,这是一个辅助工具,它实现了一种常见的模式:将消息历史记录保存在数组中。
下一步¶
恭喜你使用 LangGraph 创建了你的第一个 AI agent!如果你准备构建更多内容,请查看我们的其他教程,了解如何实现其他端到端 agent 工作流程,例如
- 检索增强生成 (RAG)
- 多 Agent 协作
- 反思 (Reflection),agent 在其中评估其工作
如果你更愿意改进你的 agent,我们有操作指南来帮助你,包括
- 工具调用 (Tool calling),使 agent 能够与 API 交互
- 为你的 agent 提供 持久性内存 (persistent memory) 以继续对话并调试意外行为
- 对于你希望人类验证的操作,将 人工干预 (human in the loop) 纳入循环
- 流式传输 agent 输出 (Streaming the agent output),使你的应用程序感觉更灵敏
- 在一行代码中更改 AI 模型