上下文¶
代理要有效运行,通常需要的不仅仅是消息列表。它们需要**上下文**。
上下文包括任何在消息列表之外的数据,这些数据可以影响代理的行为或工具执行。这可能包括:
- 运行时传递的信息,如
user_id
或API凭据。 - 在多步推理过程中更新的内部状态。
- 来自先前交互的持久记忆或事实。
LangGraph提供了**三种**主要方式来提供上下文:
类型 | 描述 | 可变性? | 生命周期 |
---|---|---|---|
配置 | 在运行开始时传递的数据 | ❌ | 每次运行 |
状态 | 在执行期间可以更改的动态数据 | ✅ | 每次运行或对话 |
长期记忆(存储) | 可在不同对话间共享的数据 | ✅ | 跨多个对话 |
您可以使用上下文来:
- 调整模型看到的系统提示
- 为工具提供必要的输入
- 在正在进行的对话中跟踪事实
提供运行时上下文¶
当您需要在运行时向代理注入数据时,请使用此功能。
配置(静态上下文)¶
配置用于不可变的数据,如用户元数据或API密钥。当您有那些在运行过程中不会改变的值时,请使用配置。
通过一个名为**"configurable"**的键来指定配置,该键专为此目的保留:
agent.invoke(
{"messages": [{"role": "user", "content": "hi!"}]},
# 下一行高亮
config={"configurable": {"user_id": "user_123"}}
)
状态(可变上下文)¶
状态充当运行期间的短期记忆。它保存动态数据,这些数据可以在执行过程中演变,例如从工具或LLM输出中得出的值。
class CustomState(AgentState):
# 下一行高亮
user_name: str
agent = create_react_agent(
# 其他代理参数...
# 下一行高亮
state_schema=CustomState,
)
agent.invoke({
"messages": "hi!",
"user_name": "Jane"
})
启用记忆
有关如何启用记忆的更多细节,请参阅记忆指南。这是一个强大的功能,允许您在多次调用之间持久化代理的状态。 否则,状态仅限于单个代理运行的范围。
长期记忆(跨会话上下文)¶
对于跨越多个对话或会话的上下文,LangGraph允许通过store
访问**长期记忆**。这可以用来读取或更新持久化的事实(例如,用户资料、偏好、先前的交互)。更多信息请参阅记忆指南。
使用上下文自定义提示¶
提示定义了代理的行为方式。为了在运行时纳入上下文信息,您可以根据代理的状态或配置动态生成提示。
常见用例:
- 个性化
- 角色或目标定制
- 条件行为(例如,用户是管理员)
from langchain_core.messages import AnyMessage
from langchain_core.runnables import RunnableConfig
from langgraph.prebuilt import create_react_agent
from langgraph.prebuilt.chat_agent_executor import AgentState
def prompt(
state: AgentState,
# 高亮下一行
config: RunnableConfig,
) -> list[AnyMessage]:
# 高亮下一行
user_name = config.get("configurable", {}).get("user_name")
system_msg = f"您是一位乐于助人的助手。用户的姓名是 {user_name}"
return [{"role": "system", "content": system_msg}] + state["messages"]
agent = create_react_agent(
model="anthropic:claude-3-7-sonnet-latest",
tools=[get_weather],
# 高亮下一行
prompt=prompt
)
agent.invoke(
...,
# 高亮下一行
config={"configurable": {"user_name": "John Smith"}}
)
from langchain_core.messages import AnyMessage
from langchain_core.runnables import RunnableConfig
from langgraph.prebuilt import create_react_agent
from langgraph.prebuilt.chat_agent_executor import AgentState
class CustomState(AgentState):
# 高亮下一行
user_name: str
def prompt(
# 高亮下一行
state: CustomState
) -> list[AnyMessage]:
# 高亮下一行
user_name = state["user_name"]
system_msg = f"您是一位乐于助人的助手。用户的姓名是 {user_name}"
return [{"role": "system", "content": system_msg}] + state["messages"]
agent = create_react_agent(
model="anthropic:claude-3-7-sonnet-latest",
tools=[...],
# 高亮下一行
state_schema=CustomState,
# 高亮下一行
prompt=prompt
)
agent.invoke({
"messages": "hi!",
# 高亮下一行
"user_name": "John Smith"
})
工具¶
工具可以通过特殊的参数**注解**访问上下文。
- 使用
RunnableConfig
访问配置 - 使用
Annotated[StateSchema, InjectedState]
访问代理状态
提示
这些注解可以防止LLM尝试填充这些值。这些参数将被**隐藏**,不会显示给LLM。
def get_user_info(
# 高亮下一行
config: RunnableConfig,
) -> str:
"""查找用户信息。"""
# 高亮下一行
user_id = config.get("configurable", {}).get("user_id")
return "User is John Smith" if user_id == "user_123" else "Unknown user"
agent = create_react_agent(
model="anthropic:claude-3-7-sonnet-latest",
tools=[get_user_info],
)
agent.invoke(
{"messages": [{"role": "user", "content": "look up user information"}]},
# 高亮下一行
config={"configurable": {"user_id": "user_123"}}
)
from typing import Annotated
from langgraph.prebuilt import InjectedState
class CustomState(AgentState):
# 高亮下一行
user_id: str
def get_user_info(
# 高亮下一行
state: Annotated[CustomState, InjectedState]
) -> str:
"""查找用户信息。"""
# 高亮下一行
user_id = state["user_id"]
return "User is John Smith" if user_id == "user_123" else "Unknown user"
agent = create_react_agent(
model="anthropic:claude-3-7-sonnet-latest",
tools=[get_user_info],
# 高亮下一行
state_schema=CustomState,
)
agent.invoke({
"messages": "look up user information",
# 高亮下一行
"user_id": "user_123"
})
工具更新上下文¶
工具可以在执行过程中修改代理的状态。这有助于持久化中间结果或将信息提供给后续工具或提示。
API Reference: InjectedToolCallId | ToolMessage | InjectedState | Command
from typing import Annotated
from langchain_core.tools import InjectedToolCallId
from langchain_core.messages import ToolMessage
from langgraph.prebuilt import InjectedState
from langgraph.types import Command
class CustomState(AgentState):
# 高亮下一行
user_name: str
def get_user_info(
# 高亮下一行
tool_call_id: Annotated[str, InjectedToolCallId],
# 高亮下一行
config: RunnableConfig
) -> Command:
"""查询用户信息。"""
# 高亮下一行
user_id = config.get("configurable", {}).get("user_id")
name = "John Smith" if user_id == "user_123" else "Unknown user"
return Command(update={
# 高亮下一行
"user_name": name,
# 更新消息历史记录
# 高亮下一行
"messages": [
ToolMessage(
"成功查询到用户信息",
# 高亮下一行
tool_call_id=tool_call_id
)
]
})
def greet(
# 高亮下一行
state: Annotated[CustomState, InjectedState]
) -> str:
"""使用此函数在找到用户信息后向其打招呼。"""
user_name = state["user_name"]
return f"Hello {user_name}!"
agent = create_react_agent(
model="anthropic:claude-3-7-sonnet-latest",
tools=[get_user_info, greet],
# 高亮下一行
state_schema=CustomState
)
agent.invoke(
{"messages": [{"role": "user", "content": "greet the user"}]},
# 高亮下一行
config={"configurable": {"user_id": "user_123"}}
)
更多详情,请参阅如何从工具更新状态。