Skip to content

Add collapsible Schema View sidebar with shared sidebar shell#1875

Merged
kmcginnes merged 1 commit into
aws:mainfrom
kmcginnes:slice-2-schema-sidebar
Jul 7, 2026
Merged

Add collapsible Schema View sidebar with shared sidebar shell#1875
kmcginnes merged 1 commit into
aws:mainfrom
kmcginnes:slice-2-schema-sidebar

Conversation

@kmcginnes

@kmcginnes kmcginnes commented Jun 30, 2026

Copy link
Copy Markdown
Collaborator

Description

Adds a collapsible, persisted sidebar to the Schema View, matching the behavior the Graph View sidebar already has, and resolves the open auto-open question from #1541.

What users get:

  • Collapse / expand — click the active tab to collapse the sidebar to an icon strip; click any tab to reopen it.
  • Persistence — the active tab and sidebar width are remembered across sessions (new schema-view-layout IndexedDB key).
  • Auto-open details — a toggle in the Details panel header (enabled by default); selecting a single node type or edge connection switches to the Details tab. Multiple/cleared selections do not, so the user is never dumped on an empty Details state. This preference is persisted and independent from the Graph View's.

The shared sidebar shell (CollapsibleSidebar + tab sub-components) is extracted to @/components now that a second view needs it, and the Graph View sidebar is refactored onto it — so both views share one presentational implementation and one default width. As a small consistency pass that the shared shell motivates, all sidebar-header buttons now use the icon-small size.

