Messages
Abstract
在 LangChain 中,Message 是模型上下文的基本单位。无论是直接调用 Chat Model,还是在 Agent 中维护对话状态,本质上都是在组织一组 messages。每条 message 通常包含三类信息:角色、内容和元数据。
- Role:表示消息来源或类型,例如
system、user、assistant、tool。 - Content:消息正文,可以是文本,也可以是图片、音频、文件等多模态内容。
- Metadata:额外信息,例如 message id、token usage、response metadata、tool call id 等。
LangChain 提供统一的 message 类型,让不同模型 provider 之间能尽量使用一致的消息表示。
基本使用
最简单的方式是创建 message 对象,然后传给模型:
from langchain.chat_models import init_chat_model
from langchain.messages import HumanMessage, SystemMessage
model = init_chat_model("gpt-5-nano")
messages = [
SystemMessage("You are a helpful assistant."),
HumanMessage("Hello, how are you?"),
]
response = model.invoke(messages)
如果只是一次性的简单请求,也可以直接传字符串。字符串可以理解为单条 HumanMessage 的快捷写法:
response = model.invoke("Write a haiku about spring")
对于多轮对话、系统指令、多模态内容或工具调用,建议显式使用 message 列表:
from langchain.messages import SystemMessage, HumanMessage, AIMessage
messages = [
SystemMessage("You are a poetry expert."),
HumanMessage("Write a haiku about spring."),
AIMessage("Cherry blossoms bloom..."),
HumanMessage("Make it shorter."),
]
response = model.invoke(messages)
也可以使用 OpenAI chat completions 风格的字典格式:
messages = [
{"role": "system", "content": "You are a poetry expert."},
{"role": "user", "content": "Write a haiku about spring."},
{"role": "assistant", "content": "Cherry blossoms bloom..."},
]
response = model.invoke(messages)
Message 类型
SystemMessage
SystemMessage 用来设定模型行为,例如角色、语气、任务边界和回答规则。它通常放在消息列表开头。
from langchain.messages import SystemMessage, HumanMessage
messages = [
SystemMessage("You are a senior Python developer. Be concise and practical."),
HumanMessage("How do I create a REST API?"),
]
response = model.invoke(messages)
System message 适合放稳定的全局指令,不适合塞入频繁变化的大量业务数据。长上下文或动态上下文更适合通过检索、memory 或 middleware 管理。
HumanMessage
HumanMessage 表示用户输入。它可以包含普通文本,也可以包含多模态内容。
from langchain.messages import HumanMessage
response = model.invoke([
HumanMessage("What is machine learning?")
])
HumanMessage 也可以带元数据:
human_msg = HumanMessage(
content="Hello!",
name="alice",
id="msg_123",
)
name 字段在不同 provider 中行为不完全一致,有些会使用它区分用户,有些会忽略。
AIMessage
AIMessage 表示模型输出。调用 chat model 后通常会得到一个 AIMessage,其中可能包含文本、工具调用、token 统计和 provider 返回的元数据。
response = model.invoke("Explain AI in one sentence.")
print(response.text)
print(response.usage_metadata)
print(response.response_metadata)
在维护对话历史时,也可以手动创建 AIMessage,把它作为历史上下文的一部分:
from langchain.messages import AIMessage, HumanMessage, SystemMessage
messages = [
SystemMessage("You are a helpful assistant."),
HumanMessage("Can you help me?"),
AIMessage("Yes, what would you like to do?"),
HumanMessage("What's 2 + 2?"),
]
response = model.invoke(messages)
AIMessage 常见字段:
text:标准文本内容。content:原始内容,可能是字符串或 provider-native content blocks。content_blocks:LangChain 标准化后的内容块。tool_calls:模型请求调用的工具列表。usage_metadata:token 使用量等统计信息。response_metadata:provider 返回的额外响应信息。
ToolMessage
当模型发起 tool call 后,工具执行结果需要通过 ToolMessage 返回给模型。ToolMessage 的 tool_call_id 必须和原始 tool call 的 id 匹配,这样模型才能知道结果对应哪次工具调用。
from langchain.messages import AIMessage, HumanMessage, ToolMessage
ai_message = AIMessage(
content=[],
tool_calls=[
{
"name": "get_weather",
"args": {"location": "San Francisco"},
"id": "call_123",
}
],
)
tool_message = ToolMessage(
content="Sunny, 72°F",
tool_call_id="call_123",
name="get_weather",
)
messages = [
HumanMessage("What's the weather in San Francisco?"),
ai_message,
tool_message,
]
response = model.invoke(messages)
如果使用 Agent,工具执行循环通常由 Agent 自动管理;如果单独使用 Model,就需要自己执行工具并维护 AIMessage / ToolMessage 的往返。
ToolMessage 还可以包含 artifact,用于保存不发送给模型但程序后续需要使用的附加数据,例如检索到的文档 id、页码、原始 JSON 等。
Message Content
Message 的 content 是实际发送给模型的 payload。它可以是:
- 普通字符串。
- provider 原生格式的 content blocks。
- LangChain 标准 content blocks。
from langchain.messages import HumanMessage
text_message = HumanMessage("Hello, how are you?")
image_message = HumanMessage(content_blocks=[
{"type": "text", "text": "Describe this image."},
{"type": "image", "url": "https://example.com/image.jpg"},
])
content_blocks 是 LangChain v1 引入的标准化表示,用来统一不同 provider 的内容格式。它不是替代 content,而是提供更类型化、更跨 provider 的访问方式。
常见 content block 类型:
text:普通文本。reasoning:模型推理内容或推理摘要。image:图片输入或输出。audio:音频输入或输出。video:视频输入或输出。file:文件,例如 PDF。tool_call:工具调用请求。tool_call_chunk:流式工具调用片段。server_tool_call:由 provider 服务端执行的工具调用。server_tool_result:服务端工具执行结果。non_standard:provider 特有的扩展内容。
多模态消息
支持多模态的模型可以接收图片、音频、视频或文件。LangChain 使用标准 content blocks 描述这些内容。
message = {
"role": "user",
"content": [
{"type": "text", "text": "Describe the content of this image."},
{"type": "image", "url": "https://example.com/path/to/image.jpg"},
],
}
response = model.invoke([message])
也可以使用 base64 或 provider-managed file id:
message = {
"role": "user",
"content": [
{"type": "text", "text": "Summarize this PDF."},
{
"type": "file",
"base64": "AAAAIGZ0eXBtcDQy...",
"mime_type": "application/pdf",
},
],
}
不是所有模型都支持所有文件类型。实际使用前要确认 provider 的模型能力、文件大小限制和 MIME type 要求。
Streaming 与 Chunks
使用 stream 时,模型不会一次性返回完整 AIMessage,而是返回多个 AIMessageChunk。这些 chunk 可以逐步展示,也可以累加成完整消息。
full_message = None
for chunk in model.stream("Explain LangChain messages."):
print(chunk.text, end="", flush=True)
full_message = chunk if full_message is None else full_message + chunk
工具调用在流式输出中也可能以 tool_call_chunk 的形式逐步出现,因此消费端需要能处理“未完成的 JSON 参数”或等待 chunk 聚合完成。
与 Chat Model 和 Agent 的关系
Chat Model 接收一组 messages,返回一个 AIMessage。如果应用需要维护上下文,就把新的 user message、AI response、tool message 继续追加到消息列表中。
Agent 也是围绕 messages 工作:用户输入、模型决策、工具调用、工具结果、最终回答都会进入 message state。理解 messages 的结构,有助于理解 Agent 为什么能在多轮工具调用中保持上下文。
小结
Messages 是 LangChain 中承载上下文的核心结构。SystemMessage 定义行为,HumanMessage 表示用户输入,AIMessage 表示模型输出,ToolMessage 连接工具执行结果。对于真实应用,消息管理不仅是“把聊天记录传给模型”,还包括多模态内容、工具调用、token 使用、流式 chunk、元数据和上下文窗口控制。