"use client"; import { useQueryClient } from "@tanstack/react-query"; import { Globe, Loader2, Lock, Share2, Users } from "lucide-react"; import { useCallback, useState } from "react"; import { toast } from "sonner"; import { Button } from "@/components/ui/button"; import { Popover, PopoverContent, PopoverTrigger } from "@/components/ui/popover"; import { type ChatVisibility, type ThreadRecord, updateThreadVisibility, } from "@/lib/chat/thread-persistence"; import { cn } from "@/lib/utils"; interface ChatShareButtonProps { thread: ThreadRecord | null; onVisibilityChange?: (visibility: ChatVisibility) => void; className?: string; } const visibilityOptions: { value: ChatVisibility; label: string; description: string; icon: typeof Lock; }[] = [ { value: "PRIVATE", label: "Private", description: "Only you can access this chat", icon: Lock, }, { value: "SEARCH_SPACE", label: "Search Space", description: "All members of this search space can access", icon: Users, }, ]; export function ChatShareButton({ thread, onVisibilityChange, className }: ChatShareButtonProps) { const queryClient = useQueryClient(); const [open, setOpen] = useState(false); const [isUpdating, setIsUpdating] = useState(false); const currentVisibility = thread?.visibility ?? "PRIVATE"; const isOwnThread = thread?.created_by_id !== null; // If we have the thread, we can modify it const handleVisibilityChange = useCallback( async (newVisibility: ChatVisibility) => { if (!thread || newVisibility === currentVisibility) { setOpen(false); return; } setIsUpdating(true); try { await updateThreadVisibility(thread.id, newVisibility); // Refetch all thread queries to update sidebar immediately await queryClient.refetchQueries({ predicate: (query) => Array.isArray(query.queryKey) && query.queryKey[0] === "threads", }); onVisibilityChange?.(newVisibility); toast.success( newVisibility === "SEARCH_SPACE" ? "Chat shared with search space" : "Chat is now private" ); setOpen(false); } catch (error) { console.error("Failed to update visibility:", error); toast.error("Failed to update sharing settings"); } finally { setIsUpdating(false); } }, [thread, currentVisibility, onVisibilityChange, queryClient] ); // Don't show if no thread (new chat that hasn't been created yet) if (!thread) { return null; } const CurrentIcon = currentVisibility === "PRIVATE" ? Lock : Users; return (

Share Chat

Control who can access this conversation

{/* Updating overlay */} {isUpdating && (
Updating...
)} {visibilityOptions.map((option) => { const isSelected = currentVisibility === option.value; const Icon = option.icon; return ( ); })}
{/* Info footer */}

{currentVisibility === "PRIVATE" ? "This chat is private. Only you can view and interact with it." : "This chat is shared. All search space members can view, continue the conversation, and delete it."}

); }