A prior PR (#1874) did the graph-view layout rename + hook flattening this builds on.

Validation

  • pnpm checks passes (types, lint, format).
  • pnpm test passes. New coverage: schemaViewLayout.test.ts (toggle/close/resize/persist + all three auto-open states + toggle states), toSchemaGraphSelection.test.ts (the single-selection auto-open gate), and component-level collapse/reopen in SchemaExplorerSidebar.test.tsx.
  • Reviewer focus: confirm the Schema View sidebar collapses on active-tab click, reopens on any tab, persists width/tab across reload, and that auto-open only fires for a single selection.

How to read

  1. CollapsibleSidebar.tsx — the extracted shared shell (Resizable + Radix tab sub-components); owns the closed/default width
  2. schemaViewLayoutDefaults.ts — the SchemaViewLayout type + default (dependency-free leaf)
  3. schemaViewLayout.ts — useSchemaViewSidebar hook (toggle/resize/close/auto-open)
  4. SchemaExplorerSidebar.tsx — the schema sidebar composed onto the shared shell
  5. SchemaGraph.tsx — wires selection → auto-open via the single-selection gate (shouldAutoOpenDetailsForSelection)
  6. Sidebar.tsx — the Graph View sidebar refactored onto the same shell (its second consumer)

Related Issues

Check List

  • I confirm that my contribution is made under the terms of the Apache 2.0 license.
  • I have verified pnpm checks passes with no errors.
  • I have verified pnpm test passes with no failures.
  • I have covered new added functionality with unit tests if necessary.
  • I have updated documentation if necessary.

Add a persisted, collapsible sidebar to the Schema View (issues aws#1722,
aws#1541) and extract the shared presentational shell now that a second
view consumes it.

Schema View:
- schemaViewLayoutAtom (key "schema-view-layout") storing active tab,
  width, and detailsAutoOpenOnSelection
- useSchemaViewSidebar deep hook (toggle, resize, close, auto-open,
  toggleDetailsAutoOpen)
- collapse-to-icon-strip behavior; auto-open details only fires for a
  single selection (shouldAutoOpenDetailsForSelection), matching the
  graph view — a multiple/cleared selection no longer yanks the user to
  the empty Details state
- DetailsPanelHeader and the Node/Edge Styling panels all carry the
  sidebar close button

Shared shell:
- extract CollapsibleSidebar + tab sub-components to @/components, and
  refactor the Graph View sidebar onto it (its second consumer); drop the
  now-unused CLOSED_SIDEBAR_WIDTH constant. BadgeIndicator keeps wrapping
  every trigger in `.stack` as before.
- CollapsibleSidebar owns the closed/default width directly (no
  defaultWidth prop); SidebarTabs no longer takes an unused slot prop.

Both sidebars share one default width (DEFAULT_SIDEBAR_WIDTH); the schema
view no longer defines its own width constant.

Sidebar-header buttons are uniformly size "icon-small" across both views
(schema Details header plus the graph view's auto-open and refresh
buttons).

Auto-open: treat undefined detailsAutoOpenOnSelection as enabled, and
toggle via toggleDetailsAutoOpen so the button flips state internally.
All three value states are covered by tests in both views.

Docs: document the schema sidebar in docs/features/schema-view.md and
align "Schema Explorer" → "Schema View" wording in
docs/agents/{schema,product}.md.

@noel-improv noel-improv left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

lgtm, just a few non-blocking findings posted for confirmation.

const [graphSelection, setGraphSelection] = useState<SelectedElements | null>(
null,
);
const { autoOpenDetails } = useSchemaViewSidebar();

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

non-blocking: SchemaGraph calls useSchemaViewSidebar() only for autoOpenDetails but the hook reads the atom with useAtom (schemaViewLayout.ts:11), so the whole Cytoscape canvas subscribes to the layout atom. Could the write path use useSetAtom instead so a sidebar resize or tab click doesn't re-render the graph?

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is a non-issue because we use React Compiler to reduce re-renders based on unused subscriptions.

const newSelection = toSchemaGraphSelection(selected);
setSelection(newSelection);

if (shouldAutoOpenDetailsForSelection(newSelection)) {

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[non-blocking]:shouldAutoOpenDetailsForSelectionautoOpenDetails() fires on every single selection and detailsAutoOpenOnSelection defaults to true (schemaViewLayout.ts:38, ?? true). So selecting a node force-switches the sidebar to Details even when I'm mid-edit in Node Styling. I recall speaking about persisting states during session or did you want selection to override a tab I've explicitly opened or only a closed sidebar?

@kmcginnes kmcginnes Jul 7, 2026

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Style editing is inside a dialog and is therefore the user can't change the selection.

However, the search and node expansion sidebars are cases where you could be in the middle of editing and change your selection in the canvas. That said, this behavior has existed for quite a while and should be expected. The edits you're in the middle of making in the search and expansion sidebar should remain if you switch back to that sidebar, so it shouldn't be an issue.

reconcileMapByKey,
),
atomWithLocalForage("graph-view-layout", defaultGraphViewLayout),
atomWithLocalForage("schema-view-layout", defaultSchemaViewLayout),

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[non-blocking]: atomWithLocalForage("schema-view-layout", defaultSchemaViewLayout) is registered with no reconcile function, unlike the sibling atoms on lines 80/86/96/102/110 that all pass reconcileMapByKey. With the Schema View open in two tabs, does a resize or tab switch in one get clobbered when the other writes its stale layout back?

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, currently, by design. I have backlog items to refine this behavior but they haven't been pushed yet.

I consider this a minor frustration and not data loss, so I'm ok with the inconvenience for the time being.


import { DEFAULT_SIDEBAR_WIDTH } from "@/core/StateProvider/graphViewLayoutDefaults";
import { schemaViewLayoutAtom } from "@/core/StateProvider/storageAtoms";
import { renderHookWithJotai } from "@/utils/testing";

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[non-blocking]: Imports renderHookWithJotai, used in all 14 tests (lines 12–175). docs/agents/testing.md says to use renderHookWithState instead. just flagging incase release catches this during pass

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm choosing to fix this now. It might end up as a separate PR if the scope is large.

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I will do this as a follow up as it is larger than I hoped.

return (
<Resizable
size={{ width: isSidebarOpen ? sidebarWidth : CLOSED_WIDTH }}
minWidth={isSidebarOpen ? DEFAULT_SIDEBAR_WIDTH : CLOSED_WIDTH}

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[non-blocking]: The shared shell sets minWidth={DEFAULT_SIDEBAR_WIDTH} (400) when open, and the schema default width is now 400 too. The old schema sidebar floor was 350 (DEFAULT_SCHEMA_SIDEBAR_WIDTH in the now-deleted schemaExplorerLayout.ts). Was raising the min to 400 intentional? It might be worth testing on a narrow screen to ensure draggability and that the canvas doesn't lose room.

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is just cleaning up a minor oversight in past code. They should never have been different, so bringing them into consistency was always the goal.

There are likely many issues with smaller screens, as this is primarily a desktop app. However, those issues are now consistent across both views and should be resolved in the same way — but that's not the intent of this PR.

@kmcginnes kmcginnes merged commit 7299c22 into aws:main Jul 7, 2026
3 checks passed
@kmcginnes kmcginnes deleted the slice-2-schema-sidebar branch July 7, 2026 18:56
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.

Add collapsible sidebar to Schema Explorer Add auto show details option to schema explorer sidebar

2 participants