Mindket

OpenAI Agents SDK:用 Python 搭建你的第一个智能体

黑色横幅,标题是“OpenAI API 实战”,下面是“Responses、工具调用、结构化输出与智能体”。

OpenAI Agents SDK 是一个 Python 和 TypeScript 库,在你的应用内部运行智能体循环。你用指令、工具和交接定义一个 Agent,Runner 负责调用模型、运行工具调用、切换智能体,直到拿到最终回答。护栏、会话和追踪都是内置的,你只需要写自己应用特有的部分。

本节内容

  • 先让一个智能体回答好一个问题,再去设计一组智能体。
  • 在每个分支上先定下谁来写最终回复,再选对应的模式。
  • 在代价高或无法撤销的操作前面,放上阻塞式检查。
  • 每段对话的记忆只放在一个地方。
  • 开始调提示词之前,先打开第一次运行的追踪记录。
全部课程
本页目录
  1. 开始之前
  2. 创建并运行你的第一个智能体
  3. 给智能体加上工具,弄懂这个循环
  4. 交接给专职智能体,并给运行加上护栏
  5. 记住对话,再读懂追踪记录
  6. OpenAI Developers 和 Steve Coffey 谈 Agents SDK
  7. 常见错误
  8. 自己试一试
  9. 接下来
  10. 自测一下
  11. 常见问题
  12. 资料来源

开始之前

在 Python 3.10 或更高版本上用 pip install openai-agents 安装 SDK,TypeScript 则用 npm install @openai/agents zod。TypeScript SDK 可以运行在 Node.js 22 或更高版本、Deno、Bun,以及开启了 nodejs_compat 的 Cloudflare Workers 上。两者都和第 1 课一样,从 OPENAI_API_KEY 读取密钥。Python 里的导入名是 agents,不是 openai_agents。

这里说的智能体,是一个带指令和工具、会一直工作到任务完成的模型。这个 SDK 是 OpenAI 用来搭建智能体的库,文档称它是早先实验项目 Swarm 的生产级升级版。它的组成部分很少:智能体,负责委派的交接和“智能体作为工具”,负责检查的护栏,以及内置的追踪。其余部分都是普通的 Python 或 TypeScript。

OpenAI 提供了三种搭建智能体的方式,智能体概览对它们做了比较。用 Responses API,循环要你自己写,就像第 2 课和第 3 课那样。用 Agents SDK,循环在你的应用内部运行,工具、存储和审批都由你的服务器掌控。用 Agents API,则由 OpenAI 运行一个托管的 Codex 运行框架来处理长时间任务,并替你保存进度。

如果你用过 Anthropic 的工具,Claude Agent SDK 一课讲的是一个目标相近、设计不同的库,Claude API 课程的最后一课则是手写循环。OpenAI 的 SDK 介于两者之间:智能体在代码里定义,循环交给运行器。

OpenAI 更新日志里的 Agents SDK 和 Agents API
  1. Agents SDK 发布

    一个用来设计、构建和部署智能体的编排框架。

  2. TypeScript 版本

    Agents SDK 推出 TypeScript 版。

  3. 沙箱和记忆控制

    智能体可以在受控沙箱里运行,记忆何时创建、存在哪里也由你决定。

  4. 更新来到 TypeScript

    带上沙箱智能体和开源的智能体运行框架。

  5. Agents API 公开 beta

    OpenAI 用托管的 Codex 环境运行智能体,并负责会话、压缩和恢复。

来源:OpenAI Docs: Changelog (2026年11月5日 查阅)

创建并运行你的第一个智能体

给一个名叫“History tutor”的智能体一条指令,再问它“When did the Roman Empire fall?”,快速入门说你会在终端里看到一个简洁的回答。这就是一次运行。下面的代码是快速入门里的 Python 版本,原样照搬。

撑起它的是三个名字。Agent 保存配置:一个会出现在追踪和交接里的 name,instructions,以及 model。Runner.run 接收一个起始智能体和一段输入,运行循环并返回结果。result.final_output 就是回答。在 TypeScript 里,同一个程序写作 new Agent({ ... }),接着 await run(agent, "..."),再读 result.finalOutput。

