Skip to main content
本快速入门指南将向你展示如何在短短几分钟内创建一个功能完备的 AI 智能体。
正在使用 AI 编码助手?

安装依赖

安装以下包以跟随本教程:
npm install deepagents langchain @langchain/core
# 需要 Node.js 20+

设置 API 密钥

任何受支持的模型提供商(例如,Google Gemini 或 OpenAI)获取 API 密钥。 设置 API 密钥,例如:
export OPENAI_API_KEY="your-api-key"

构建基础智能体

首先创建一个简单的智能体,它能够回答问题并调用工具。此示例中的智能体使用所选的语言模型、一个作为工具的基本天气函数,以及一个简单的提示来指导其行为:
import { createAgent, tool } from "langchain";
import * as z from "zod";

const getWeather = tool(
  (input) => `It's always sunny in ${input.city}!`,
  {
    name: "get_weather",
    description: "Get the weather for a given city",
    schema: z.object({
      city: z.string().describe("The city to get the weather for"),
    }),
  }
);

const agent = createAgent({
  model: "gpt-5.4",
  tools: [getWeather],
});

console.log(
  await agent.invoke({
    messages: [{ role: "user", content: "What's the weather in San Francisco?" }],
  })
);
当你运行代码并提示智能体告诉你旧金山的天气时,智能体会使用该输入及其可用的上下文。 智能体理解你是在询问旧金山市的天气,因此会使用提供的城市名称调用天气工具。
你可以通过更改代码中的模型名称并设置相应的 API 密钥来使用任何受支持的模型

构建实际应用智能体

在接下来的示例中,你将构建一个研究智能体,它可以回答关于文本文件的问题。 在此过程中,你将探索以下概念:
  1. 详细的系统提示,以改善智能体行为
  2. 创建工具,与外部数据集成
  3. 模型配置,以获得一致的响应
  4. 对话记忆,实现类似聊天的交互
  5. Deep Agents,提供内置功能
  6. 测试你的智能体
1

定义系统提示

系统提示定义了你的智能体的角色和行为。保持其具体且可操作:
const SYSTEM_PROMPT = `You are a literary data assistant.

## Capabilities

- \`fetch_text_from_url\`: loads document text from a URL into the conversation.
Do not guess line counts or positions—ground them in tool results from the saved file.`;
2

创建工具

工具允许模型通过调用你定义的函数与外部系统交互。 工具可以依赖于运行时上下文,也可以与智能体记忆交互。此示例使用一个工具从给定的 URL 加载文档:
import { tool } from "@langchain/core/tools";
import { createAgent, initChatModel } from "langchain";
import { z } from "zod";

const fetchTextFromUrl = tool(
    async ({ url }: { url: string }): Promise<string> => {
        const controller = new AbortController();
        const timeoutId = setTimeout(() => controller.abort(), 120_000);
        try {
            const resp = await fetch(url, {
                headers: {
                "User-Agent": "Mozilla/5.0 (compatible; quickstart-research/1.0)",
                },
                signal: controller.signal,
            });
            if (!resp.ok) {
                return `Fetch failed: HTTP ${resp.status} ${resp.statusText}`;
            }
            return await resp.text();
        } catch (e) {
            const msg = e instanceof Error ? e.message : String(e);
            return `Fetch failed: ${msg}`;
        } finally {
            clearTimeout(timeoutId);
        }
    },
    {
        name: "fetch_text_from_url",
        description: "Fetch the document from a URL.",
        schema: z.object({ url: z.string().url() }),
    },
);
Zod 是一个用于验证和解析预定义模式的库。你可以用它来定义工具的输入模式,以确保智能体只使用正确的参数调用工具。或者,你可以将 schema 属性定义为 JSON schema 对象。请记住,JSON schema 不会在运行时进行验证。
import { tool } from "langchain";

const fetchTextFromUrl = tool(
async ({ url }: { url: string }): Promise<string> => {
    const controller = new AbortController();
    const timeoutId = setTimeout(() => controller.abort(), 120_000);
    try {
    const resp = await fetch(url, {
        headers: {
        "User-Agent": "Mozilla/5.0 (compatible; quickstart-research/1.0)",
        },
        signal: controller.signal,
    });
    if (!resp.ok) {
        return `Fetch failed: HTTP ${resp.status} ${resp.statusText}`;
    }
    return await resp.text();
    } catch (e) {
    const msg = e instanceof Error ? e.message : String(e);
    return `Fetch failed: ${msg}`;
    } finally {
    clearTimeout(timeoutId);
    }
},
{
    name: "fetch_text_from_url",
    description: "Fetch the document from a URL.",
    schema: {
    type: "object",
    properties: {
        url: {
        type: "string",
        description: "The URL of the document to fetch.",
        format: "uri",
        },
    },
    required: ["url"],
    },
},
);
3

配置你的模型

为你的用例设置具有正确参数的语言模型。例如:
import { initChatModel } from "langchain";

const model = await initChatModel("gpt-5.4", {
  temperature: 0.5,
  timeout: 300,
  maxTokens: 25000,
});
根据所选的模型和提供商,初始化参数可能有所不同;详情请参阅其参考页面。
4

添加记忆

为你的智能体添加记忆,以在交互中保持状态。这允许 智能体记住之前的对话和上下文。
import { MemorySaver } from "@langchain/langgraph";

