Conversation
When an agent is killed without the Stop hook firing, its session remains in ACTIVE phase permanently. PostCommit unconditionally set hasNew=true for ACTIVE sessions and skipped the file overlap check, so stale ACTIVE sessions got condensed into every subsequent commit. Apply the file overlap check to ALL sessions (including ACTIVE) by intersecting filesTouchedBefore with the actually-committed files before calling filesOverlapWithContent. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> Entire-Checkpoint: 8642696e40dd
PR SummaryMedium Risk Overview This centralizes the condensation decision in Written by Cursor Bugbot for commit 014f53f. Configure here. |
There was a problem hiding this comment.
Pull request overview
This PR fixes a bug where stale ACTIVE sessions (agent killed without the Stop hook firing) were incorrectly condensed into every subsequent commit. The fix extends the file overlap check to ALL sessions, including ACTIVE ones, by intersecting the session's touched files with the actually-committed files before calling filesOverlapWithContent.
Changes:
- Modified
HandleCondenseinmanual_commit_hooks.goto apply content overlap checking to ACTIVE sessions - Added
filesTouchedBeforefield topostCommitActionHandlerand filter logic to check only committed files - Added comprehensive regression test
TestPostCommit_StaleActiveSession_NotCondensed - Updated
TestHandleTurnEnd_PartialFailureto includesecond.txtinFilesTouchedfor accurate overlap checking - Refactored test constant
testNewActiveSessionIDfor consistency
Reviewed changes
Copilot reviewed 2 out of 2 changed files in this pull request and generated no comments.
| File | Description |
|---|---|
| cmd/entire/cli/strategy/manual_commit_hooks.go | Fixed condensation logic to apply overlap check to ALL sessions including ACTIVE, preventing stale sessions from being incorrectly condensed |
| cmd/entire/cli/strategy/phase_postcommit_test.go | Added regression test for stale ACTIVE sessions, updated existing test for correct FilesTouched tracking, and refactored constant |
The overlap check from the previous commit only applied to HandleCondense (ACTIVE/IDLE sessions). ENDED sessions go through HandleCondenseIfFilesTouched, which had no overlap check at all — it only checked len(FilesTouched) > 0. Carry-forward sets FilesTouched with remaining uncommitted files after condensation. On the next commit, sessionHasNewContent returns true (shadow branch has content), and HandleCondenseIfFilesTouched condenses the session again. This cycle repeats on every commit indefinitely. Extract shouldCondenseWithOverlapCheck as a shared method and use it in both HandleCondense and HandleCondenseIfFilesTouched. This ensures ALL condensation paths verify that committed files actually overlap with session files. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> Entire-Checkpoint: 2fbfa77cb815
…n-vacuums-too-much # Conflicts: # cmd/entire/cli/strategy/manual_commit_hooks.go
shouldCondenseWithOverlapCheck() was fail-open when filesTouchedBefore was empty, causing IDLE sessions with no files (e.g., conversation-only sessions) to be condensed into unrelated commits. Now only ACTIVE sessions fail-open (to handle mid-turn commits before files are saved to state); IDLE/ENDED sessions with no files return false. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> Entire-Checkpoint: 058ec85be074
|
bugbot run |
- Update comment to reference SaveStep/SaveTaskStep instead of nonexistent SaveChanges - Remove unused newHead computation in idle empty-files test Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> Entire-Checkpoint: 2ac81686c7e4
Summary
Fixes zombie sessions being re-condensed into every commit indefinitely.
Root cause: After condensation, carry-forward sets
FilesTouchedwith uncommitted files. On subsequent commits,sessionHasNewContentreturns true (shadow branch has content), and the condensation handlers condense the session again without checking whether the committed files actually relate to the session. This cycle repeats on every commit.Affected code paths:
HandleCondense(ACTIVE/IDLE sessions) — skipped the overlap check entirely for ACTIVE sessions (hasNew=trueunconditionally)HandleCondenseIfFilesTouched(ENDED sessions) — had zero overlap checking, only checkedlen(FilesTouched) > 0 && hasNewImpact: In one real case, 6 zombie sessions accumulated over 11 days (Feb 8–19), polluting 12 checkpoints with 18 duplicate condensation events.
Fix: Extract
shouldCondenseWithOverlapCheck()as a shared method that intersects session files with actually-committed files before callingfilesOverlapWithContent. BothHandleCondenseandHandleCondenseIfFilesTouchednow use this method, ensuring ALL condensation paths verify file overlap.Commits
1.
bee7df26— fix stale ACTIVE sessions being condensed into every commitfilesTouchedBeforefield topostCommitActionHandler, populated fromstate.FilesTouched(IDLE/ENDED) or transcript extraction (ACTIVE)shouldCondenseWithOverlapCheck()method: intersectsfilesTouchedBeforewithcommittedFileSet, then callsfilesOverlapWithContenton the intersectionHandleCondenseandHandleCondenseIfFilesTouchednow use this shared methodTestPostCommit_StaleActiveSession_NotCondensedregression test2.
744c4f3f— fix ENDED sessions with carry-forward re-condensed into every commitHandleCondenseIfFilesTouched(ENDED sessions), which previously had zero overlap checkingTestPostCommit_EndedSessionCarryForward_NotCondensedIntoUnrelatedCommitregression testTestHandleTurnEnd_PartialFailureto includesecond.txtinFilesTouchedso the overlap check passes3.
014f53f2— fix IDLE sessions with empty FilesTouched incorrectly condensedshouldCondenseWithOverlapCheck()was fail-open whenfilesTouchedBeforewas empty, causing IDLE sessions with no files (e.g., conversation-only) to be condensed into unrelated commitsisActiveparameter: ACTIVE sessions fail-open (handles mid-turn multi-session commits), IDLE/ENDED sessions return falseTestPostCommit_IdleSessionEmptyFilesTouched_NotCondensedregression testTest plan
TestPostCommit_StaleActiveSession_NotCondensedTestPostCommit_EndedSessionCarryForward_NotCondensedIntoUnrelatedCommitTestPostCommit_IdleSessionEmptyFilesTouched_NotCondensedTestPostCommit_ActiveSessionAlwaysCondenses— ACTIVE sessions with no files still condense (multi-session)TestHandleTurnEnd_PartialFailure— updated for overlap checkmise run fmt && mise run lintclean🤖 Generated with Claude Code