运行器有三个入口。Runner.run 是异步的,Runner.run_sync 把它包装成普通脚本可用的同步版本,Runner.run_streamed 则在运行进行中就把事件交给你。流式运行用的是同一个循环,所以要等流结束,才能把这次运行当作已经完成。没写 model 的智能体,会在设置了 OPENAI_DEFAULT_MODEL 时退回到它,这样整个进程可以共用一个默认模型。如果指令要随当前用户或租户而变,定义指南建议用一个动态指令回调,而不是在调用智能体的地方拼接字符串。

import asyncio

from agents import Agent, Runner

agent = Agent(
    name="History tutor",
    instructions="You answer history questions clearly and concisely.",
    model="gpt-6-astra",
)

async def main() -> None:
    result = await Runner.run(agent, "When did the Roman Empire fall?")
    print(result.final_output)

if __name__ == "__main__":
    asyncio.run(main())
  1. 用 pip install openai-agents 安装 SDK,并导出 OPENAI_API_KEY。
  2. 把代码存成 agent.py。
  3. 运行 python agent.py,读一读智能体打印出来的回答。
  4. 把指令改成只要求一句话,再运行一次。
  5. 在 OpenAI 平台的追踪记录里,找到你刚才那次运行。

给智能体加上工具,弄懂这个循环

工具通常是智能体最先需要的东西。在 Python 里,@function_tool 装饰器能把一个普通函数变成工具。SDK 读取函数签名来生成 JSON Schema,并用文档字符串作为工具描述和每个参数的描述。在快速入门的示例里,“Return a short history fact.”就成了模型看到的描述。

托管工具也能用,比如第 2 课的网页搜索和文件搜索。在 TypeScript 里,函数工具写作 tool({ name, description, parameters, execute }),参数用一个 Zod 对象来写。工具很多时,可以先藏起来:@function_tool(defer_loading=True) 让一个工具先不露面,等 ToolSearchTool() 需要时再加载。

MCP 服务器有两种接法。托管的 MCP 工具适合公开的远程服务器,模型通过 OpenAI 访问它们。本地或私有的服务器则从你自己的运行环境经 stdio 或可流式 HTTP 连接,连接、过滤和审批都由你的代码掌控。

接下来,运行器反复执行同一个循环。它用准备好的输入调用当前智能体的模型,再看返回了什么。如果是工具调用,就运行它们,把结果追加进去,再转一圈。如果是交接,就切换当前智能体,再转一圈。如果是最终回答,运行就结束。

最终回答的意思是:输出了预期类型的文本,并且没有工具调用。如果把 output_type 设为一个 Pydantic 模型或 Zod schema,预期类型就是这个结构,背后用的正是第 3 课的结构化输出。没有设置时,预期类型就是纯文本。

每转一圈算一个回合,Python SDK 默认把一次运行限制在 10 个回合。超过上限,运行器会抛出 MaxTurnsExceeded。传入 max_turns 可以调高或调低这个上限,传 max_turns=None 则取消上限。想停得温和一些,可以用 error_handlers,它接受 "max_turns"、"model_refusal" 和 "invalid_final_output",让你返回一个可控的最终输出,而不是抛出异常。

有些工具不该在没人点头的情况下运行。用 @function_tool(needs_approval=True) 标记它,运行就会暂停,而不是直接调用。这时结果里会有 interruptions,以及一个可以用 result.to_state() 恢复的状态。你的代码调用 state.approve(interruption) 批准或拒绝,再用 Runner.run(agent, state) 继续。指南把这看作同一次运行,而不是新的用户回合,审核期间还可以把状态存起来。

import asyncio

from agents import Agent, Runner, function_tool

@function_tool
def history_fun_fact() -> str:
    """Return a short history fact."""
    return "Sharks are older than trees."

agent = Agent(
    name="History tutor",
    instructions="Answer history questions clearly. Use history_fun_fact when it helps.",
    tools=[history_fun_fact],
)

async def main() -> None:
    result = await Runner.run(
        agent,
        "Tell me something surprising about ancient life on Earth.",
    )
    print(result.final_output)

if __name__ == "__main__":
    asyncio.run(main())
