Skip to content

Commit c8c2bf4

Browse files
committed
update
1 parent 8bac13e commit c8c2bf4

File tree

3 files changed

+85
-21
lines changed

3 files changed

+85
-21
lines changed
Lines changed: 57 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,57 @@
1+
# :snippet-start: tool-update-state-py
2+
from langchain.agents import AgentState
3+
from langchain.messages import ToolMessage
4+
from langchain.tools import ToolRuntime, tool
5+
from langgraph.types import Command
6+
7+
8+
class CustomState(AgentState):
9+
user_name: str
10+
11+
12+
@tool
13+
def set_user_name(new_name: str, runtime: ToolRuntime[None, CustomState]) -> Command:
14+
"""Set the user's name in the conversation state."""
15+
return Command(
16+
update={
17+
"user_name": new_name,
18+
"messages": [
19+
ToolMessage(
20+
content=f"User name set to {new_name}.",
21+
tool_call_id=runtime.tool_call_id,
22+
)
23+
],
24+
}
25+
)
26+
27+
28+
# :snippet-end:
29+
30+
# :remove-start:
31+
if __name__ == "__main__":
32+
from langchain.agents import create_agent
33+
from langchain_anthropic import ChatAnthropic
34+
35+
model = ChatAnthropic(model_name="claude-sonnet-4-6", timeout=None)
36+
37+
agent = create_agent(
38+
model,
39+
tools=[set_user_name],
40+
state_schema=CustomState,
41+
system_prompt=(
42+
"You are a test harness. Always call the `set_user_name` tool when asked to "
43+
"set the user's name. Reply with a brief confirmation."
44+
),
45+
)
46+
result = agent.invoke(
47+
{"messages": [{"role": "user", "content": "Set my name to Alice."}]}
48+
)
49+
50+
assert result["user_name"] == "Alice"
51+
tool_messages = [m for m in result["messages"] if isinstance(m, ToolMessage)]
52+
assert len(tool_messages) == 1
53+
assert tool_messages[0].content == "User name set to Alice."
54+
assert tool_messages[0].tool_call_id, "expected tool_call_id to be set"
55+
56+
print("✓ Tool works as expected")
57+
# :remove-end:

src/oss/langchain/tools.mdx

Lines changed: 2 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ import ToolReturnObjectPy from '/snippets/code-samples/tool-return-object-py.mdx
88
import ToolReturnObjectJs from '/snippets/code-samples/tool-return-object-js.mdx';
99
import ToolReturnCommandPy from '/snippets/code-samples/tool-return-command-py.mdx';
1010
import ToolReturnCommandJs from '/snippets/code-samples/tool-return-command-js.mdx';
11+
import ToolUpdateStatePy from '/snippets/code-samples/tool-update-state-py.mdx';
1112

1213
Tools extend what [agents](/oss/langchain/agents) can do—letting them fetch real-time data, execute code, query external databases, and take actions in the world.
1314

@@ -279,27 +280,7 @@ def get_user_preference(
279280
Use @[`Command`] to update the agent's state. This is useful for tools that need to update custom state fields.
280281
Include a `ToolMessage` in the update so the model can see the result of the tool call:
281282

282-
```python
283-
from langchain.messages import ToolMessage
284-
from langchain.tools import ToolRuntime, tool
285-
from langgraph.types import Command
286-
287-
288-
@tool
289-
def set_user_name(new_name: str, runtime: ToolRuntime) -> Command:
290-
"""Set the user's name in the conversation state."""
291-
return Command(
292-
update={
293-
"user_name": new_name,
294-
"messages": [
295-
ToolMessage(
296-
content=f"User name set to {new_name}.",
297-
tool_call_id=runtime.tool_call_id,
298-
)
299-
],
300-
}
301-
)
302-
```
283+
<ToolUpdateStatePy />
303284

304285
<Tip>
305286
When tools update state variables, consider defining a [reducer](/oss/langgraph/graph-api#reducers) for those fields. Since LLMs can call multiple tools in parallel, a reducer determines how to resolve conflicts when the same state field is updated by concurrent tool calls.
Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
```python
2+
from langchain.agents import AgentState
3+
from langchain.messages import ToolMessage
4+
from langchain.tools import ToolRuntime, tool
5+
from langgraph.types import Command
6+
7+
8+
class CustomState(AgentState):
9+
user_name: str
10+
11+
12+
@tool
13+
def set_user_name(new_name: str, runtime: ToolRuntime[None, CustomState]) -> Command:
14+
"""Set the user's name in the conversation state."""
15+
return Command(
16+
update={
17+
"user_name": new_name,
18+
"messages": [
19+
ToolMessage(
20+
content=f"User name set to {new_name}.",
21+
tool_call_id=runtime.tool_call_id,
22+
)
23+
],
24+
}
25+
)
26+
```

0 commit comments

Comments
 (0)