[BUG] Agent view daemon: stale "done" sessions accumulate uncleaned, causing synchronous blocking cleanup that stalls session spawn/switch

Open 💬 0 comments Opened Jul 2, 2026 by pnutshellmenace

Preflight Checklist

  • [x] I have searched existing issues — related but not exact: #71459 (confirms a "memory-pressure reaping" design pattern exists for background shell jobs, different subsystem), #68394 (Windows: agent session processes not reaped at all — opposite-direction symptom), #70252 (terminated agents persist in the agent list, no cleanup mechanism). None describe the spawn/switch-blocking behavior below.
  • [x] This is a single bug report
  • [x] I am using the latest version of Claude Code

What's Wrong?

The background-agent daemon (claude agents / agent view) accumulates completed ("done") sessions without proactively cleaning them up. When the daemon's internal low-memory heuristic trips, it synchronously retires/reaps settled sessions before proceeding — and this blocking cleanup is visible to the user as a multi-second stall (~15-20s observed) in at least two places:

  1. Spawning a new session ("open new session" from agent view) — the new session sits in a delayed/stalled loading state; typed commands (e.g. /rename) are accepted but don't echo or update the UI until cleanup finishes. Oddly, once it does unblock, the original dispatch prompt appears to get processed/echoed after the interim command typed during the stall, suggesting queued messages are replayed out of order once the session unblocks.
  2. Switching between existing sessions in agent view — produces a "waiting for session to redraw" message for a similarly extended period.

The low-memory heuristic appears miscalibrated. At the exact moment it fired (logged "low memory (120MB free)"), memory_pressure reported the system at 41% free/available system-wide on a 32GB machine — not remotely under real memory pressure. This suggests the check reads raw free pages rather than actually-available memory (free + reclaimable/purgeable) — macOS deliberately keeps raw free pages low via aggressive disk caching, so a raw-free-pages check will trigger constantly on macOS regardless of real headroom.

Separately, claude agents --json --all showed a large majority of all tracked sessions already in state: done — apparently never proactively reaped after completion, only lazily/reactively when the daemon needs memory for a new spawn. The larger this backlog grows, the more blocking cleanup work lands at the least convenient moment (exactly when the user is trying to do something).

Steps to Reproduce

  1. Use claude agents / agent view regularly over an extended period, accumulating many completed background sessions that aren't manually cleaned up.
  2. Run claude agents --json --all — observe a large number of state: done sessions still tracked.
  3. Dispatch a new session ("open new session") or switch between existing sessions in agent view.
  4. If the daemon's low-memory check trips at that moment, observe a multi-second (10-20s+) stall: new sessions appear delayed/stalled with no immediate echo of typed input; switching sessions shows "waiting for session to redraw."
  5. Check ~/.claude/daemon.log around the same timestamp for a [bg] bg: low memory (NNNMB free) — retiring settled workers before spawning <id> line correlating with the stall.

Evidence

Representative daemon.log excerpt (session IDs are short random hex identifiers, replaced with placeholders — not personally identifying either way):

[bg] bg: low memory (68MB free) — retiring settled workers before spawning <id>
[bg] bg spawned <id> (fleet)
[bg] bg: low memory (86MB free) — retiring settled workers before spawning <id>
[bg] bg spawned <id> (fleet)
[bg] bg: low memory (105MB free) — retiring settled workers before spawning <id>
[bg] bg spawned <id> (fleet)

This pattern recurred 27 times in a single day in my logs, with reported "free" values ranging from 68MB to ~350MB.

At the time of one of these events, memory_pressure reported:

System-wide memory free percentage: 41%

— on a 32GB machine, i.e. not under real memory pressure by any conventional measure.

claude agents --json --all at time of investigation:

Total tracked sessions: 81
  state=done:     78
  state=blocked:   2
  state=working:   1

Expected Behavior

  • The low-memory check should use an accurate available-memory metric (free + reclaimable/purgeable pages), not raw free pages — especially on macOS, where raw free pages are intentionally kept low by the OS's disk cache.
  • Completed (done) sessions should be proactively reaped shortly after completion or on a schedule, rather than accumulating indefinitely and only being cleaned up reactively.
  • Any necessary retirement/cleanup work triggered by a user action (new session spawn, session switch) should happen asynchronously rather than blocking that action — or at minimum the UI should clearly communicate that cleanup is in progress rather than appearing to silently hang.

Environment

  • Claude Code CLI 2.1.198
  • macOS 26.5.2 (build 25F84), Apple Silicon
  • 32GB RAM; memory_pressure reporting 41% free/available at time of stall
  • Heavy claude agents / background-agent usage over an extended period, resulting in dozens of accumulated done sessions

Related

  • #71459 — confirms a similar "memory-pressure reaping" design pattern exists elsewhere in the codebase (background shell jobs, opt-out via CLAUDE_CODE_DISABLE_BG_SHELL_PRESSURE_REAP) — possibly a variant of the same subsystem applied here to full agent-view sessions.
  • #68394 — opposite-direction symptom on Windows (sessions not reaped at all, accumulating unboundedly) — may share a root cause in when/how the reaping logic runs.
  • #70252 — terminated agents persist in the agent list with "no cleanup mechanism," same general accumulation theme.

View original on GitHub ↗