fix(subagent,core): reap panicked sub-agents via join_handle, scrub PII in sub-agent debug dumps#6414
Merged
Merged
Conversation
…just status_rx collect_finished_subagents() previously determined reapability purely from status_rx terminal state, so a panicking sub-agent task left its handle frozen in the last observed Working state and never got reaped, reproducing the zombie-sidebar-entry symptom via a path #6406 did not close. Add join_handle.is_finished() as an independent terminal signal. collect() also early-returned via `?` on a panicked join_handle, skipping fleet mark_terminal and the final TranscriptMeta write; flattened the double-Result so both still run for panicked tasks. Closes #6408
Sub-agent LLM-call debug dumps wired in #6406 received the baseline scrub_content/redact_binary_blobs pass but skipped the optional extra PiiFilter.scrub() layer that top-level dumps get when [classifiers]/PII filtering is enabled, giving sub-agent dumps a weaker PII-redaction posture than top-level dumps. Add PiiScrubbingDumpSink, wrapping DebugDumper with the same PiiFilter handle used by top-level dump construction, and wire it into build_spawn_context's debug_dump_sink for both fresh spawn and /agent resume. PiiFilter now derives Clone (cheap, Regex is Arc-backed). Closes #6407
collect_finished_subagents_reaps_handle_whose_task_finished_without_terminal_status covers the reap side of the join_handle.is_finished() backstop but nothing guarded against over-eager reaping. Add a test asserting a handle whose task is genuinely still running (status_rx == Working, is_finished() == false) survives collect_finished_subagents().
Replace redundant closure with a bare function reference in the negative-path regression test (clippy::redundant_closure under -D warnings), and add the missing CHANGELOG.md entry for the #6408 fix.
DebugState::write_chat_debug_dump is private (agent::state is pub(crate)), so linking to it from a pub item trips rustdoc::private_intra_doc_links under -D warnings. Drop the link markup, keep the reference as plain inline code text.
bug-ops
enabled auto-merge (squash)
July 17, 2026 20:12
bug-ops
force-pushed
the
fix/6408-subagent-reap-pii-scrub
branch
from
July 17, 2026 20:12
15d301c to
3381c8d
Compare
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Two P3 bug follow-ups discovered during impl-critic review of PR #6406, bundled together since both are small, independent defense-in-depth fixes from the same review cycle.
collect_finished_subagents()(crates/zeph-core/src/agent/scheduler_loop.rs) determined reapability purely fromstatus_rx's terminal state, so a sub-agent task that exited via a panic — without ever publishing a terminalSubAgentStatus— left its handle frozen in the last observedWorkingstate forever, reproducing the TUI agents sidebar shows sub-agent as WORKING forever after LLM-call timeout (zombie entry, elapsed counter climbs indefinitely) #6381 zombie-sidebar-entry symptom through a path fix(subagent): publish terminal status on LLM timeout and capture debug dumps #6406 did not close. Addedjoin_handle.is_finished()as an independent terminal signal (BlockingHandle::is_finishedinzeph-common,SubAgentManager::is_task_finishedinzeph-subagent). Also fixed a related bug inSubAgentManager::collect(), which early-returned via?on a panickedjoin_handle, skipping the fleetmark_terminalcall and the finalTranscriptMetawrite for panicked tasks.DebugDumpSink) received baselinescrub_content/redact_binary_blobsscrubbing but skipped the optional extraPiiFilter.scrub()layer that top-level dumps get when PII filtering is enabled — an inconsistent PII-redaction posture between top-level and sub-agent-executed dumps. AddedPiiScrubbingDumpSink, wrappingDebugDumperwith the samePiiFilterhandle used by top-level dump construction, wired intobuild_spawn_contextfor both fresh spawn and/agent resume.Closes #6408
Closes #6407
Test plan
cargo +nightly fmt --checkcargo clippy --profile ci --workspace --all-targets --features "desktop,ide,server,chat,pdf,scheduler,testing" -- -D warningscargo nextest run --config-file .github/nextest.toml --workspace --features "desktop,ide,server,chat,pdf,scheduler" --lib --bins(14161 passed)RUSTFLAGS="-D warnings" RUSTDOCFLAGS="--deny rustdoc::broken_intra_doc_links" cargo doc --no-deps --workspace --features "desktop,ide,server,chat,pdf,scheduler"cargo test --doc --workspace --features "desktop,ide,server,chat,pdf,scheduler"(34 doc-test suites)gitleaks detecton the branch diff