出自运行智能体指南和 Python SDK 的运行智能体页面,2026 年 11 月 5 日阅读。
模型产出了什么运行器接下来做什么
预期类型的文本,且没有工具调用结束循环,返回结果
一个或多个工具调用运行它们,追加结果,再次调用模型
交接给另一个智能体把那个智能体设为当前智能体,再次调用模型
调用了标记为 needs_approval 的工具暂停,返回 interruptions 和可恢复的状态
超过回合上限之后的任何输出抛出 MaxTurnsExceeded

交接给专职智能体,并给运行加上护栏

给一个“Homework triage”智能体列上历史辅导和数学辅导两个交接对象,再问它“Who was the first president of the United States?”。运行最后给出的是历史辅导的回答,result.last_agent.name 会告诉你是哪个专职智能体给的。这个示例就是快速入门里的原样代码。

在背后,每个交接都是一个工具。一个叫“Refund Agent”的智能体,会变成一个叫 transfer_to_refund_agent 的工具,分诊智能体像调用别的工具一样调用它。每个专职智能体上的 handoff_description 告诉路由智能体什么时候该选它,所以指南要求写得简短具体。交接之后,如果希望这个专职智能体继续主导,就把 last_agent 传进下一个回合。交接还可以携带结构化的元数据或过滤过的历史,具体接法见各语言的 SDK 文档。

编排指南把这个选择看成归属问题。交接是把对话交给专职智能体。“智能体作为工具”则不同,Python 里用 agent.as_tool(),TypeScript 里用 agent.asTool(),由一个管理者智能体调用专职智能体完成摘要这类边界清楚的任务,最终回复由它自己来写。指南的建议是从一个智能体开始,只有当某个分支需要不同的指令、工具、策略或模型时才拆分。

护栏是自动检查。输入护栏验证用户发来的内容,输出护栏检查最终回答,工具护栏包住函数工具的参数或结果。检查不通过时会触发绊线,运行器随即抛出 InputGuardrailTripwireTriggered 或对应的输出异常,并停止运行。

输入护栏默认和智能体并行运行,也就是 run_in_parallel=True,这样能省时间。可一旦它触发,智能体可能已经用掉了 token、运行了工具。如果启动智能体的代价或风险太高,就设置 run_in_parallel=False,让检查先跑完。指南的示例正是这样做的,它把一个作业检查放在客服智能体前面。问到“Can you solve 2x + 3 = 11 for me?”时,检查触发,运行器抛出异常,示例打印出“Guardrail blocked the request.”。异常里的 guardrail_result 会写明是哪个护栏触发的。

两种护栏都有作用范围。输入护栏只对链条上的第一个智能体运行,输出护栏只对产出最终输出的那个智能体运行。工具护栏则在它所挂的函数工具上运行。在管理者模式的流程里,要把检查放在真正产生副作用的那个工具旁边。

import asyncio

from agents import Agent, Runner

history_tutor = Agent(
    name="History tutor",
    handoff_description="Specialist for history questions.",
    instructions="Answer history questions clearly and concisely.",
)

math_tutor = Agent(
    name="Math tutor",
    handoff_description="Specialist for math questions.",
    instructions="Explain math step by step and include worked examples.",
)

triage_agent = Agent(
    name="Homework triage",
    instructions="Route each homework question to the right specialist.",
    handoffs=[history_tutor, math_tutor],
)

async def main() -> None:
    result = await Runner.run(
        triage_agent,
        "Who was the first president of the United States?",
    )
    print(result.final_output)
    print(result.last_agent.name)

if __name__ == "__main__":
    asyncio.run(main())
出自编排与交接指南,2026 年 11 月 5 日阅读。
模式什么时候用谁来写回复
交接某个专职智能体应该接管对话的这一分支专职智能体
智能体作为工具管理者应该一直主导,调用专职智能体完成边界清楚的任务管理者

记住对话,再读懂追踪记录

先问“What city is the Golden Gate Bridge in?”,再问“What state is it in?”,第二个问题只有在记得第一个时才说得通。在下面会话页面的示例里,注释写着文档预期的回答,先是“San Francisco”,然后是“California”。每次调用 Runner.run 都传入同一个 SQLiteSession 对象,SDK 会在每次运行前后读取和保存历史。

