feat(channels): channel spaces and a structured task Activity view#3784
feat(channels): channel spaces and a structured task Activity view#3784puemos wants to merge 57 commits into
Conversation
|
Merging to
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 |
|
React Doctor found 3 issues in 3 files · 3 warnings. 3 warnings
Reviewed by React Doctor for commit |
|
✅ Visual changes approved by @puemos — baseline updated in 6 changed. |
4b6aa1a to
0fc2774
Compare
Analyze the spaces/task-view layout mockup against what exists today (Channels alpha, PanelLayout tabs, task thread, PR review) and lay out a phased prototype plan built on existing pieces, with deferred items and open questions called out. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
…ty panel) With Channels on: the sidebar scopes to the active channel (space) with Context/Loops/Artifacts nav, pinned + recent items, and an Arc-style dot switcher (starred channels; click/swipe/Ctrl+Alt+arrows, slide transition). Title bar swaps the tab strip for a search pill plus Activity and Inbox icons. The task thread panel becomes an Activity panel with Timeline/Artifacts/Comments tabs — artifacts derived from the thread, run output, and Slack link, with live PR state and comment counts. The task tab strip's + is now a chat/terminal/canvas menu (only terminal enabled). Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
… cards, gear The "#" dot now opens a browse-all-channels menu (picking one opens it as a space) instead of navigating to /website, whose index redirect snapped the sidebar straight back into a space. The "+" no longer jumps to the create modal: it lists existing channels to add as spaces (starring them so the dot persists) with "New channel" at the bottom. The personal #me space is always first in the dot row (created lazily on first click) and is the default scope on load. Pinned/recent sidebar items get a hover card with kind, run status, author, and last update. A Configure gear sits beside the account switcher. The redundant channel-header section tabs are removed — the space sidebar owns those entries now. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
The "#" dot no longer opens a popover: it toggles the sidebar body into the all-channels list in place; picking a channel opens it as a space. The "+" now opens a temporary draft space, Arc/Zen-style — a hollow dashed dot appears in the switcher and the sidebar becomes a chooser to attach an existing channel (starring it so the dot persists) or create a new channel. Selecting any space dismisses the overrides; any navigation while a picker is open also dismisses it, covering re-selecting the current channel where the route doesn't change. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
…pe, chrome-free browse
Browse mode ("#") now shows purely the channel list with no nav chrome. The "#me" glyph moves into the dot group as its leftmost member; added spaces keep star-creation order so new ones always append on the right. Right-clicking a dot opens a context menu with an emoji grid (the emoji replaces the dot, persisted locally) and a Remove space action for starred channels. Horizontal swipe now works anywhere on the sidebar (space, browse, or draft view) and moves strictly one space per gesture — inertia events extend a quiet-period lock instead of re-firing. The new-space chooser drops the "Channels" subheader for a search field.
Generated-By: PostHog Code
Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
Pinned/recent rows now use a Base UI PreviewCard instead of a tooltip: a panel-styled card with the item's icon, full title (so the row's built-in truncation tooltip is suppressed by passing a non-string label), kind and freshness line, a colored status badge, and the author with their avatar (gravatar for task creators, initial fallback for canvas authors). Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
The space sidebar's Recent section gains the old task-list header controls (minus Add folder): a search toggle with inline input, and a filter menu for created-by (anyone / me / other people) and run status. Rows now show the relative time at rest and swap to pin + archive hover actions exactly like the old task rows — pin works for tasks and canvases (pin-to-channel), archive for tasks only, using the existing archive flow with its undo toast. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
…re-session swipe Three fixes from prototype feedback. The personal space now shows only your items: the shared "me" folder can hold other people's canvases/tasks, so anything with a known non-you author is dropped (unknown authors stay, and nothing filters until the current user loads). The Activity Timeline becomes the task's full history — creation, the user messages sent to the agent (derived from the session, what used to live "inside the thread"), human comments, artifact announcements, the run-output PR fallback, and the run's terminal status — instead of only the sparse human thread. The swipe handler is rewritten as a gesture-session latch (the approach use-gesture's own docs recommend for wheel inertia, without taking the dependency): events under 250ms apart form one session, the axis is decided once per session so diagonal scrolling can't flap, and each session fires at most once — a fast fling with a long inertia tail moves exactly one space. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
…r menu Swiping/cycling no longer wraps around the ends — running past the last space clamps instead of jumping back to the first, which read as the switcher "swiping all around". The gesture gap drops to 150ms so two deliberate back-to-back swipes register as two moves while inertia tails still can't re-fire (their tiny deltas never reach the threshold). The Recent filter menu is rebuilt with the same DropdownMenuRadioGroup construction as the task list's filter menu, so the rows are compact, left-aligned, and consistent with every other menu. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
The New task row moves from the top of the space sidebar to below the channel header and Context/Loops/Artifacts rows, sitting just above Pinned — per the annotated screenshot. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
The session latch guaranteed one fire per gesture but swallowed the next swipe when it started while the previous swipe's inertia was still streaming (or right after vertical scrolling axis-locked the session) — repeat swipes only worked if you paused, which read as random. Add Lethargy-style burst re-arm: a horizontal delta that reaches 15px and 2.5x the recent stream level re-opens a spent or vertically-locked session, so back-to-back swipes each count while decaying inertia still can't re-fire. Fire threshold drops to 50px for snappier response. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
Per feedback: the footer goes back to just the account/project switcher (its dropdown still carries Settings). Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
…wipes Channel Pinned/Recent rows resolved filed tasks against the mine-only task list, silently dropping every teammate's task while their canvases (project-wide query) showed — resolve against all users' tasks instead (the personal space's ownership filter still applies). The swipe re-arm gains two guards against one fling moving several spaces: a fired session can only re-arm after a 250ms cooldown (inside that window the fling's own ramp/peak deltas could pass the burst test), and for 800ms after a fire, a "new" session opened by a sparse inertia tail that outlasted the gesture gap parks on the vertical axis — only a genuine burst can turn it back into a swipe. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
…show
The previous fix (all-users task query) returned zero tasks for regular members, so Recent showed only canvases. Switch the space sidebar to the same source the channel home uses: resolve the folder channel to its backend channel and read useChannelFeed (server-side getTasks({ channel })), which returns every filed task as a full object regardless of author — no fragile join against a separately-filtered task list. The personal #me ownership filter still applies on top.
Generated-By: PostHog Code
Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
Replace the whole gesture-session + burst-re-arm machinery (which could double-fire) with macOS-Spaces semantics: accumulate horizontal wheel delta, fire once when it crosses 40px, then lock until the wheel is quiet for 250ms. Inertia keeps the lock alive (it never re-fires); the lock releases only after the fling fully stops, and the next swipe re-arms. No speed dependence, no heuristics — one swipe moves exactly one space, clamped at the ends. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
…n swipe Three fixes. Timeline aesthetics: lifecycle events (task created / completed / failed) become compact markers — a small real person avatar for "created", a small colored status glyph for the terminal state — instead of oversized gray avatar boxes. User messages now render as proper message rows with the author's real avatar (gravatar/initials) rather than a generic person icon. Browse-to-pin: clicking a channel from the all-channels browse list now stars it, so it becomes a permanent space dot rather than a transient visit; captured from the store before setCurrentChannel clears the browsing flag. Swipe: add a hard minimum interval between switches on top of the quiet-gap release, so a sparse inertia tail whose gaps exceed the quiet threshold still can't fire a second switch — one physical swipe moves exactly one space regardless of the tail's shape. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
Clicking a channel in the "#" all-channels list now just shows that channel's activity in the main view — it no longer scopes the sidebar into a space or stars/pins the channel. The browse directory stays open in the sidebar while you preview channels; only non-browse navigation (a dot, deep link, in-space nav) adopts a channel as the current space. Closing the directory ("#" again) returns to the current space (or the landing) so the preview leaves no trace. Channels still become spaces only via "+" (or #me).
Generated-By: PostHog Code
Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
The "created" and "completed/failed" lifecycle rows used a compact small-glyph marker while messages and the PR row used the full ThreadItem avatar layout, so the timeline looked mixed. All rows now use the same ThreadItem shape: a large gutter avatar (the person's real avatar for "created", a neutral status-icon avatar for terminal states — the same avatar the artifact rows use) plus a header with the title, a muted action suffix, and the timestamp. Every row in the timeline now reads alike. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
The Artifacts tab already gathered the PR (from thread pr_created events / run output — the same PR shown in the Timeline), canvases, and the Slack thread. Add the files the agent uploads during the run (plans, outputs, references, skill bundles) — read defensively off the run JSON since they aren't on the typed TaskRun — each opening via a freshly presigned URL. User attachments (task inputs, not generated output) are skipped. So the tab now collects everything produced during the session. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
…anvases/plans Timeline (direction A): lifecycle events (created / run finished) are now slim nodes sitting on a continuous vertical rail down the avatar column, while messages/comments/artifacts stay full avatar rows hanging off the same rail — so the bodyless events no longer look like empty chunky rows. Timestamps are right-aligned on every row. Artifacts (critical): stop listing internal upload blobs (the UUID-named .pack/skill/output files). The tab now shows a curated set gathered across ALL runs of the task — PRs (thread events + each run's output PR), canvases, and plans (run-uploaded artifacts of type "plan"), plus the originating Slack thread. Adds useTaskRuns to fetch every run; plan names that are raw UUIDs fall back to "Plan". Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
The account/project/org menu no longer takes a full two-line card at the bottom of the sidebar in the spaces layout. ProjectSwitcher gains a "compact" variant — a single ~28px user avatar trigger — placed at the right end of the title bar next to the bell/inbox/PostHog Web. The dropdown body is unchanged (user header, project + org switchers, Discord/changelog/learn-more, settings, logout) but anchors to a fixed width and right-aligns under the avatar. The bottom card stays for the non-spaces Code layout. Frees the sidebar's bottom for the space's pinned/recent content. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
…v, drop dots/emoji/swipe Design + naming overhaul of the flag-gated layout: - The channel header is now a switcher: clicking "# channel" opens a searchable popover — #me first, then starred channels, then the rest — with right-click star/unstar and a "New channel…" entry. Replaces the dots rail entirely (dots, "#" browse, "+" draft are removed, along with swipe/keyboard cycling, the slide animation, and the per-channel emoji picker). - Search / Inbox / Activity move out of the title bar back into the sidebar, above the channel switcher, with a separator between them. The title-bar search pill and Activity/Inbox buttons are gone. - The "spaces" concept is renamed to channels everywhere: SpaceSidebar→ChannelSidebar, SpaceNav→ChannelNav, SpaceItemRow→ChannelItemRow, useSpaceItems→useChannelItems, spaceStore→currentChannelStore (now just currentChannelId), useSpacesLayout→useChannelsLayout, SPACES_LAYOUT_FLAG→CHANNELS_LAYOUT_FLAG. The flag key stays "code-spaces-layout" to match the live PostHog flag. - Analytics: switcher picks track as open_channel/sidebar; the space_switch/browse/draft events and method/open props are removed. Typecheck + biome clean, 2089 UI tests pass. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
…ter menu Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
…channels, switcher fixes - Account/project menu returns to the sidebar bottom (compact title-bar pill removed) - New task is the first global nav item, above Search (channel-scoped) - Channel switcher popover: override quill's gap-4 + unlayered padding/width so it reads as a tight menu; scroll-mask the list - mod+1..4 jump to starred channels via useHotkeys (SWITCH_TASK yields in the new layout); Kbd hints on rows - Skeleton loading rows for pinned/recent while the channel feed loads Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
#me now has its own ⌘0 shortcut, and starred-channel shortcuts run the full ⌘1-9 range instead of stopping at 4. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
… item - Switcher rows get a hover-revealed star toggle (always visible when starred); right-click keeps working - Channel header (feed) gets a star button next to the channel name - Channel sidebar gains a Feed row above Context that routes to the channel home - Star/unstar tracked as channel actions on both surfaces Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
…+ side popover - Bring Command Center back as a global nav destination inside a channel (it was only reachable from the pre-channel landing nav) - Search / Inbox / Activity / Command Center become a 4-up grid of square icon tiles, Arc-style: label in the tooltip, count badge in the corner - Add a star toggle beside the channel switcher trigger so the header matches the switcher rows and the feed header - Channel switcher popover opens to the right of the sidebar instead of below, so it no longer covers the channel list Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
…pover clears sidebar - Nav tiles are a fixed 48px instead of aspect-square in a fluid grid, so they no longer balloon as the sidebar widens. Four fit inside SIDEBAR_MIN_WIDTH, so the row never wraps. - Each tile gets a caption under its icon, so the destination is legible without hovering; the tooltip keeps the full name plus a properly formatted shortcut. - New task moves below the launcher row. - The switcher star becomes an overlay parked in a reserved well inside the trigger rather than a sibling button, so the trigger keeps a predictable full-row width. - The switcher popover offset now clears the row's 8px inset plus an 8px gap, landing it just past the content pane border instead of hovering over the sidebar. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
… a rule The row of square tiles couldn't carry its own labels: four squares across SIDEBAR_MIN_WIDTH leave ~44px of caption, so "Command Center" truncated to "Comm…". Segmented-control practice is to size every cell to the longest label and keep labels to one or two words, so the cells become landscape pills in a 2x2 — icon beside an 11px label instead of a 10px caption crammed under it, with "Command" abbreviating the longest name and the tooltip carrying it in full. Also drops the per-tile borders (four competing outlines) for a filled surface with a three-step rest/hover/selected progression, moves counts inline to the trailing edge, and separates New task from the launcher with a rule — it acts on the current channel rather than being a global destination. Widths stay fixed rather than fluid, so the pills don't balloon as the sidebar widens. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
…con row, New task under the switcher - Search leaves the sidebar nav for the title bar, beside the history controls — it is chrome rather than a destination, and it keeps company with the back/forward group. - The remaining destinations (Inbox, Activity, Command Center) collapse to a single row of icon-only buttons; names and shortcuts move into tooltips, and counts become corner notification badges. - New task moves under the channel switcher, where it reads as an action on the current channel rather than a global destination. Its own separator is gone, since ChannelsSidebar already rules off the nav. ChannelNav no longer needs a channelId now that New task has moved out. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
…drop nav rule - The switcher trigger sized itself off its contents, and the 24px star well only existed on starrable channels — so #code rendered 4px taller than #me and everything below shifted on every switch. The trigger now has a fixed height and always reserves the well. - #me shows a dimmed, non-interactive star in both the trigger and the dropdown row. It is permanently pinned to slot 0 so there is nothing to toggle, but the slot keeps every row's trailing edge aligned and the trigger identical across channels. - New task gains an opt-in elevated variant (quill outline button: distinct fill plus a hairline border) so it reads as the primary action rather than another nav row. The legacy sidebar keeps the plain row. - Drops the rule between the nav icons and the switcher — the bordered switcher already separates them. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
…annel list As a bordered row directly beneath the channel switcher, New task was a second box of near-identical weight — two equal-weight controls competing at the top of the sidebar, with plain rows underneath. Neither won, and the stack read top-heavy. Moving it to a FAB separates action from navigation spatially: the top is now one chrome control plus flat destination rows, and the primary action gets primary treatment. It reuses the accent-filled round button the channel list already floats over its own list (ChannelsFab), so the two views stay coherent. The "Draft" badge becomes a pip on the button, drawn in the button's foreground so it stays legible on the accent fill, with the draft state also called out in the tooltip. Reverts the elevated NewTaskItem variant added for the previous attempt, now that nothing uses it. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
The channel FAB now opens a menu instead of going straight to the task composer, offering New task and New canvas — matching the "+" dropdown already on the channel rows. New canvas reuses the existing create path (useCreateAndOpenDashboard behind trackAndCreateCanvas) rather than a second one, so it creates on the default template, enters edit mode, navigates, and reports creation the same way every other canvas entry point does. The menu opens upward, since the button sits at the bottom. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
…arch leads the history controls The title bar's left strip is pinned to the sidebar width and none of its contents shrink. Its intrinsic width is 228px — 78px traffic-light inset, 62px logo + toggle, 80px search + history buttons, 8px trailing padding — so at a 240px minimum the two groups sat exactly one 12px gap apart and search was pressed against the sidebar edge. The minimum is now 272, leaving them ~44px apart. Search also moves ahead of the history buttons, so the history group rather than search sits against the edge. createSidebarStore gains an optional minWidth that clamps live sets and rehydrated values alike; without it a width persisted under the old 240 minimum (or the legacy Code width adopted by the channels-sidebar migration) would survive below the new floor, since nothing re-clamped on load. The skills sidebar passes no minWidth and is unaffected. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
⌘N (and every other generic entry point — the command menu, the sidebar "+") called openTaskInput with no space, which routed to the unscoped /code new-task screen even while a channel was open, so the task was created outside the channel. openTaskInput now routes to the current channel's new-task screen when one is set. A current channel only exists while the channels layout is on, so this is gated on that flag without threading it through every caller — and ChannelsSidebar now clears the scope when the layout goes away, since flags resolve after first paint and can flip mid-session, which keeps that stand-in honest. WebsiteNewTask also has to honour prefill for this to be safe: it renders on a route that already merges prefill into the view, but never read it, so redirecting a prefill-carrying call (a deep link's prompt, a report association) would have silently dropped it. It now passes the same prefill props /website/new does. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
Open over the feed, the channel list competed with the text around it — quill's default popover shadow is faint on a dark surface, so nothing separated the menu from its backdrop. Adds a scrim that fades in with the popover, reusing the tokens and easing of the sidebar-peek scrim in __root so the two dims read as one effect. It is portaled to the body to sit above the app but below the popover's z-50, and stays pointer-transparent so close-on-outside-press still works; the docked sidebar carries no z-index, so it dims along with everything else. The popover also picks up a deeper shadow to lift it off the dimmed backdrop — with a `!` override, since quill sets box-shadow from unlayered CSS that beats plain utilities. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
…, and deepen it Replaces the hand-rolled scrim with Popover.Backdrop. Base UI is a peer dependency of quill imported by specifier, so quill's Popover and the parts from @base-ui/react share one instance and one context — the backdrop reads the open state itself, mounts and unmounts with the popup, and exposes data-starting-style / data-ending-style, which replaces the manual open prop, the always-mounted createPortal, and the opacity toggle. It is also interactive, so clicking the dim now closes the menu. It still needs Popover.Portal: the backdrop renders in place, and ResizableSidebar's transform makes the sidebar a containing block that would clip a fixed overlay. Deepens the dim from blackA-2/5 to blackA-4/7, since the feed stayed legible enough to compete at the old strength. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
… states Cuts the PR's added comments by a quarter, keeping only non-obvious why and cross-file contracts and dropping narration of what the code plainly does. Also fixes a stale one: the shortcut note still said mod+1-4 after the range widened to mod+0-9. Removes ProjectSwitcher's "compact" variant. It was added for the title-bar avatar, which later moved back into the sidebar, leaving the branch, its props and two imports unreachable. Two convention fixes: ChannelSidebar's empty states now use quill's <Empty>, matching how ChannelsList renders its own in the same sidebar; and ActivityTimeline's static rail offset moves from an inline style to a Tailwind utility. StatusVariant is no longer exported, since it is only used in the file that declares it. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
… test Two changes in this PR reached users who don't have the channels layout. The sidebar minimum went from 240 to 272 for everyone, but the extra room exists for the title bar's search button, which only the new layout renders — without it the strip needs 208px and fits 240 comfortably. Anyone on the old layout with a narrow sidebar would have been widened for nothing. SIDEBAR_MIN_WIDTH returns to 240 and the new layout raises its own floor: ResizableSidebar takes an optional minWidth, and ChannelsSidebar supplies it and lifts an already-narrower width once, only while the flag is on. The channel header's star also rendered unconditionally, so it appeared in the pre-existing channels alpha, which reaches that header too. It is now behind the flag like the rest of the new layout. Adds a test for openTaskInput, the riskiest shared change, pinning that creates go to Code (or an explicitly requested website space) until a channel is scoped, which only the new layout does. Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
…s in the sidebar A private channel now shows a lock where a public one shows a hash, the Slack convention, so privacy reads at a glance. One helper (channelGlyph) decides it for every surface that renders channel identity — sidebar list, switcher trigger and rows, channel header, breadcrumb, command palette — which also retires the awkward trailing lock the #me row carried, since the leading glyph now says it. The personal #me channel is the only channel that is private today: neither the folder Channel nor the backend TaskChannel carries a privacy flag, so isPrivateChannel is the single place that has to learn about one when it lands. Also moves the channel sidebar off the absolute gray scale and onto the theme's fill/foreground tokens. The fill tokens are color-mix(foreground N%, transparent) — relative to the surface and tuned per mode (4% light, 7% dark) — whereas gray-3 is absolute, and its relationship to the chrome it is painted on inverts between modes: 3 L* below a near-white chrome in light, where darker reads heavier, so the nav's filled chips came out as muddy beige slabs. They now follow the same transparent-rest, fill-on-hover idiom as every other sidebar control.</body> Generated-By: PostHog Code Task-Id: c401c7cb-e436-4da3-80bf-1d3008ee5d38
A review of the prototype turned up ten verified defects, three of which bite every dogfooder the moment the flag is on. Fixed here, along with the forks the prototype introduced against the code it was copied from. The three that mattered most: - The channel sidebar fabricated the name `"channel"` while the folder list was still loading and handed it to `useBackendChannel`, whose resolve-or-create effect then provisioned a real backend channel called "channel" on every cold load. `useChannelItems` now resolves the name itself and reports loading until it knows it, so no caller can invent one. That also fixes the personal channel briefly showing other people's canvases. - Gating `BrowserTabStrip` behind the flag unmounted the only global owner of Cmd+W, whose handler exists specifically to stop Electron's Window > Close from taking the window. A headless `TabShortcutFallback` holds the key wherever the strip isn't mounted — including the settings shell, which never mounted it either. - Nothing cleared `currentChannelId` on a project switch or logout, so `openTaskInput` filed the next task into the previous project's channel. `useCurrentChannel` now resolves the id against the live list and self-heals; the auth side effects and channel deletion clear it explicitly. Also: `mod+0` leaves the starred-channel chord (Electron's main process owns CmdOrCtrl+0 for "Actual Size", which a renderer preventDefault can't beat), so than one that only mounts once a channel is scoped; the Archived row comes back, since the layout offers an Archive action on every row; the command-center badge counts live tasks instead of persisted cell ids; and the auto-scope latch resets when the flag reads false so a flag flicker can't strand the sidebar unscoped. Consolidations, so the prototype's copies can't drift from the originals: `useThreadConversation` is now shared by ThreadPanel and ActivityPanel (the @agent authorization rule and the draft-restore-on-failure existed twice); `usePrArtifact` and a shared `parseHttpsUrl` replace three PR-row copies, and give WebsiteChannelArtifacts the github-origin check the other two had; run status has one label map instead of four disagreeing ones; `CountBadge` absorbs three copies of the 99+ cap. Conventions: run artifacts are decoded with a Zod schema, and the sidebar's empty states use the prescribed `<Empty>` composition. Also fixed while here: the shortcuts sheet no longer advertises keys nothing owns in the current layout; nav clicks carry a `layout` property so the two sidebars are distinguishable in analytics; `CHANNELS_SPACE_VIEWED` moves to the shell so space adoption doesn't read as zero once the flag lands; the Activity tabs use quill's Tabs primitive for real tab semantics; and the channel sidebar sits behind an error boundary so one bad row can't take out the project switcher. The Customize-sidebar settings page is hidden under the flag rather than left silently inert — the layout's nav is fixed. Sidebar customization and the global Loops list are deliberately not carried over; see the PR description. Generated-By: PostHog Code Task-Id: 4020e833-acf4-46ee-bdca-88e4a60e225d
cbbe30e to
89657e3
Compare
puemos
left a comment
There was a problem hiding this comment.
Validated the findings below against the current head and traced each through its call sites.
Keep cold channel deep links scoped to their route instead of racing with the personal-channel default. Carry the selected historical pull request into the review surface and clear that override when review closes. Generated-By: PostHog Code Task-Id: 6190e713-9b80-43d9-a05c-5e3b1ecdf297
Wait for the current-user query before building the personal channel item list, preventing a cold load from briefly showing other members' work. Generated-By: PostHog Code Task-Id: 6190e713-9b80-43d9-a05c-5e3b1ecdf297
Remove the disabled roadmap-only chat option and its one-action dropdown. The add button now opens a terminal directly in every layout. Generated-By: PostHog Code Task-Id: 6190e713-9b80-43d9-a05c-5e3b1ecdf297
Reset the space-viewed latch when the channels world is left so a later entry records a new view, matching the event's documented semantics. Generated-By: PostHog Code Task-Id: 6190e713-9b80-43d9-a05c-5e3b1ecdf297
Use shared fixture defaults, keep ownership implementation private, and drop a memo-identity assertion while retaining the channel item behavior and integration regressions. Generated-By: PostHog Code Task-Id: 6190e713-9b80-43d9-a05c-5e3b1ecdf297
Remove component narration and restatements while retaining comments that document safety boundaries, regression-prone ordering, and non-obvious invariants. Generated-By: PostHog Code Task-Id: 6190e713-9b80-43d9-a05c-5e3b1ecdf297
|
Superseded by the reviewable four-PR stack:
The stack tip is byte-for-byte equivalent to this branch, and every stack commit is GitHub-verified. |
Problem
Everything in Code hangs off one flat task list. There's no notion of where work lives, so a task, its canvases and its discussion have no shared home, and the task view has nowhere to put anything that isn't the agent transcript.
This reorganises the app around channels: the sidebar scopes to the channel you're in, and a task gets a structured Activity panel beside the transcript.
Behind
code-spaces-layout(plusproject-bluebird). Flag off is byte-for-byte the current experience — that's asserted by tests, not just by inspection.Changes
Channel-scoped sidebar. When you're in a channel the sidebar becomes that channel: a row of global destinations (Inbox / Activity / Command Center), a switcher that opens a searchable channel list, the channel's own sections, and its pinned + recent tasks and canvases with search and filters. Creating anything — ⌘N, the command menu, the FAB — files it into the channel you're in.
Task Activity panel. The thread panel gains Timeline / Artifacts / Comments. Timeline is the task's full history on a rail; Artifacts collects PRs, canvases, plans and the originating Slack thread across every run, with live PR state.
Channel switching. ⌘1–9 jump to starred channels, and a channel can be starred from the switcher or the channel header. Private channels show a lock instead of a hash, as in Slack.
Under the UI. The list-merging, run-status and run-artifact logic moved to
@posthog/coreas pure, tested functions. Three copies of the PR-artifact row and two of the thread-conversation logic were consolidated intousePrArtifactanduseThreadConversation, so the new surfaces can't drift from the ones they were copied from.The last commit is a review pass over the prototype: ten verified defects, the three worst being a cold load provisioning a backend channel literally named "channel", the flag unmounting the only global owner of Cmd+W, and a project switch leaving the next task filed into the previous project's channel.
How did you test this?
pnpm --filter @posthog/ui test— 2170 passing.pnpm --filter @posthog/core test— 2542 passing.pnpm typecheck— 24/24 packages clean.Automatic notifications
Created with PostHog Code