const checkpointer = new MemorySaver();
在生产环境中,请使用将消息历史保存到数据库的持久化检查点。 有关更多详细信息,请参阅添加和管理记忆
5

创建并运行智能体

现在,使用所有组件组装你的智能体并运行它。创建智能体有两种不同的框架:LangChain 智能体和 deep agents。 LangChain 和 deep agents 都为你提供了对工具、记忆等的细粒度控制。 两者的主要区别在于 deep agents 内置了一系列常用功能,例如规划、文件系统工具和子智能体。当你希望以最少的设置获得最大功能时,请使用 deep agents;当你需要细粒度控制时,请选择 LangChain 智能体。
由于代码使用了《了不起的盖茨比》的全部文本来调用模型,因此它使用了大量的 token。你可以在下一步中查看示例输出。
让我们尝试两种方式:
async function main() {
    const agent = createAgent({
        model,
        tools: [fetchTextFromUrl],
        systemPrompt: SYSTEM_PROMPT,
        checkpointer,
    });

    const deepAgent = createDeepAgent({
        model,
        tools: [fetchTextFromUrl],
        systemPrompt: SYSTEM_PROMPT,
        checkpointer,
    });

    const content = `Project Gutenberg hosts a full plain-text copy of F. Scott Fitzgerald's The Great Gatsby.
    URL: https://www.gutenberg.org/files/64317/64317-0.txt

    Answer as much as you can:

    1) How many lines in the complete Gutenberg file contain the substring \`Gatsby\` (count lines, not occurrences within a line, each line ends with a line break).
    2) The 1-based line number of the first line in the file that contains \`Daisy\`.
    3) A two-sentence neutral synopsis.

    Do your best on (1) and (2). If at any point you realize you cannot **verify** an exact answer with
    your available tools and reasoning, do not fabricate numbers: use \`null\` for that field and spell out
    the limitation in \`how_you_computed_counts\`. If you encounter any errors please report what the error was and what the error message was.`;

    const agentResult = await agent.invoke(
        { messages: [{ role: "user", content }] },
        { configurable: { thread_id: "great-gatsby-lc" } },
    );
    const deepAgentResult = await deepAgent.invoke(
        { messages: [{ role: "user", content }] },
        { configurable: { thread_id: "great-gatsby-da" } },
    );

    const agentMessages = agentResult.messages;
    const deepMessages = deepAgentResult.messages;
    console.log(agentMessages[agentMessages.length - 1]!.content_blocks);
    console.log("\n");
    console.log(deepMessages[deepMessages.length - 1]!.content_blocks);
}

main().catch((err) => {
    console.error(err);
    process.exitCode = 1;
});
6

查看结果

结果会因模型和执行情况而异。
**1) 包含 `Gatsby` 的行数:** `null`

**2) 包含 `Daisy` 的第一行:** `null`

**3) 概要:**
《了不起的盖茨比》讲述了神秘的百万富翁杰伊·盖茨比及其与前情人黛西·布坎南重聚的痴迷,由他的邻居尼克·卡拉韦叙述。故事背景设定在长岛的咆哮二十年代,小说探讨了财富、阶级以及美国梦的虚幻本质等主题。

**how_you_computed_counts:**
我成功使用 `fetch_text_from_url` 工具获取了电子书的全文。但是,由于我无法访问代码执行环境(如 Python)或文本处理工具(如 `grep`),我无法确定性地按换行符分割文本、遍历数千行并验证确切的行号或匹配计数。LLM 无法在没有外部计算工具的情况下,在其上下文窗口内可靠地对大量文本执行精确的行计数或索引。根据指示,我没有编造或猜测数字,而是为确切的计数和位置输出了 `null`。
如果你查看两个标签页上的输出,你会注意到 LangChain 智能体提供了答案,但它们是估计值。智能体缺乏回答此问题的工具。你也可能收到提示太长的错误。另一方面,deep agent 可以:
  1. 规划其方法,使用内置的 write_todos 工具来分解研究任务。
  2. 加载文件,通过调用 fetch_text_from_url 工具来收集信息。
  3. 管理上下文,使用文件系统工具(grepread_file)。
  4. 生成子智能体,根据需要将复杂的子任务委托给专门的子智能体。
对于 LangChain 智能体,你必须实现更多功能才能获得类似级别的服务,并且可以根据需要随时进行自定义。

跟踪智能体调用

你使用 LangChain 构建的大多数有趣的应用程序都会多次调用 LLM。随着这些应用程序变得越来越复杂,能够检查智能体内部到底发生了什么变得非常重要。最好的方法是使用 LangSmith 注册一个 LangSmith 帐户并设置以下内容以开始记录跟踪:
export LANGSMITH_TRACING="true"
export LANGSMITH_API_KEY="..."
设置完成后,再次运行你的脚本,然后在 LangSmith 上检查智能体调用期间发生了什么。
要了解更多关于使用 LangSmith 跟踪智能体的信息,请参阅 LangSmith 文档

后续步骤

你现在拥有的智能体可以:
  • 理解上下文并记住对话
  • 智能地使用工具
  • 以一致的格式提供结构化响应
  • 通过上下文处理用户特定信息
  • 在交互中维护对话状态
  • 规划、研究和综合(仅限 deep agents)
继续学习: