Skip to content

Add multiplexer detach/resume (#407) - #430

Open
jvanderen1 wants to merge 3 commits into
kitknox:mainfrom
jvanderen1:feature/407-1-mux-detach-resume
Open

jvanderen1 wants to merge 3 commits into
kitknox:mainfrom
jvanderen1:feature/407-1-mux-detach-resume

Conversation

@jvanderen1

@jvanderen1 jvanderen1 commented Sep 8, 2026

Copy link
Copy Markdown
Contributor

Summary

  • Detach Session from Tabs and the tab context menu for tmux -CC, raw tmux, zellij, herdr (including herdr (control)), and zmx. Session stays running on the host; reattach from Profiles / the same auto-start profile.
  • Resume-or-focus when opening that profile while a live attachment exists. herdr (control) matches HerdrController the same way tmux -CC matches TmuxController (not the leftover gateway shell).
  • Short post-detach banner with optional Reconnect (✕ dismisses).
  • herdr (control) uses the same HerdrController.detach path as ESC / the herdr menu.
  • On this PR, zmx tab ✕ still leaves the session (closing the client is zmx’s native detach), as requested in review. Destroy-on-✕ is not in this diff — see Fix mux tab close after detach/reattach (#407) #431.
  • Raw-pane detach chords come from swipe/session discovery when present, otherwise the usual defaults (⌃B d / ⌃O d / ⌃B q). No new Settings UI.
  • No default Detach keybind (assign in Settings → Keybinds). ⌘⇧X Detach Other Clients unchanged.
  • iPad Visor and Quick Settings stay intact.

This PR is only detach / resume / banner. Dropped from an earlier draft: Detach All, a Detach Chords settings page, tab-title session subtitles, and missing-binary scaffolding (#432).

Part of #407. Stack: PR 1 of 3 — follow-ups: #431 (close-after-reattach / ✕ vs Detach), #432 (optional missing-binary banner).

Screencast

One DietPi recording covers this PR and #431 (no separate #430-only take).

Different.Multiplexers-gh.mp4

This PR

  1. tmux -CC — Detach Session → banner → reconnect from Profiles (tabs return).
  2. zmx — Detach Session → reconnect; work still running.
  3. herdr (control) — Detach Session → no leftover SSH shell → reconnect from Profiles.

Later in the same recording (not this diff)

Test plan

  • tmux -CC: context-menu Detach → banner appears
  • herdr (control): Detach Session / ESC post the same reconnect banner; no leftover gateway shell
  • Banner dismisses; Reconnect reopens when SSH offer is present
  • Same profile reconnect focuses the live attachment
  • zmx Detach keeps the session (tab ✕ also leaves it, on this PR)
  • Quick Settings and Discover Sessions still work
  • No default Detach keybind unless the user assigned one
  • iPad Visor still presents and can take focus

@kitknox

kitknox commented Sep 8, 2026

Copy link
Copy Markdown
Owner

What is the expected behavior for multiplexers that are started outside of profiles?

This will otherwise need some changes before it can be merged.

  1. It appears it whacked part of the new iPad Visor implementation and Quick Settings, not sure if that was from something merge related on your end?

  2. Close tab on a zmx pane now appears to destroy the remote session

  3. Detach chords are hard coded. I believe we have some auto discovery elsewhere for the swipe feature. For any auto detect failure we otherwise need to make configurable?

@jvanderen1

Copy link
Copy Markdown
Contributor Author

Thanks for the review — addressing these in follow-up commits on this PR.

Multiplexers started outside profiles
Intent is that Detach/resume/banners key off the live pane binding (raw / passthrough / tmux -CC controller), not only profile auto-start. Hardening detection so a manually started / discovered attachment is not second-class.

1. Visor / Quick Settings
Not intentional — rebasing onto current main and verifying Visor / Quick Settings are intact.

2. Close Tab destroying zmx
Agreed this fights zmx’s model (closing the client is detach). Reverting Close Tab to leave the session alive; Detach stays the explicit leave path. An explicit Kill Session can be a follow-up if we still want destroy in-app.

3. Hard-coded detach chords
Moving prefix/d (and friends) onto the same discovery path as swipe bindings, with hard-coded defaults only as fallback when discovery has not run / failed.

@jvanderen1

Copy link
Copy Markdown
Contributor Author

Thanks for the review — a few notes and one design call I’d like your preference on.

Multiplexers started outside profiles

Intent is that Detach/resume/banners key off the live pane binding (raw / passthrough / tmux -CC controller), not only profile auto-start. So a manually started zmx attach … / discovered session should behave the same once rootshell knows the attachment. If that’s thin today for “typed it myself” cases, I’ll harden detection so non-profile launches aren’t second-class.

  1. Visor / Quick Settings Not intentional. The Detach menu items were additive on the Tabs nav group; I’ll rebase onto current main and double-check nothing Visor/Quick Settings related got dropped in the merge.

  2. Close Tab destroying zmx. That was deliberate on our side to distinguish Detach (leave session) from Close (destroy), but it fights zmx’s own model where closing the client is detach. Happy to flip Close Tab back to leave-alive and keep destroy behind an explicit Kill Session (or only via zmx kill outside the app) if you prefer native zmx semantics. Which do you want as the product rule?

  3. Hard-coded detach chords. Agreed. Prefix/d (and friends) should follow the same discovery path as swipe/expose where we already learn bindings, with Settings overrides when discovery fails or the user customized the prefix. I’ll move the hard-coded chords behind that.

@kitknox

kitknox commented Sep 9, 2026

Copy link
Copy Markdown
Owner

I wonder if we should try to consolidate the close tab behavior setting which is currently tmux control mode specific.
Screenshot 2026-09-08 at 5 10 23 PM

@kitknox

kitknox commented Sep 13, 2026

Copy link
Copy Markdown
Owner

Since this PR was started I've also now landed full herdr control mode support that will want to ensure is consistent in terms of detach behavior.

jvanderen1 added a commit to jvanderen1/rootshell that referenced this pull request Sep 13, 2026
Rebase kitknox#430 onto latest main (Discover Sessions, herdr control mode, Quick Settings / Visor). Detach keys off live pane bindings, uses swipe-discovered chords with Settings fallback, routes herdr -CC through HerdrController.detach, and Close Tab on zmx leaves the session.
@jvanderen1
jvanderen1 force-pushed the feature/407-1-mux-detach-resume branch from 103cc2e to 20c8620 Compare September 13, 2026 20:52
@kitknox

kitknox commented Sep 13, 2026

Copy link
Copy Markdown
Owner

Latest force push has regression that removes the iPad visor feature.

@jvanderen1

Copy link
Copy Markdown
Contributor Author

Sorry, it's still a WIP integrating everything. Will let you know when things shape up.

Leave a mux session running from Tabs / the tab menu, focus a live
auto-start attachment instead of opening a second client, and offer
Reconnect on a short banner. Raw-pane chords use swipe discovery
when present, otherwise the usual defaults.
@jvanderen1
jvanderen1 force-pushed the feature/407-1-mux-detach-resume branch from 5187cdc to 8463343 Compare September 13, 2026 21:27
herdr (control) is a gateway plus projected tabs, not a raw pane binding.
Match HerdrController the same way tmux -CC matches TmuxController, and do
not treat a leftover gateway shell as still attached.
@jvanderen1

Copy link
Copy Markdown
Contributor Author

@kitknox I went ahead and addressed some outstanding items. This and follow-up PR's are quite large though. Feel free to review at your own time or close if it's too large!

jvanderen1 added a commit to jvanderen1/rootshell that referenced this pull request Sep 16, 2026
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.

2 participants