fix(agent): add return_exceptions=True to asyncio.gather in context reference expansion - #59954
fix(agent): add return_exceptions=True to asyncio.gather in context reference expansion#59954x7peeps wants to merge 3 commits into
Conversation
teknium1
left a comment
There was a problem hiding this comment.
Thanks for isolating the context-reference gather path. Current main still has the unguarded gather at agent/context_references.py:161, so the focused hunk remains relevant.
Problems
agent/moa_loop.py:384only times outFuture.result(). The surroundingThreadPoolExecutorcontext (agent/moa_loop.py:407) still owns unfinished workers at scope exit, so a hung reference can still block return.tools/voice_mode.py:1109can raise a secondTimeoutExpiredinside the first timeout handler. That skips the cleanup at lines 1110-1111 and can leave_active_playbackset.- No test file is included. Add a context-reference regression with one escaping child failure and one successful sibling; the existing concurrency tests only cover successful fetches.
Suggested changes
- Keep this PR focused on
agent/context_references.py(or split the independent MoA and voice fixes), then add the regression test. - Rework the MoA and voice timeout handling with explicit cleanup and tests before proposing them separately.
Automated hermes-sweeper review.
| for future, idx in futures.items(): | ||
| results[idx] = future.result() | ||
| try: | ||
| results[idx] = future.result(timeout=300) |
There was a problem hiding this comment.
This does not bound the time until _run_references_parallel returns: timing out future.result() leaves the worker running, and the surrounding executor context still waits as it exits. Use a design that can return without waiting for timed-out workers, or split this unrelated change.
| logger.warning("System player %s timed out, killing process", cmd[0]) | ||
| proc.kill() | ||
| proc.wait() | ||
| proc.wait(timeout=10) |
There was a problem hiding this comment.
proc.wait(timeout=10) can itself raise TimeoutExpired inside this handler; the following except Exception will not catch it, and _active_playback is not cleared. Handle the second timeout and perform cleanup in finally.
Summary
Added to in to prevent a single failing reference expansion from crashing the entire agent turn.
Problem
concurrently expands multiple context references via without . If any single call raises an exception (e.g. network failure for , permission error for ), the gather immediately propagates the exception, causing:
Fix
Testing