Skip to content

feat(ui): prototype static spaces sidebar - #4060

Closed
puemos wants to merge 26 commits into
mainfrom
posthog-code/static-spaces-sidebar
Closed

feat(ui): prototype static spaces sidebar#4060
puemos wants to merge 26 commits into
mainfrom
posthog-code/static-spaces-sidebar

Conversation

@puemos

@puemos puemos commented Jul 31, 2026

Copy link
Copy Markdown
Contributor

Problem

Prototype for a new sidebar design: get rid of the moving (sliding) sidenav and replace it with a single static nav where every space shows its tasks beneath it, and where spaces only appear once a user adds them to their sidebar (by adding an existing space or creating a new one) instead of listing all spaces by default.

Changes

  • Under the existing code-spaces-layout flag, ChannelsSidebar now renders a static SpacesSidebarNav instead of the 200%-width panes slider (the ChannelPanes track, swipe gesture, and route-scoping side effects are removed from the shell).
  • New SpacesSidebarNav: Home / Tasks / Inbox nav rows (Inbox has a "+" affordance), then every pinned (starred) space with its tasks expanded inline beneath it, an "Add space" menu (finding an existing space stars it; "New space" opens the create modal), and a pinned-agents placeholder section.
  • Pinning = starring: reuses the existing starred-channel shortcuts as the sidebar membership model — no backend changes. Expanded state per space is a persisted local store (spacesSidebarStore).
  • Space task rows reuse the existing useChannelItems + ChannelItemRow, so a space's tasks render identically to the old channel pane.

Screenshots to follow once run against a live backend.

How did you test this?

  • pnpm --filter @posthog/ui test — all 289 files / 2443 tests pass (rewrote ChannelsSidebar.test.tsx for the static nav; kept Archived-row and tracking coverage).
  • pnpm --filter @posthog/ui typecheck — clean.
  • pnpm biome check packages/ui/src — clean.

Automatic notifications

  • Publish to changelog?
  • Alert Sales and Marketing teams?

Created with PostHog Code

Generated-By: PostHog Code
Task-Id: 7698cad8-55a1-4e67-9657-91ce3e8f0a52
@trunk-io

trunk-io Bot commented Jul 31, 2026

Copy link
Copy Markdown

Merging to main in this repository is managed by Trunk.

  • To merge this pull request, check the box to the left or comment /trunk merge below.

After your PR is submitted to the merge queue, this comment will be automatically updated with its status. If the PR fails, failure details will also be posted here

@github-actions

github-actions Bot commented Jul 31, 2026

Copy link
Copy Markdown

React Doctor found 7 issues in 4 files · 7 warnings.

7 warnings

src/features/canvas/components/ChannelItemRow.tsx

src/features/canvas/components/SpacesSidebarNav.tsx

src/features/canvas/components/WatchListSection.tsx

src/features/canvas/components/WebsiteNewTask.tsx

Reviewed by React Doctor for commit 9f12ff6.

puemos added 4 commits July 31, 2026 22:05
…ace toggle

Generated-By: PostHog Code
Task-Id: 7698cad8-55a1-4e67-9657-91ce3e8f0a52
Generated-By: PostHog Code
Task-Id: 7698cad8-55a1-4e67-9657-91ce3e8f0a52
Generated-By: PostHog Code
Task-Id: 7698cad8-55a1-4e67-9657-91ce3e8f0a52
… language

Drops the Home/Tasks/Inbox rows (the ChannelNav icon row already covers
them), replaces the per-space tab strip with the channel header's own
tabs, and makes space rows behave like the rest of the sidebar: the row
opens the space, the disclosure caret folds it, the star (hover-revealed)
pins. The All spaces list becomes a section-labelled directory whose rows
open the space instead of silently pinning it, with a New space entry and
the ChannelsFab restored so the static layout keeps a create affordance.

Generated-By: PostHog Code
Task-Id: 0331ac58-0a1c-4b4e-b884-2ff7d8e71986

puemos commented Jul 31, 2026

Copy link
Copy Markdown
Contributor Author

Pushed a design pass over the prototype (e9de196): removed the Home/Tasks/Inbox rows (the icon nav already covers them), dropped the per-space tab strip in favour of the channel header's existing tabs, made space rows open-on-click with a proper disclosure caret and hover-revealed pin star, turned All spaces into a section-labelled directory whose rows open the space (clicking used to silently pin), and restored a create path in this layout via the FAB plus a New space row. Details in the commit message; AllSpacesSection now has unit coverage.


Created with PostHog Code

puemos added 21 commits July 31, 2026 23:18
…rectory

