fix(agent): close length recovery lifecycle gaps

This commit is contained in:
chengyongru
2026-07-27 01:39:46 +08:00
committed by Xubin Ren
parent 27a00c7a4f
commit e6baecafcd
7 changed files with 195 additions and 7 deletions
+34
View File
@@ -482,6 +482,40 @@ async def test_runner_length_recovery_returns_all_segments():
assert provider.chat_with_retry.await_count == 3
@pytest.mark.asyncio
async def test_runner_length_recovery_preserves_prefix_at_max_iterations():
"""Budget exhaustion must not replace output already produced by recovery."""
from nanobot.agent.runner import AgentRunner
provider = MagicMock(spec=LLMProvider)
provider.chat_with_retry = AsyncMock(
return_value=LLMResponse(content="partial answer", finish_reason="length")
)
tools = MagicMock()
tools.get_definitions.return_value = []
runner = AgentRunner()
result = await runner.run(make_run_spec(
provider,
initial_messages=[{"role": "user", "content": "give a long answer"}],
tools=tools,
model="test-model",
max_iterations=1,
max_tool_result_chars=_MAX_TOOL_RESULT_CHARS,
finalize_on_max_iterations=False,
max_iterations_message="limit reached",
))
assert result.stop_reason == "max_iterations"
assert result.final_content == "partial answer\n\nlimit reached"
assert result.pending_stream_content == "\n\nlimit reached"
assert [
message["content"]
for message in result.messages
if message.get("role") == "assistant"
] == ["partial answer", "limit reached"]
@pytest.mark.asyncio
async def test_runner_length_recovery_does_not_leak_across_tool_calls():
"""A recovered prefix belongs only to its contiguous response chain."""