diff --git a/apps/web/src/features/chat/components/thread/index.tsx b/apps/web/src/features/chat/components/thread/index.tsx index 4d2fe6da0..9edda2d5a 100644 --- a/apps/web/src/features/chat/components/thread/index.tsx +++ b/apps/web/src/features/chat/components/thread/index.tsx @@ -45,6 +45,7 @@ import { Alert, AlertDescription, AlertTitle } from "@/components/ui/alert"; import { useFileUpload } from "@/hooks/use-file-upload"; import { ContentBlocksPreview } from "./messages/ContentBlocksPreview"; import { useApiKeys, useHasApiKeys } from "@/hooks/use-api-keys"; +import { useLastSelectedAgent } from "@/hooks/use-last-selected-agent"; import { Tooltip, TooltipContent, @@ -100,6 +101,7 @@ function NewThreadButton(props: { hasMessages: boolean }) { const [agentId, setAgentId] = useQueryState("agentId"); const [deploymentId, setDeploymentId] = useQueryState("deploymentId"); const [_, setThreadId] = useQueryState("threadId"); + const [lastSelectedAgent, setLastSelectedAgent] = useLastSelectedAgent(); const handleNewThread = useCallback(() => { setThreadId(null); @@ -135,8 +137,11 @@ function NewThreadButton(props: { hasMessages: boolean }) { setAgentId(agentId); setDeploymentId(deploymentId); setThreadId(null); + + // Save the selected agent to local storage + setLastSelectedAgent(nextValue); }, - [setAgentId, setDeploymentId, setThreadId], + [setAgentId, setDeploymentId, setThreadId, setLastSelectedAgent], ); const agentValue = @@ -146,13 +151,28 @@ function NewThreadButton(props: { hasMessages: boolean }) { if (agentValue || !agents.length) { return; } + + // First, try to use the last selected agent from local storage + if (lastSelectedAgent) { + const [storedAgentId, storedDeploymentId] = lastSelectedAgent.split(":"); + // Verify the stored agent still exists in the current agents list + const storedAgent = agents.find( + (agent) => agent.assistant_id === storedAgentId && agent.deploymentId === storedDeploymentId + ); + if (storedAgent) { + onAgentChange(lastSelectedAgent); + return; + } + } + + // Fallback to default agent if no last selected agent or it doesn't exist anymore const defaultAgent = agents.find(isUserSpecifiedDefaultAgent); if (defaultAgent) { onAgentChange( `${defaultAgent.assistant_id}:${defaultAgent.deploymentId}`, ); } - }, [agents, agentValue, onAgentChange]); + }, [agents, agentValue, onAgentChange, lastSelectedAgent]); if (!props.hasMessages) { return ( diff --git a/apps/web/src/features/chat/providers/Stream.tsx b/apps/web/src/features/chat/providers/Stream.tsx index 8d931166d..43dc5b6b3 100644 --- a/apps/web/src/features/chat/providers/Stream.tsx +++ b/apps/web/src/features/chat/providers/Stream.tsx @@ -26,6 +26,7 @@ import { useAuthContext } from "@/providers/Auth"; import { getDeployments } from "@/lib/environment/deployments"; import { useHasApiKeys } from "@/hooks/use-api-keys"; import { checkApiKeysWarning } from "@/lib/agent-utils"; +import { useLastSelectedAgent } from "@/hooks/use-last-selected-agent"; export type StateType = { messages: Message[]; ui?: UIMessage[] }; @@ -120,16 +121,32 @@ export const StreamProvider: React.FC<{ children: ReactNode }> = ({ const { session } = useAuthContext(); const hasApiKeys = useHasApiKeys(); const warningShownRef = useRef(""); + const [lastSelectedAgent, setLastSelectedAgent] = useLastSelectedAgent(); useEffect(() => { if (value || !agents.length) { return; } + + // First, try to use the last selected agent from local storage + if (lastSelectedAgent) { + const [storedAgentId, storedDeploymentId] = lastSelectedAgent.split(":"); + // Verify the stored agent still exists in the current agents list + const storedAgent = agents.find( + (agent) => agent.assistant_id === storedAgentId && agent.deploymentId === storedDeploymentId + ); + if (storedAgent) { + setValue(lastSelectedAgent); + return; + } + } + + // Fallback to default agent if no last selected agent or it doesn't exist anymore const defaultAgent = agents.find(isUserSpecifiedDefaultAgent); if (defaultAgent) { setValue(`${defaultAgent.assistant_id}:${defaultAgent.deploymentId}`); } - }, [agents]); + }, [agents, lastSelectedAgent]); useEffect(() => { if (agentId && deploymentId) { @@ -154,6 +171,9 @@ export const StreamProvider: React.FC<{ children: ReactNode }> = ({ const [agentId_, deploymentId_] = value.split(":"); setAgentId(agentId_); setDeploymentId(deploymentId_); + + // Save the selected agent to local storage + setLastSelectedAgent(value); }; // Show the form if we: don't have an API URL, or don't have an assistant ID diff --git a/apps/web/src/hooks/use-last-selected-agent.tsx b/apps/web/src/hooks/use-last-selected-agent.tsx new file mode 100644 index 000000000..095f25cb8 --- /dev/null +++ b/apps/web/src/hooks/use-last-selected-agent.tsx @@ -0,0 +1,16 @@ +import { useLocalStorage } from "./use-local-storage"; + +/** + * Custom hook to manage the last selected agent ID in local storage. + * + * @returns A tuple containing the last selected agent ID and a function to update it. + * The agent ID is stored in the format "agentId:deploymentId" + */ +export function useLastSelectedAgent(): [string | null, (agentId: string | null) => void] { + const [lastSelectedAgent, setLastSelectedAgent] = useLocalStorage( + "oap-last-selected-agent", + null + ); + + return [lastSelectedAgent, setLastSelectedAgent]; +}