Sidebar feedback round: a space row is now a single click target that
folds its task list (no separate caret hover zone); the hover gear on the
right opens the space in the main view, and #me's lock moves into that
same trailing well. The header regains a tab strip under the channels
layout (Feed, Context, Loops, Artifacts, Recents) as the breadcrumb's
trailing slot, since the sidebar no longer carries page links. A My-tasks
switch above the pinned list narrows every space's tasks to the viewer's
own via the exported core ownership rule. All spaces docks at the bottom,
sheds its cube for a caret aligned with the space rows, and opens upward
to a capped, scrollable height.

Generated-By: PostHog Code
Task-Id: 0331ac58-0a1c-4b4e-b884-2ff7d8e71986
…ce task windows

Sidebar feedback round three. The space header swaps its trailing button
strip for quill line tabs (Feed/Context/Loops/Artifacts/Recents) on their
own row under the space name, matching Inbox/Activity; the header bar
grows via min-height so single-row breadcrumbs are unchanged. Each
space's task list leads with a "New session" row, shows a five-row
scroll window with View all pinned below, and its task rows are
draggable into the Command Center with the same text/x-task-id payload
as the code sidebar. Pinned spaces reorder by dragging their header row
(dnd-kit sortable, #me fixed first, order persisted in the sidebar
store). The filter row is labeled "Spaces" and its switch explains
itself in a tooltip.

Generated-By: PostHog Code
Task-Id: 0331ac58-0a1c-4b4e-b884-2ff7d8e71986
…ab icons

Sidebar feedback round four. Create moves to a New session button at the
top of the nav (the Fab is gone), landing on the composer which now
carries a Space dropdown to retarget where the task files — the typed
draft survives the switch. Space rows trade their inline New session row
for a hover plus beside the gear, and their task lists show five recents
flat (no inner scroll) with View all still leading to Recents. A
cross-space My tasks section sits above Spaces, each row wearing its
space's name in muted text and opening the task inside that space. The
header page tabs pick up their channelPages icons.

Generated-By: PostHog Code
Task-Id: 0331ac58-0a1c-4b4e-b884-2ff7d8e71986
The composer's space picker becomes a chip beside the Cloud/Local
workspace-mode select — same trigger shape, icon + name + caret — via a
new spaceSelector slot on TaskInput (channels new-task only; /code is
untouched). A space's own "+" still pre-fills that space; the sidebar's
global New session now always lands on #me, with the chip as the way to
retarget. Draft text survives the switch as before.

Generated-By: PostHog Code
Task-Id: 0331ac58-0a1c-4b4e-b884-2ff7d8e71986
…header

The cross-space My tasks list now builds ChannelItemModels through the
same core builder the space lists use and renders them as ChannelItemRows
— status dot, badge stacks, hover preview card, pin/archive menu — with
open routing each row into its own space. The space name rides in a new
optional contextLabel slot in the row's trailing stack, muted. The
section header drops the space-row shape for the same 12px section-label
type as the Spaces header beneath it, still folding on click.

Generated-By: PostHog Code
Task-Id: 0331ac58-0a1c-4b4e-b884-2ff7d8e71986
…e tabs

Drops the custom indicator-transition overrides so the header's page
tabs are the untouched quill TabsList variant="line" pattern, identical
to the Loops and Skills tab strips.

Generated-By: PostHog Code
Task-Id: 0331ac58-0a1c-4b4e-b884-2ff7d8e71986
The left-aligned outline treatment read oddly in the sidebar; the create
CTA is now quill's primary variant — elevated, centered, still sm-sized
to match the rows around it.

Generated-By: PostHog Code
Task-Id: 0331ac58-0a1c-4b4e-b884-2ff7d8e71986
…style

