Files
kandev/apps/web/components/quick-chat/quick-chat-provider.tsx
T

55 lines
1.8 KiB
TypeScript

"use client";
import { useSyncExternalStore } from "react";
import { useAppStore } from "@/components/state-provider";
import { useSettingsData } from "@/hooks/domains/settings/use-settings-data";
import { QuickChatModal } from "./quick-chat-modal";
// SSR-safe client mount detection without useEffect setState
const emptySubscribe = () => () => {};
const getClientSnapshot = () => true;
const getServerSnapshot = () => false;
function useIsMounted() {
return useSyncExternalStore(emptySubscribe, getClientSnapshot, getServerSnapshot);
}
export function getWorkspaceId(
sessions: { sessionId: string; workspaceId: string }[],
isOpen: boolean,
activeSessionId: string | null,
activeWorkspace: string | null,
): string | null {
if (!isOpen) return null;
return (
sessions.find((session) => session.sessionId === activeSessionId)?.workspaceId ??
activeWorkspace
);
}
/**
* Global provider for Quick Chat functionality.
* Renders the modal that can be opened from anywhere in the app.
* Preloads agent profiles so they're available when quick chat is opened.
*/
export function QuickChatProvider({ children }: { children: React.ReactNode }) {
const quickChatSessions = useAppStore((s) => s.quickChat.sessions);
const isOpen = useAppStore((s) => s.quickChat.isOpen);
const activeSessionId = useAppStore((s) => s.quickChat.activeSessionId);
const activeWorkspace = useAppStore((s) => s.workspaces.activeId);
const mounted = useIsMounted();
// Preload agent profiles so they're available when quick chat is opened
useSettingsData(true);
const workspaceId = getWorkspaceId(quickChatSessions, isOpen, activeSessionId, activeWorkspace);
return (
<>
{children}
{/* Only render modal on client side and if we have a workspace */}
{mounted && workspaceId && <QuickChatModal workspaceId={workspaceId} />}
</>
);
}