Skip to content

fix: clean up all sessions on worktree removal#191

Open
JHK wants to merge 6 commits into
hmans:mainfrom
JHK:beans/keen-magpie-hc58
Open

fix: clean up all sessions on worktree removal#191
JHK wants to merge 6 commits into
hmans:mainfrom
JHK:beans/keen-magpie-hc58

Conversation

@JHK
Copy link
Copy Markdown
Contributor

@JHK JHK commented Apr 13, 2026

Summary

RemoveWorktree had several session cleanup issues, and terminal session teardown didn't kill descendant processes:

Session cleanup on worktree removal:

  • Run terminal sessions (keyed id + "__run") were never closed — the shell process kept running
  • Agent sessions were not stopped — a running Claude Code process could outlive its worktree
  • Sessions were cleaned up after the worktree directory was deleted, leaving processes with a dangling working directory

Process group kill for terminal sessions:

  • Closing a terminal session only killed the immediate shell, not its child processes (e.g. mise dev spawning multiple subprocesses)
  • Now uses process group kill (-pid) to reap all descendants on Unix

Changes

  • Close both id and id + RunSessionSuffix terminal sessions on worktree removal
  • Stop the agent session via AgentMgr.StopSession(id)
  • Reorder cleanup to stop sessions before removing the worktree directory
  • Add killProcessGroup() platform helper (Unix: syscall.Kill(-pid, SIGKILL); Windows: taskkill /F /T)
  • Use process group kill in Session.Close() to reap all descendant processes
  • Extract shared testutil.InitTestRepo helper

🤖 Generated with Claude Code

…btx)

- Add `TerminalMgr.Close(id + RunSessionSuffix)` in RemoveWorktree resolver
  so run sessions (keyed `<id>__run`) are cleaned up alongside regular sessions
- Add TestRemoveWorktreeClosesRunSession covering the cleanup path

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
@JHK JHK marked this pull request as draft April 13, 2026 12:21
JHK and others added 3 commits April 13, 2026 14:33
… (Refs: beans-4btx)

- Stop agent process (AgentMgr.StopSession) when removing a worktree
- Extract initTestRepo into internal/testutil.InitTestRepo shared helper
- Remove redundant comment restating what the code does

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
…s: beans-4btx)

- Log warning when AgentMgr.StopSession fails instead of silently discarding error
- Add AgentMgr to RemoveWorktree test and verify agent session is stopped
- Rename test to TestRemoveWorktreeCleansUpSessions to reflect broader scope
- Remove trivial initTestRepo wrapper in worktree_test.go, call testutil.InitTestRepo directly

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
…s: beans-4btx)

- Stop agent/terminal sessions before removing the worktree directory
- Remove dead error handling for StopSession (always returns nil)
- Strengthen test by setting status to Running before removal
- Add defer agentMgr.Shutdown() for proper test cleanup
- Remove extra blank line in worktree_test.go

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
@JHK JHK changed the title fix: close run terminal session when removing worktree (Refs: beans-4btx) fix: clean up all sessions on worktree removal (Refs: beans-4btx) Apr 13, 2026
JHK and others added 2 commits April 13, 2026 15:18
- Set Setpgid on commands spawned by CreateWithCommand (Unix only)
- Session.Close() sends SIGTERM to entire process group, escalates to
  SIGKILL after 3s grace period
- Interactive shell sessions unchanged (still use direct Process.Kill)
- Platform-specific files: process_unix.go, process_windows.go (no-op)
- Tests for process group kill and graceful SIGTERM shutdown

Refs: beans-3fmc

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
- Remove redundant Setpgid/pgid field; go-pty's Setsid already makes
  every spawned PID a process group leader
- Close() now unconditionally kills the process group via -pid
- SIGTERM with 3s grace, escalating to SIGKILL
- Applies to all sessions (interactive and command), not just CreateWithCommand

Refs: beans-3fmc

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
@JHK JHK changed the title fix: clean up all sessions on worktree removal (Refs: beans-4btx) fix: clean up sessions and kill process trees on worktree removal (Refs: beans-4btx) Apr 13, 2026
@JHK JHK changed the title fix: clean up sessions and kill process trees on worktree removal (Refs: beans-4btx) fix: clean up all sessions on worktree removal Apr 13, 2026
@JHK
Copy link
Copy Markdown
Contributor Author

JHK commented Apr 13, 2026

This code is so far au pair programmed but not tested by me. I will convert this to a proper PR once I've validated the fixes and consider them useful.

Background: While working with beans-serve over longer sessions — starting workspaces, finishing work, integrating changes, and closing workspaces — I noticed orphaned claude and watchexec processes accumulating. This eventually escalated to running out of file descriptors. I don't have a consistent reproduction yet, but code analysis confirmed several cleanup gaps.

@JHK JHK marked this pull request as ready for review April 27, 2026 14:37
@JHK
Copy link
Copy Markdown
Contributor Author

JHK commented Apr 27, 2026

Finally found the time to do some testing and can confirm that this patch does indeed fix the issue of processes piling up and lingering around - thus ready for review.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant