From 536abea2e2ed3bee160cf16a12b23558ed6e3fa3 Mon Sep 17 00:00:00 2001 From: David Hill <1879069+iamdavidhill@users.noreply.github.com> Date: Fri, 13 Mar 2026 15:08:23 +0000 Subject: [PATCH] fix(app): restore sidebar dash and sync session spinner colors (#17384) --- .../src/components/session/session-header.tsx | 8 +- .../app/src/pages/layout/sidebar-items.tsx | 147 +++++------------- .../src/pages/session/message-timeline.tsx | 4 +- packages/app/src/utils/agent.ts | 12 ++ 4 files changed, 65 insertions(+), 106 deletions(-) diff --git a/packages/app/src/components/session/session-header.tsx b/packages/app/src/components/session/session-header.tsx index ae9d2800e..4c9e30e43 100644 --- a/packages/app/src/components/session/session-header.tsx +++ b/packages/app/src/components/session/session-header.tsx @@ -16,9 +16,11 @@ import { useLanguage } from "@/context/language" import { useLayout } from "@/context/layout" import { usePlatform } from "@/context/platform" import { useServer } from "@/context/server" +import { useSync } from "@/context/sync" import { useTerminal } from "@/context/terminal" import { focusTerminalById } from "@/pages/session/helpers" import { useSessionLayout } from "@/pages/session/session-layout" +import { messageAgentColor } from "@/utils/agent" import { decode64 } from "@/utils/base64" import { Persist, persisted } from "@/utils/persist" import { StatusPopover } from "../status-popover" @@ -132,6 +134,7 @@ export function SessionHeader() { const server = useServer() const platform = usePlatform() const language = useLanguage() + const sync = useSync() const terminal = useTerminal() const { params, view } = useSessionLayout() @@ -218,6 +221,9 @@ export function SessionHeader() { ({ id: "finder", label: fileManager().label, icon: fileManager().icon } as const), ) const opening = createMemo(() => openRequest.app !== undefined) + const tint = createMemo(() => + messageAgentColor(params.id ? sync.data.message[params.id] : undefined, sync.data.agent), + ) const selectApp = (app: OpenApp) => { if (!options().some((item) => item.id === app)) return @@ -330,7 +336,7 @@ export function SessionHeader() { >
}> - +
{language.t("common.open")} diff --git a/packages/app/src/pages/layout/sidebar-items.tsx b/packages/app/src/pages/layout/sidebar-items.tsx index 04d898134..5ce526103 100644 --- a/packages/app/src/pages/layout/sidebar-items.tsx +++ b/packages/app/src/pages/layout/sidebar-items.tsx @@ -9,14 +9,13 @@ import { Tooltip } from "@opencode-ai/ui/tooltip" import { base64Encode } from "@opencode-ai/util/encode" import { getFilename } from "@opencode-ai/util/path" import { A, useNavigate, useParams } from "@solidjs/router" -import { type Accessor, createEffect, createMemo, For, type JSX, on, onCleanup, Show } from "solid-js" -import { createStore } from "solid-js/store" +import { type Accessor, createMemo, For, type JSX, Match, onCleanup, Show, Switch } from "solid-js" import { useGlobalSync } from "@/context/global-sync" import { useLanguage } from "@/context/language" import { getAvatarColors, type LocalProject, useLayout } from "@/context/layout" import { useNotification } from "@/context/notification" import { usePermission } from "@/context/permission" -import { agentColor } from "@/utils/agent" +import { messageAgentColor } from "@/utils/agent" import { sessionPermissionRequest } from "../session/composer/session-request-tree" import { hasProjectPermissions } from "./helpers" @@ -102,94 +101,46 @@ const SessionRow = (props: { warmPress: () => void warmFocus: () => void cancelHoverPrefetch: () => void -}): JSX.Element => { - const [slot, setSlot] = createStore({ - open: false, - show: false, - fade: false, - }) - - let f: number | undefined - const clear = () => { - if (f !== undefined) window.clearTimeout(f) - f = undefined - } - - onCleanup(clear) - createEffect( - on( - () => props.isWorking(), - (on, prev) => { - clear() - if (on) { - setSlot({ open: true, show: true, fade: false }) - return - } - if (prev) { - setSlot({ open: false, show: true, fade: true }) - f = window.setTimeout(() => setSlot({ show: false, fade: false }), 260) - return - } - setSlot({ open: false, show: false, fade: false }) - }, - { defer: true }, - ), - ) - - return ( - { - props.setHoverSession(undefined) - if (props.sidebarOpened()) return - props.clearHoverProjectSoon() - }} - > - 0)}> -
0, - }} - aria-hidden="true" - /> - - -
- - - - {props.session.title} - +}): JSX.Element => ( + { + props.setHoverSession(undefined) + if (props.sidebarOpened()) return + props.clearHoverProjectSoon() + }} + > +
+
+ }> + + + + +
+ + +
+ + 0}> +
+ +
-
- ) -} + + {props.session.title} + +
+ +) const SessionHoverPreview = (props: { mobile?: boolean @@ -268,19 +219,7 @@ export const SessionItem = (props: SessionItemProps): JSX.Element => { }) const tint = createMemo(() => { - const messages = sessionStore.message[props.session.id] - if (!messages) return undefined - let user: Message | undefined - for (let i = messages.length - 1; i >= 0; i--) { - const message = messages[i] - if (message.role !== "user") continue - user = message - break - } - if (!user?.agent) return undefined - - const agent = sessionStore.agent.find((a) => a.name === user.agent) - return agentColor(user.agent, agent?.color) + return messageAgentColor(sessionStore.message[props.session.id], sessionStore.agent) }) const hoverMessages = createMemo(() => @@ -359,7 +298,7 @@ export const SessionItem = (props: SessionItemProps): JSX.Element => { return (
!!pending() || sessionStatus().type !== "idle") + const tint = createMemo(() => messageAgentColor(sessionMessages(), sync.data.agent)) const [slot, setSlot] = createStore({ open: false, @@ -689,7 +691,7 @@ export function MessageTimeline(props: { "opacity-0": slot.fade, }} > - +
diff --git a/packages/app/src/utils/agent.ts b/packages/app/src/utils/agent.ts index 7c2c81e74..390932a13 100644 --- a/packages/app/src/utils/agent.ts +++ b/packages/app/src/utils/agent.ts @@ -9,3 +9,15 @@ export function agentColor(name: string, custom?: string) { if (custom) return custom return defaults[name] ?? defaults[name.toLowerCase()] } + +export function messageAgentColor( + list: readonly { role: string; agent?: string }[] | undefined, + agents: readonly { name: string; color?: string }[], +) { + if (!list) return undefined + for (let i = list.length - 1; i >= 0; i--) { + const item = list[i] + if (item.role !== "user" || !item.agent) continue + return agentColor(item.agent, agents.find((agent) => agent.name === item.agent)?.color) + } +}