会话是 SDK 的记忆层。它把一段对话的输出项按一个 id 存起来,你就不用再手动回放 result.to_input_list()。SQLiteSession("conversation_123") 把它存在内存里,再加第二个参数,也就是 "conversations.db" 这样的文件路径,就会存到磁盘上。对话很长时,OpenAIResponsesCompactionSession 可以包在另一种会话外面,每个回合后压缩保存的历史。它不能包住 OpenAIConversationsSession,因为两者管理历史的方式不同。

会话是保存状态的四种方式之一,运行指南要求每段对话只选一种。另外三种是自己回放历史、Conversations API 的 conversation_id,以及 previous_response_id,都在第 1 课讲过。同一次运行里,会话不能和那些服务端选项一起用,因为混用会让上下文重复。

追踪默认是打开的。每次运行都会记录模型调用、工具调用、交接、护栏,以及你自己加的任何自定义跨度,你可以在 OpenAI 平台的 Traces 控制台里查看。可观测性指南建议,第一次运行跑通后就马上打开追踪记录,然后再去调提示词。

关闭追踪有三种办法。设置环境变量 OPENAI_AGENTS_DISABLE_TRACING=1,在代码里调用 set_tracing_disabled(True),或者在某一次运行的 RunConfig 上设置 tracing_disabled。采用零数据保留政策的组织完全无法使用追踪。如果只是想少记录一些,可观测性指南更推荐用这些 SDK 级或单次运行的开关,而不是把可见性全部去掉。等你开始给行为打分时,追踪记录也会成为智能体评估的原始材料。

from agents import Agent, Runner, SQLiteSession

# Create agent
agent = Agent(
    name="Assistant",
    instructions="Reply very concisely.",
)

# Create a session instance with a session ID
session = SQLiteSession("conversation_123")

# First turn
result = await Runner.run(agent, "What city is the Golden Gate Bridge in?", session=session)
print(result.final_output)  # "San Francisco"

# Second turn - agent automatically remembers previous context
result = await Runner.run(agent, "What state is it in?", session=session)
print(result.final_output)  # "California"

# Also works with synchronous runner
result = Runner.run_sync(agent, "What's the population?", session=session)
print(result.final_output)  # "Approximately 39 million"
选自 Python SDK 的会话页面,2026 年 11 月 5 日阅读。
会话类型适合
SQLiteSession本地开发和简单应用,存在内存或文件里
RedisSession在多个工作进程和服务之间共享记忆
SQLAlchemySession已有数据库的生产应用
OpenAIConversationsSession通过 Conversations API 由 OpenAI 保存历史
EncryptedSession在另一种会话外面加上加密和过期

OpenAI Developers 和 Steve Coffey 谈 Agents SDK

OpenAI Developers 在 2025-03-11 在 X 上介绍了 Agents SDK:一个用来编排多智能体工作流的开源 SDK,是对 Swarm 的改进。帖子点名的几样东西,正是本课用到的:内置工具、交接、安全护栏,以及用来调试的执行追踪。这四样至今仍是 SDK 的核心,所以先把它们学会,再去碰更新的功能。

Steve Coffey 在 OpenAI 做 API,他在 2026-04-15 发帖介绍了一次很大的更新。照他的说法,有了这次更新,你不用自己搭整套运行框架,也能在生产环境里扩展 Codex 式的智能体。计算机操作、技能、记忆和压缩也都一起加了进来。如果你的智能体要长时间运行或需要沙箱,自己写运行框架之前,先看看这次更新带来了什么。

给智能体配置内置工具、交接任务、加上安全护栏,并把执行追踪可视化,用来调试和优化性能。

