import { useState, useEffect, useCallback } from "react"; import { UserGroupIcon, ArrowPathIcon, PencilIcon, } from "@heroicons/react/20/solid"; import clsx from "clsx"; import { useSessionStore, useSharedSessionStore } from "@/stores/sessionStore"; import { useJsonRpc } from "@/hooks/useJsonRpc"; import SessionControlPanel from "@/components/SessionControlPanel"; import NicknameModal from "@/components/NicknameModal"; import SessionsList, { SessionModeBadge } from "@/components/SessionsList"; import { sessionApi } from "@/api/sessionApi"; export default function SessionPopover() { const { currentSessionId, currentMode, sessions, sessionError, setSessions, } = useSessionStore(); const { setNickname } = useSharedSessionStore(); const [isRefreshing, setIsRefreshing] = useState(false); const [showNicknameModal, setShowNicknameModal] = useState(false); const [editingSessionId, setEditingSessionId] = useState(null); const { send } = useJsonRpc(); // Adapter function to match existing callback pattern const sendRpc = useCallback((method: string, params: Record, callback?: (response: { result?: unknown; error?: { message: string } }) => void) => { send(method, params, (response) => { if (callback) callback(response); }); }, [send]); const handleRefresh = async () => { if (isRefreshing) return; setIsRefreshing(true); try { const refreshedSessions = await sessionApi.getSessions(sendRpc); setSessions(refreshedSessions); } catch (error) { console.error("Failed to refresh sessions:", error); } finally { setIsRefreshing(false); } }; // Fetch sessions on mount useEffect(() => { if (sessions.length === 0) { sessionApi.getSessions(sendRpc) .then(sessions => setSessions(sessions)) .catch(error => console.error("Failed to fetch sessions:", error)); } }, [sendRpc, sessions.length, setSessions]); return (
{/* Header */}

Session Management

{/* Session Error */} {sessionError && (

{sessionError}

)} {/* Current Session */}
Your Session
{currentSessionId && ( <> {/* Display current session nickname if exists */} {sessions.find(s => s.id === currentSessionId)?.nickname && (
Nickname: {sessions.find(s => s.id === currentSessionId)?.nickname}
)}
)}
{/* Active Sessions List */}
Active Sessions ({sessions.length})
{sessions.length > 0 ? ( { setEditingSessionId(sessionId); setShowNicknameModal(true); }} onApprove={(sessionId) => { sendRpc("approveNewSession", { sessionId }, (response) => { if (response.error) { console.error("Failed to approve session:", response.error); } else { handleRefresh(); } }); }} onDeny={(sessionId) => { sendRpc("denyNewSession", { sessionId }, (response) => { if (response.error) { console.error("Failed to deny session:", response.error); } else { handleRefresh(); } }); }} onTransfer={async (sessionId) => { try { await sessionApi.transferPrimary(sendRpc, currentSessionId!, sessionId); handleRefresh(); } catch (error) { console.error("Failed to transfer primary:", error); } }} /> ) : (

No active sessions

)}
s.id === currentSessionId)?.nickname ? "Update Your Nickname" : "Set Your Nickname") : `Set Nickname for ${sessions.find(s => s.id === editingSessionId)?.mode || 'Session'}`} description={editingSessionId === currentSessionId ? "Choose a nickname to help identify your session to others" : "Choose a nickname to help identify this session"} onSubmit={async (nickname) => { if (editingSessionId && sendRpc) { try { await sessionApi.updateNickname(sendRpc, editingSessionId, nickname); if (editingSessionId === currentSessionId) { setNickname(nickname); } setShowNicknameModal(false); setEditingSessionId(null); handleRefresh(); } catch (error) { console.error("Failed to update nickname:", error); throw error; } } }} onSkip={() => { setShowNicknameModal(false); setEditingSessionId(null); }} />
); }