refactor(dashboard): remove the legacy layout engine (dockview-only) - #266
Merged
Conversation
dockview shipped as the default in #263; this deletes the legacy binary-tree layout, the detached-terminal overlay (SessionMountLayer), the `groups` system, the `layoutEngine` flag, and react-resizable-panels (ADR-047 "delete legacy"). Removed: layoutTree(.ts/.test), SplitLayout, PaneSlot, SessionMountLayer, LayoutContext, DropZoneOverlay, TabBar (8 files); the binary-tree/group slices of the store (layout/focusedLeafId/groups/activeGroupId + 11 split-pane actions) and their persist entries; the dual-engine branches (switchPane/open* collapse to dockview, fetchSessions legacy prune dropped); the legacy keyboard shortcuts (Ctrl+D/Ctrl+Shift+D/Ctrl+W — dockview-native keybinds are a follow-up); the DragProvider/useDragContext React context (kept DRAG_TYPE/encode/decodeDragData). Re-sourced the sidebar's on-screen-agent indicator from dockview: DockviewLayout publishes its visible panel ids to a new `visiblePaneIds` store field (via onDidLayoutChange) that the sidebar reads, replacing allTabPanes(layout). Net ~3.5k LOC removed. dockview is now the only layout engine. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01MGMW4cbhv5Le8wka7Th8bS
aterrylu
enabled auto-merge (squash)
June 28, 2026 19:36
nox-0x
approved these changes
Jun 28, 2026
nox-0x
left a comment
Collaborator
There was a problem hiding this comment.
Approving — clean atomic deletion of the legacy layout engine; the two reconciliation fixes (prune effect now triggers on previewPanes change; visiblePaneIds cleared on DockviewLayout unmount) close the obvious gaps a tree-as-source-of-truth removal would have left. Sound reasoning throughout:
- The
visiblePaneIdsround-trip (DockviewLayout'sonDidLayoutChange→ store → Sidebar memo'd Set) replacesallTabPanes(layout)cleanly.pushVisibleis stable ([]deps) and fires on all add/remove/move events. CreateAgentPanelno longer self-closes — verifiedspawnSessioncallsswitchPane({type:'session',id})on success (store.ts:574), which solo-replaces the create-agent panel viasyncToActive.- Effect ordering safe:
syncToActive(mount-restore) runs beforepruneDead(declaration order), so newly-added previews/sessions never get pruned mid-add. - Removing the legacy-only
pruneStaleSessionTabsbranch infetchSessionsis correct — dockview owns topology andpruneDeadhandles dead-session panels. - Tests trimmed to the actual surface (switchPane semantics under dockview); legacy split/move/closeTab suites correctly gone with the code they exercised.
Minor follow-up (non-blocking): README.md:109 still lists react-resizable-panels in the tech-stack line — the dep is gone now, swap to dockview-react whenever convenient.
aterrylu
added a commit
that referenced
this pull request
Jun 28, 2026
The `Ctrl+D splits the focused leaf` e2e test (e2e/layout.spec.ts) read the removed binary-tree `layout` via the store bridge (`leafCount`) and pressed the removed Ctrl+D shortcut — both deleted with the legacy layout engine (#266), so it failed on main (e2e isn't a required check, so #266 merged with it red). Remove that test + its now-dead `leafCount` helper; keep the still-valid tab-switching test (Org Chart → Templates) verbatim. dockview-native split keybinds + their e2e coverage are a planned follow-up. Claude-Session: https://claude.ai/code/session_01MGMW4cbhv5Le8wka7Th8bS Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
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
Removes the legacy layout engine now that dockview is the default (ADR-047 "delete legacy" phase; follows #263). This is the atomic deletion the ADR planned: ~3,500 LOC of fragile hand-rolled layout code comes out, leaving dockview as the only engine.
No user-facing behavior change — dockview already shipped on by default in #263 and is untouched here. This PR is pure subtraction + two small reconciliation fixes.
What's deleted
graph LR subgraph Gone["Deleted (~3.5k LOC)"] direction TB A["layoutTree.ts (+723-line test)"] B["SessionMountLayer<br/>(detached overlay)"] C["SplitLayout · PaneSlot<br/>DropZoneOverlay · TabBar · LayoutContext"] D["groups workspace-swap<br/>+ 11 split-pane store actions"] E["layoutEngine flag<br/>+ dual-engine branches"] F["react-resizable-panels dep"] end subgraph Kept["Remaining engine"] G["dockview-react<br/>(the only layout engine)"] end Gone -.retired.-> GlayoutTree.ts(+ its 723-line test),SplitLayout.tsx,PaneSlot.tsx,SessionMountLayer.tsx,LayoutContext.tsx,DropZoneOverlay.tsx,TabBar.tsx.layout/focusedLeafId/groups/activeGroupIdstate + 11 binary-tree/group actions + their persist entries; thelayoutEngineflag is gone (dual-path actions collapse to their dockview body).DragContext.tsx: kept the drag serialization (DRAG_TYPE/encodeDragData/decodeDragData/DragData— dockview still uses these); removed the legacy ReactDragProvider/useDragContext.react-resizable-panelsremoved from dependencies.Re-sourced: the sidebar's on-screen-agent indicator
The only behavioral wiring change. The sidebar marked which agent rows are currently on-screen via
allTabPanes(layout)(the deleted tree). It now reads a newvisiblePaneIdsstore field that DockviewLayout publishes from its live panel set (onDidLayoutChange+ after restore/drop). Cleared on unmount so it doesn't go stale when the dock empties.Review fixes
A
code-reviewerpass on the diff caught two reconciliation gaps (both from removing the layout tree as the single reconcile source) — fixed:sessionschanges). The prune effect now also triggers onpreviewPanes.visiblePaneIdson unmount: killing the active pane left the sidebar highlighting a now-empty dock.visiblePaneIdsis now cleared on DockviewLayout unmount.Testing
make checkgreen: biome +tsc --build+ 613 server tests + 227 dashboard tests.DragContext's serialization is still needed by dockview); one reviewed the diff and found the two reconciliation gaps above (fixed).e2e(real Playwright). dockview's interactive behavior — click=solo, drag=compose, workspace restore, cold-reload, hidden-panel visibility, overlay suppression — was exhaustively Playwright-verified in feat(dashboard): rebuild tabs + split-pane layout on dockview, default on #263 and is unchanged here, so this PR leans on CI e2e rather than re-running that suite locally.Risks
layoutEngineflag is gone, so there's no runtime fallback to legacy anymore — intentional (ADR-047). The legacy code is fully removed, not just default-off.🤖 Generated with Claude Code
https://claude.ai/code/session_01MGMW4cbhv5Le8wka7Th8bS