The composer's space menu now leads with the starred spaces in their
sidebar order (#me first), a separator, then the rest alphabetically.
Items use the switchers' flyout vocabulary — leading check well, the
space's own glyph (only #me carries one), left-aligned 13px name — and
the content gets a proper min width. The blanket cube/lock icons are
gone in favor of the channelGlyph rule.

Generated-By: PostHog Code
Task-Id: 0331ac58-0a1c-4b4e-b884-2ff7d8e71986
…on headers

The cross-space My tasks section becomes a Watch list: drag any task row
onto it (they all carry the text/x-task-id payload) to keep a local
reference, newest first, rendered with the same ChannelItemRows and
muted space names; a hover × forgets the reference. Watching is a
local-only pointer for now, persisted in the sidebar store. Both it and
the Spaces header now use the MenuLabel section style (the code
sidebar's "Sessions" look), with a Separator between the two sections.

Generated-By: PostHog Code
Task-Id: 0331ac58-0a1c-4b4e-b884-2ff7d8e71986
A dropped task only rendered if it happened to be in the viewer's loaded
task list, so drops of anything else stored a reference and showed
nothing. Watch entries now capture the title at drop time (rows put it
on the drag payload alongside the id), the list synthesizes a row for
any watched task the query doesn't hold, and a toast confirms each add.
Legacy bare-id entries are normalized on read.

Generated-By: PostHog Code
Task-Id: 0331ac58-0a1c-4b4e-b884-2ff7d8e71986
…r remove

Watch rows drop the relative-age text (they're references, not activity),
and removal now works everywhere: v0 persisted bare-id entries are lifted
to refs by a store migration so the × matches them, the × itself gets a
solid chrome backing and bolder glyph so it reads over the badges it
covers, and "Remove from watch list" joins the row's hover-card and
right-click menus for a discoverable path.

Generated-By: PostHog Code
Task-Id: 0331ac58-0a1c-4b4e-b884-2ff7d8e71986
Generated-By: PostHog Code
Task-Id: 0331ac58-0a1c-4b4e-b884-2ff7d8e71986
A search toggle joins the Spaces header (same icon-button + input recipe
as the channel sidebar's Sessions header): typing filters every space's
task list by title, spaces without a match step aside, and matching
spaces open on their matches regardless of fold state. Per-space lists
drop the five-row cap and View all — an unfolded space shows its whole
list, with the pinned-spaces region as the sidebar's single scroll
container so nothing nests scrollbars.

Generated-By: PostHog Code
Task-Id: 0331ac58-0a1c-4b4e-b884-2ff7d8e71986
All-spaces rows now carry a text/x-space-id drag payload and the pinned
region accepts them — dropping stars the space (one gesture instead of
the hover star) and lands it at the bottom of the user's order, ready to
reorder. The watch list stops going stale: each watched task gets its
own polled detail query, merged over the list copies, so a task the
task-list query doesn't return still renders with its real status dot
and badges instead of the synthesized quiet row.

Generated-By: PostHog Code
Task-Id: 0331ac58-0a1c-4b4e-b884-2ff7d8e71986
An opened space leads with its first five items; "Show more (n)" unfolds
the rest in place and flips to "Show less". Search still shows every
match uncapped, and the pinned-spaces region stays the single scroll
container.

Generated-By: PostHog Code
Task-Id: 0331ac58-0a1c-4b4e-b884-2ff7d8e71986
The search input no longer drops in as a second row under SPACES —
opening search swaps the section label for the input on the same line
(the Mine switch steps aside for the width and returns on close), with
Escape closing it. The header row holds a stable height either way.

Generated-By: PostHog Code
Task-Id: 0331ac58-0a1c-4b4e-b884-2ff7d8e71986
Each space page pushed its own ChannelHeader through the header store on
mount and nulled it on unmount, so switching tabs tore down and rebuilt
the whole header — breadcrumb, tab strip, indicator — which read as a
flicker. WebsiteLayout now renders one persistent ChannelHeader for the
five page routes (page derived from the pathname), so a tab switch just
updates the page prop and the indicator slides. Task detail, new task,
canvases, and legacy-layout scenes keep the store path unchanged.

Generated-By: PostHog Code
Task-Id: 0331ac58-0a1c-4b4e-b884-2ff7d8e71986
… hover star

Unpinning a starred space was buried in the All spaces directory. Now:
dragging a pinned row and releasing it outside the list unpins it
(in-place drops stay safe — the row itself is still the drop target),
every space row gets a right-click menu (Open space / New task / Unpin
space), and hover reveals a filled star between the plus and the gear
that unpins directly. #me stays fixed and offers no unpin.

Generated-By: PostHog Code
Task-Id: 0331ac58-0a1c-4b4e-b884-2ff7d8e71986
quill's default button paints --fill-expanded while aria-expanded, which
read as a permanent highlight on a section that's open most of the time.
The rotated caret already says open; hover feedback stays.

Generated-By: PostHog Code
Task-Id: 0331ac58-0a1c-4b4e-b884-2ff7d8e71986
Generated-By: PostHog Code
Task-Id: 0331ac58-0a1c-4b4e-b884-2ff7d8e71986
Outline alone read flat on the dark chrome; the button keeps the outline
variant but gains the gray-3 raised fill and a small shadow — elevated
without primary's shout.

Generated-By: PostHog Code
Task-Id: 0331ac58-0a1c-4b4e-b884-2ff7d8e71986
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