Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 4 additions & 5 deletions agentrun/integration/langgraph/agent_converter.py
Original file line number Diff line number Diff line change
Expand Up @@ -925,17 +925,16 @@ def _convert_astream_events_event(
else:
error_message = str(error)

# 发送 ERROR 事件
# 发送 TOOL_RESULT 事件,避免把工具失败升级成 run error
yield AgentResult(
event=EventType.ERROR,
event=EventType.TOOL_RESULT,
data={
"message": (
"id": tool_call_id,
"result": (
Comment on lines 929 to +933
f"Tool '{tool_name}' error: {error_message}"
if tool_name
else error_message
),
"code": "TOOL_ERROR",
"tool_call_id": tool_call_id,
},
)

Expand Down
23 changes: 12 additions & 11 deletions tests/unittests/integration/test_langgraph_events.py
Original file line number Diff line number Diff line change
Expand Up @@ -746,7 +746,7 @@ def test_on_tool_error(self):
"""测试 on_tool_error 事件

输入: on_tool_error with error
输出: ERROR 事件
输出: TOOL_RESULT 事件
"""
event = {
"event": "on_tool_error",
Expand All @@ -761,11 +761,10 @@ def test_on_tool_error(self):
results = list(AgentRunConverter().to_agui_events(event))

assert len(results) == 1
assert results[0].event == EventType.ERROR
assert "weather_tool" in results[0].data["message"]
assert "ValueError" in results[0].data["message"]
assert results[0].data["code"] == "TOOL_ERROR"
assert results[0].data["tool_call_id"] == "run_123"
assert results[0].event == EventType.TOOL_RESULT
assert "weather_tool" in results[0].data["result"]
assert "ValueError" in results[0].data["result"]
assert results[0].data["id"] == "run_123"

def test_on_tool_error_with_runtime_tool_call_id(self):
"""测试 on_tool_error 使用 runtime 中的 tool_call_id"""
Expand All @@ -786,7 +785,8 @@ class FakeRuntime:
results = list(AgentRunConverter().to_agui_events(event))

assert len(results) == 1
assert results[0].data["tool_call_id"] == "call_original_id"
assert results[0].event == EventType.TOOL_RESULT
assert results[0].data["id"] == "call_original_id"

def test_on_tool_error_with_string_error(self):
"""测试 on_tool_error 使用字符串错误"""
Expand All @@ -803,7 +803,8 @@ def test_on_tool_error_with_string_error(self):
results = list(AgentRunConverter().to_agui_events(event))

assert len(results) == 1
assert "Division by zero" in results[0].data["message"]
assert results[0].event == EventType.TOOL_RESULT
assert "Division by zero" in results[0].data["result"]

def test_on_llm_error(self):
"""测试 on_llm_error 事件
Expand Down Expand Up @@ -878,7 +879,7 @@ def test_tool_error_in_complete_flow(self):

流程:
1. on_tool_start (TOOL_CALL_CHUNK)
2. on_tool_error (ERROR)
2. on_tool_error (TOOL_RESULT)
"""
events = [
{
Expand All @@ -903,9 +904,9 @@ def test_tool_error_in_complete_flow(self):
chunk_events = filter_agent_events(
all_results, EventType.TOOL_CALL_CHUNK
)
error_events = filter_agent_events(all_results, EventType.ERROR)
error_events = filter_agent_events(all_results, EventType.TOOL_RESULT)

assert len(chunk_events) == 1
assert len(error_events) == 1
assert chunk_events[0].data["id"] == "run_risky"
assert error_events[0].data["tool_call_id"] == "run_risky"
assert error_events[0].data["id"] == "run_risky"
23 changes: 12 additions & 11 deletions tests/unittests/integration/test_langgraph_to_agent_event.py
Original file line number Diff line number Diff line change
Expand Up @@ -744,7 +744,7 @@ def test_on_tool_error(self):
"""测试 on_tool_error 事件

输入: on_tool_error with error
输出: ERROR 事件
输出: TOOL_RESULT 事件
"""
event = {
"event": "on_tool_error",
Expand All @@ -759,11 +759,10 @@ def test_on_tool_error(self):
results = list(AgentRunConverter().to_agui_events(event))

assert len(results) == 1
assert results[0].event == EventType.ERROR
assert "weather_tool" in results[0].data["message"]
assert "ValueError" in results[0].data["message"]
assert results[0].data["code"] == "TOOL_ERROR"
assert results[0].data["tool_call_id"] == "run_123"
assert results[0].event == EventType.TOOL_RESULT
assert "weather_tool" in results[0].data["result"]
assert "ValueError" in results[0].data["result"]
assert results[0].data["id"] == "run_123"

def test_on_tool_error_with_runtime_tool_call_id(self):
"""测试 on_tool_error 使用 runtime 中的 tool_call_id"""
Expand All @@ -784,7 +783,8 @@ class FakeRuntime:
results = list(AgentRunConverter().to_agui_events(event))

assert len(results) == 1
assert results[0].data["tool_call_id"] == "call_original_id"
assert results[0].event == EventType.TOOL_RESULT
assert results[0].data["id"] == "call_original_id"

def test_on_tool_error_with_string_error(self):
"""测试 on_tool_error 使用字符串错误"""
Expand All @@ -801,7 +801,8 @@ def test_on_tool_error_with_string_error(self):
results = list(AgentRunConverter().to_agui_events(event))

assert len(results) == 1
assert "Division by zero" in results[0].data["message"]
assert results[0].event == EventType.TOOL_RESULT
assert "Division by zero" in results[0].data["result"]

def test_on_llm_error(self):
"""测试 on_llm_error 事件
Expand Down Expand Up @@ -876,7 +877,7 @@ def test_tool_error_in_complete_flow(self):

流程:
1. on_tool_start (TOOL_CALL_CHUNK)
2. on_tool_error (ERROR)
2. on_tool_error (TOOL_RESULT)
"""
events = [
{
Expand All @@ -901,9 +902,9 @@ def test_tool_error_in_complete_flow(self):
chunk_events = filter_agent_events(
all_results, EventType.TOOL_CALL_CHUNK
)
error_events = filter_agent_events(all_results, EventType.ERROR)
error_events = filter_agent_events(all_results, EventType.TOOL_RESULT)

assert len(chunk_events) == 1
assert len(error_events) == 1
assert chunk_events[0].data["id"] == "run_risky"
assert error_events[0].data["tool_call_id"] == "run_risky"
assert error_events[0].data["id"] == "run_risky"
Loading