Agent tool background-dispatch becomes permanently unresumable after a session/context rollover, despite transcript existing on disk
Summary
When the Agent tool is dispatched with run_in_background: true and the parent conversation undergoes a session rollover (e.g. context compaction, producing a new session ID), the background agent's completion notification never arrives, and SendMessage cannot resume it — even though the agent completed successfully and its full transcript exists on disk exactly where expected.
Environment
- Claude Code version:
2.1.270(from transcript metadata) - Entrypoint:
sdk-ts - Platform: Linux
Steps to reproduce
- In a session (call it session A, ID
173d72f3-...), dispatch a backgroundAgent(run_in_background: true). Note the returnedagentId. - Let the conversation continue long enough to trigger a session rollover — in this case, context compaction produced a new session ID (
67a929, visible afterward viaListAgents). - Wait for the agent to finish. No
<task-notification>arrives in the (now-rolled-over) session. - Attempt
SendMessage({ to: "<agentId>" })to resume/read the result.
Observed behavior
SendMessage returns:
{"success":false,"message":"Agent \"<agentId>\" could not be resumed: No transcript found for agent ID: <agentId>. If you read this id in a message from another Claude Code process ..."}
But the transcript does exist and is complete:
/home/<user>/.claude/projects/<project>/173d72f3-.../subagents/agent-<agentId>.jsonl (218KB)
— ending cleanly in a normal finished assistant turn, timestamped after the dispatch. The agent did its job; only the resume/notification path failed.
Root cause (as far as I can tell from the outside)
The agent's transcript is stored under the session that launched it (173d72f3-...). SendMessage's resume logic appears to look for the agent only within the current session's own subagent directory. Once the parent conversation rolls over to a new session ID (compaction), the current session no longer "owns" that subagent directory, so the agent becomes unreachable via SendMessage — permanently — even though nothing was lost on disk and the <agentId>.output symlink still resolves correctly.
This also means the promised "you will be notified automatically when it completes" behavior silently fails in this scenario: no notification is delivered to the post-rollover session, and there's no indication to the assistant/user that the agent's outcome is now orphaned rather than merely delayed.
Impact
This has happened repeatedly (5+ times across sessions per our own usage) and is expensive: the only recovery is manually locating and reading the raw JSONL transcript file by path, which isn't part of the documented/expected workflow and risks overflowing context if not filtered carefully. For a user relying on background dispatch for real parallelism, this makes the feature unreliable across any turn that triggers compaction.
Suggested fix
SendMessage's resume logic should search across all session directories for a given agent ID within the project, not just the current session's own subagent folder (the ID is already globally unique).- Alternatively/additionally, when a session rollover occurs, in-flight or completed background agents launched under the prior session ID should be re-associated with the new session so notifications and resume both continue to work.
- At minimum, the error message should distinguish "never existed" from "exists but is orphaned under a different session" so the caller knows to fall back to direct transcript reading rather than assuming the agent vanished.