OpenAI Developers, OpenAI 面向开发者的官方账号,引文为译文 · X (2026年11月5日 查阅)
OpenAI Developers(@OpenAIDevs)2025 年 3 月 11 日在 X 上发帖:Agents SDK,我们新的开源 SDK,用来编排多智能体工作流,是对 Swarm 的改进。可以给智能体配置内置工具、交接任务、加上安全护栏,并把执行追踪可视化,用来调试和优化。
OpenAI Developers 在 X 上,2025 年 3 月 11 日
Steve Coffey(@stevendcoffey)2026 年 4 月 15 日在 X 上发帖:今天我们给 OpenAI Agents SDK 推出一次相当大的更新。有了 Agents SDK,你不用自己搭整套运行框架,也能在生产环境里扩展 Codex 式的智能体。计算机操作、技能、记忆、压缩等现代智能体的能力,都加到了你已经在用的平台上。
Steve Coffey 在 X 上,2026 年 4 月 15 日
OpenAI 自己的 YouTube 频道上,Build Hour 系列讲 Agents SDK 的一期。

X 官方嵌入卡片的截图,拍摄于 2026-11-05,时间为 UTC。点击截图可到 X 上打开原帖。X 用 Show more 截断了 Steve Coffey 的帖子。

常见错误

  • 一个智能体还没答好一个问题,就先设计了五个智能体。
  • 拆出来的专职智能体,用的工具和指令却完全一样。
  • 本该由管理者继续写回复的地方,用了交接。
  • 代价高的输入护栏还留在并行模式,为它后来拦下的工作白白付费。
  • 指望第一个智能体上的输入护栏,去检查交接之后发生的调用。
  • 把审批暂停当成新的用户回合,而不是从状态恢复。
  • 在同一次运行里既传了会话,又传了 previous_response_id。
  • 调高 max_turns,来掩盖一个永远得不到最终回答的循环。

自己试一试

  • 运行历史辅导智能体,然后打开它的追踪记录,找到那次模型调用。
  • 加上 history_fun_fact 工具,问一个应该用到它的问题。追踪记录里有这次调用吗?
  • 给分诊智能体一个数学问题,打印 result.last_agent.name。
  • 用 as_tool() 把数学辅导改写成工具,比较一下最终回答是谁写的。
  • 在一个需要工具的运行上设置 max_turns=1,捕获 MaxTurnsExceeded。
  • 给 SQLiteSession 加上文件路径,停掉脚本,重新启动,再问一个追问。
  • 用 needs_approval=True 标记一个工具,在代码里批准这次中断,确认运行从它的状态继续。

接下来

这是 OpenAI API 课程的最后一课。RAG 教程是下一门课的开头,它会更深入地讲怎样让模型检索你自己的文档,比第 2 课的托管文件搜索走得更远。

智能体能在你自己的数据里查找信息之后,会更有用。这一课的工具、会话和追踪,都能直接用到那部分工作里。

自测一下

  1. 一次 Python 运行超过了回合上限,默认会怎样?

    查看答案

    D. 运行器抛出 MaxTurnsExceeded 默认上限是 10 个回合,超过就会抛出 MaxTurnsExceeded,除非你设置了错误处理函数。

  2. 哪种模式能让管理者智能体一直负责最终回复?

    查看答案

    B. 智能体作为工具,用 as_tool() 智能体作为工具时,管理者调用专职智能体完成边界清楚的任务,回复由它自己来写。

  3. 一个输入护栏保持默认的 run_in_parallel 设置并触发了,之前可能已经发生了什么?

    查看答案

    C. 智能体用掉了 token 并运行了工具 并行护栏和智能体同时启动,所以在绊线叫停之前,工作可能已经做了。

  4. 不用手动回放,什么能让对话历史在多次 Runner.run 调用之间保留下来?

    查看答案

    A. 把同一个 SQLiteSession 作为 session 传入 会话会在每次运行前后读取和保存对话的输出项。

常见问题

Agents SDK 能用其他厂商的模型吗?

能。Python SDK 的 README 说它与厂商无关:它支持 OpenAI 的 Responses 和 Chat Completions 接口,以及 100 多种其他模型,并提供 any-llm 和 LiteLLM 等集成。厂商的配置方式因语言而异,模型指南让你去看各语言 SDK 自己的文档。

Agents SDK 有 TypeScript 版本吗?

有,就是 @openai/agents,放在 openai-agents-js 仓库里。名字遵循 TypeScript 风格:用 run() 代替 Runner.run,还有 finalOutput、lastAgent、handoffDescription、outputType 和 asTool()。函数工具用 tool() 加 Zod 参数来写,快速入门用 Agent.create 搭建路由智能体。

