fix(core): 用户中断 reasoning 时丢弃未执行的工具调用 - #2471
Conversation
|
Caution The consumer version of Gemini Code Assist on GitHub has been sunset. All code review activity has officially ceased. |
Codecov Report✅ All modified and coverable lines are covered by tests. 📢 Thoughts on this report? Let us know! |
|
Caution The consumer version of Gemini Code Assist on GitHub has been sunset. All code review activity has officially ceased. |
oss-maintainer
left a comment
There was a problem hiding this comment.
Review: PR #2471
fix(core): 用户中断 reasoning 时丢弃未执行的工具调用
Summary
Fixes a correctness issue where user-interrupted reasoning could persist orphaned ToolUseBlock entries into the conversation history, making subsequent model calls fail due to unresolvable tool-use references.
Analysis
Root cause: The reasoning message (including any in-flight ToolUseBlock) was persisted to memory before the acting phase. If a user interrupt arrived during the window between tool-call generation and acting start, the tool call was written to state without a corresponding ToolResultBlock, leaving the conversation in an unrecoverable state.
Fix approach — correct and minimal:
persistInterruptedReasoningMessage()— new method that stripsToolUseBlockentries forUSERinterrupts while preserving text/thinking content.SYSTEMinterrupts retain existingPartialReasoningPolicysemantics (unchanged).- Deferred persistence — moves the
contextMutable().add(eventMsg)call to aftercheckInterrupted()in the pre-acting path, closing the race window. withoutToolUseBlocks()— clean static helper that filters out tool-use blocks; returnsnullif nothing remains (avoiding empty message persistence).
Code quality:
- Clean separation between user and system interrupt handling
- No changes to public API or
PartialReasoningPolicycontract - Proper null handling throughout
toList()(immutable) used correctly
Test coverage (420 lines, 7 scenarios):
- Partial streaming tool call during user interrupt
- Completed tool call before acting during user interrupt
- Text-only reasoning preserved on user interrupt
- Tool-call-only reasoning not persisted as empty message
- System interrupt with
SAVEandDISCARDpolicies gotoReasoningwith non-null and null reasoning messages- Agent rebuild from interrupted state with strict history validation
All 2228 core tests pass. CI is fully green.
Verdict: Approved ✅ — well-scoped fix with thorough test coverage.
7aefec4 to
02b5e71
Compare
02b5e71 to
c00e9f4
Compare
fix: #2470
AgentScope-Java Version
2.0.1-SNAPSHOT
Description
修改概述
修复用户中断 ReActAgent 的 reasoning 阶段时,尚未执行的工具调用被写入 memory,导致后续请求携带孤立
tool_use、会话上下文无法恢复的问题。问题原因
reasoning 产生的消息会在工具执行前写入 memory。用户中断恰好发生在工具调用流式生成期间,或 reasoning 已完成但 acting 尚未开始时,当前实现仍会保留其中的
ToolUseBlock。由于对应工具没有执行,memory 中不会产生配对的工具结果;重建 Agent 或发起下一轮模型请求时,严格校验消息历史的模型会拒绝这段上下文。修复方案
ToolUseBlock。PartialReasoningPolicy的既有语义不变。测试覆盖
PartialReasoningPolicy.SAVE和DISCARD。gotoReasoning时分别处理非空和空 reasoning 消息。agentscope-core测试:2228 tests,0 failures,0 errors,8 skipped。Checklist
Please check the following items before code is ready to be reviewed.
mvn spotless:applymvn -pl agentscope-core test)