feat(app): pin workspace tabs - #4134
Closed
aliozkanozdurmus wants to merge 6 commits into
Closed
aliozkanozdurmus wants to merge 6 commits into
aliozkanozdurmus wants to merge 6 commits into
Conversation
added 6 commits
August 31, 2026 21:05
Collaborator
|
Closing this feature PR. Please discuss the workflow and shared need in Discussions, following CONTRIBUTING.md. |
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.
The problem
Workspace tabs accumulate over long sessions: a couple of anchors (the main agent session, a long-running terminal, a reference file) mixed into short-lived scratch tabs. Every bulk-close gesture — "Close other tabs", "Close to the left/right" — treats all tabs the same, so keeping anchors around means closing scratch tabs one by one, or reopening anchors after a bulk close. There is no way to say "this tab matters, keep it".
What changes
Users can pin any persistent workspace tab:
isPinnedis optional, so previously persisted layouts load unchanged.This is separate from the existing internal
pinnedAgentIdsvisibility-reconciliation mechanism, which is untouched.Tests
Unit/integration (vitest, run from
packages/app):workspace-tab-menu.test.ts— Pin/Unpin item per tab kind, label switching, toggle dispatch, no pin for ephemeral kindsworkspace-tab-model.test.ts,workspace-tabs/model.test.ts— pinned state on the tab model and persistence eligibilityworkspace-bulk-close.test.ts+workspace-tab-bulk-close-actions.test.ts— close before/after/others skip pinned, driven through the real store + menu handlers, not the selector in isolationworkspace-pane-close.test.ts— relocation, final-pane block, and failure-path atomicity (unpinned tabs present; zero mutations when relocation fails)workspace-tab-presentation.test.tsx— rendered pin slot, stable width/height/flexShrink across pin togglesworkspace-layout-store.test.ts— persistence, tab replacement, reconciliationBrowser e2e:
e2e/browser/pinned-tabs.spec.ts— a real Playwright run (isolated daemon + Metro harness) that creates three terminal tabs through the real UI, pins via the real context menu, and verifies "Close other tabs" from an unpinned anchor keeps the pinned tab, then that unpinning restores normal close behavior. Mutation-checked: with the pinned filter removed, the spec fails; restored, it passes.QA evidence
Commands run on this branch:
npm run typecheck, targetednpm run lint -- <changed files>(0 warnings/errors), andnpm run format:checkall pass.Screenshots captured from the e2e run:
Video of the full interaction: pinned-tabs-e2e.webm
Platforms
Daemon and protocol are untouched — this is an app-side change only.
Notes
I know feature PRs here normally start with a product discussion; this one is framed workflow-first per the contributing guide, and I'm happy to open a Discussion or reshape any part of it (icon, placement, close semantics) to fit the direction you want. Maintainer edits are enabled.