追踪会记录我的用户数据吗?

可能会。生成跨度会保存模型的输入和输出,函数跨度会保存工具的输入和输出。如果这些数据敏感,就在 RunConfig 上把 trace_include_sensitive_data 设为 false,这样跨度还在,但不带内容。

怎样把数据库客户端交给工具,又不让模型看到它?

把它作为运行上下文传进去。Runner.run 接受一个 context 参数,工具和护栏通过 RunContextWrapper 拿到它,这样数据库客户端、日志器或已登录的用户能到达你的代码,却从不进入对话。定义指南把界线划得很清楚:模型需要的事实,放进指令、输入或工具里,只有运行环境需要的,就留在本地上下文里。

资料来源

  1. OpenAI Docs: Agents (2026年11月5日 查阅)https://developers.openai.com/api/docs/guides/agents
  2. OpenAI Docs: Agents SDK (2026年11月5日 查阅)https://developers.openai.com/api/docs/guides/agents/sdk
  3. OpenAI Docs: Agents SDK quickstart (2026年11月5日 查阅)https://developers.openai.com/api/docs/guides/agents/quickstart
  4. OpenAI Docs: Agent definitions (2026年11月5日 查阅)https://developers.openai.com/api/docs/guides/agents/define-agents
  5. OpenAI Docs: Agents SDK models and providers (2026年11月5日 查阅)https://developers.openai.com/api/docs/guides/agents/models
  6. OpenAI Docs: Running agents (2026年11月5日 查阅)https://developers.openai.com/api/docs/guides/agents/running-agents
  7. OpenAI Docs: Orchestration and handoffs (2026年11月5日 查阅)https://developers.openai.com/api/docs/guides/agents/orchestration
  8. OpenAI Docs: Guardrails and human review (2026年11月5日 查阅)https://developers.openai.com/api/docs/guides/agents/guardrails-approvals
  9. OpenAI Docs: Integrations and observability (2026年11月5日 查阅)https://developers.openai.com/api/docs/guides/agents/integrations-observability
  10. OpenAI Agents SDK (Python): Running agents (2026年11月5日 查阅)https://openai.github.io/openai-agents-python/running_agents/
  11. OpenAI Agents SDK (Python): Sessions (2026年11月5日 查阅)https://openai.github.io/openai-agents-python/sessions/
  12. OpenAI Agents SDK (Python): Tracing (2026年11月5日 查阅)https://openai.github.io/openai-agents-python/tracing/
  13. OpenAI Agents SDK (Python): Guardrails (2026年11月5日 查阅)https://openai.github.io/openai-agents-python/guardrails/
  14. OpenAI Agents SDK (Python): Handoffs (2026年11月5日 查阅)https://openai.github.io/openai-agents-python/handoffs/
  15. OpenAI Agents SDK (Python): Tools (2026年11月5日 查阅)https://openai.github.io/openai-agents-python/tools/
  16. openai/openai-agents-python on GitHub (2026年11月5日 查阅)https://github.com/openai/openai-agents-python
  17. openai/openai-agents-js on GitHub (2026年11月5日 查阅)https://github.com/openai/openai-agents-js
  18. OpenAI Docs: Changelog (2026年11月5日 查阅)https://developers.openai.com/api/docs/changelog
  19. X: OpenAI Developers introduce the Agents SDK (2026年11月5日 查阅)https://x.com/OpenAIDevs/status/1899531857143972051
  20. X: Steve Coffey on the April 2026 Agents SDK update (2026年11月5日 查阅)https://x.com/stevendcoffey/status/2044465818239701041
  21. YouTube (OpenAI): Build Hour: Agents SDK (2026年11月5日 查阅)https://www.youtube.com/watch?v=tK32trvj_b4

分享本节课

看看其他开发者做的智能体

在 Mindket 浏览已上架的 AI 智能体,读读每个是怎样设置的,再把你用 SDK 做的智能体也上架。

浏览 AI 智能体

本节课的 Markdown 版本 · OpenAI API 实战课:Responses、工具调用、结构化输出与智能体 · 全部课程