核心抽象与 Agent 循环
LangChain 1.0 的核心抽象只有几个:ChatModels、Messages、Tools,加上 create_agent 把三者转成循环。面试主线:抽象怎么设计、循环怎么转、怎么插桩。
三大抽象
| 抽象 | 作用 | 关键点 |
|---|---|---|
| ChatModels | 模型统一接口 | bind_tools 声明工具、with_structured_output 结构化输出 |
| Messages | 对话消息类型 | HumanMessage / AIMessage / ToolMessage / SystemMessage |
| Tools | 模型可调用的能力 | @tool 装饰器、BaseTool、描述即契约 |
from langchain.chat_models import init_chat_model
from langchain.tools import tool
@tool
def get_weather(city: str) -> str:
"""查询城市天气"""
return f"{city}: 晴 25°C"
model = init_chat_model("openai:gpt-4o")
model_with_tools = model.bind_tools([get_weather])ChatModels 的意义:换模型不换代码(init_chat_model 按字符串初始化),工具调用协议由框架统一处理(OpenAI/Anthropic 的工具格式差异被抹平)。
Messages:对话的唯一载体
- HumanMessage:用户输入
- AIMessage:模型输出,可能带
tool_calls(请求调用工具) - ToolMessage:工具执行结果,必须关联 tool_call_id
- SystemMessage:系统提示词
Agent 循环里的消息序列就是状态本身:把完整消息列表喂回模型,模型看到工具结果后决定下一步。
create_agent:最小 harness
Agent 循环: 模型请求工具 → 执行 → 回填, 直到模型直接回答
from langchain.agents import create_agent
agent = create_agent(
model=model,
tools=[get_weather],
system_prompt="你是天气助手。",
)
result = agent.invoke({"messages": "北京天气?"})- create_agent 是 LangChain 1.0 的标准入口,内置“模型→工具→回填”循环
- 循环终止条件:模型输出不再包含 tool_calls
- Agent = Model + Harness:模型可换,harness(循环逻辑)固定
middleware 钩子:循环的插桩点
create_agent 支持 middleware 列表,在循环的关键点挂钩子:
def log_tool_calls(agent, middleware_inputs, **kwargs):
print("工具调用:", middleware_inputs["tool_calls"])
return {"middleware_outputs": {"status": "ok"}}
agent = create_agent(
model=model, tools=[...],
middleware=[log_tool_calls],
)常用钩子:before_model(模型调用前)、after_model(模型输出后)、on_tool_start/on_tool_end(工具执行前后)、on_llm_start/on_llm_end(LLM 事件)。
middleware 的价值:不改循环代码就能插观测、限流、日志、注入(类似 Web 框架的中间件思想,见设计模式篇的中间件与责任链)。
面试追问
- create_agent 的循环是什么? 模型输出 tool_calls → 执行工具 → 结果作为 ToolMessage 回填 → 再调模型,直到模型直接回答
- ChatModels 抽象的价值? 统一模型接口:bind_tools 声明工具、换模型不换代码。工具调用协议差异被抹平
- 三种 Message 的关系? Human 输入、AI 输出(可带 tool_calls)、Tool 执行结果(关联 tool_call_id)。消息序列即 agent 状态
- middleware 钩子干什么? 在循环关键点(模型前后、工具前后)插桩:日志、限流、观测,不改循环代码
- Agent = Model + Harness 什么意思? 模型负责决策,harness 负责循环、工具执行、消息管理。换模型不改 harness