import React, { useState, useEffect, useMemo } from 'react'; import { Button } from "@/components/ui/button"; import { Badge } from "@/components/ui/badge"; import { Input } from "@/components/ui/input"; import { ScrollArea } from "@/components/ui/scroll-area"; import { Folder, Edit, Search, Trash2, Users } from 'lucide-react'; import { getFoldersWithStats, renameFolder } from '@/ui/main-axios'; import { toast } from 'sonner'; import { useTranslation } from 'react-i18next'; import type { FolderManagerProps } from '../../../types/index.js'; interface FolderStats { name: string; hostCount: number; hosts: Array<{ id: number; name?: string; ip: string; }>; } export function FolderManager({ onFolderChanged }: FolderManagerProps) { const { t } = useTranslation(); const [folders, setFolders] = useState([]); const [loading, setLoading] = useState(true); const [error, setError] = useState(null); const [searchQuery, setSearchQuery] = useState(''); // Rename state const [renameLoading, setRenameLoading] = useState(false); useEffect(() => { fetchFolders(); }, []); const fetchFolders = async () => { try { setLoading(true); const data = await getFoldersWithStats(); setFolders(data || []); setError(null); } catch (err) { setError('Failed to fetch folder statistics'); } finally { setLoading(false); } }; const handleRename = async (folder: FolderStats) => { const newName = prompt( `Enter new name for folder "${folder.name}":\n\nThis will update ${folder.hostCount} host(s) that use this folder.`, folder.name ); if (!newName || newName.trim() === '' || newName === folder.name) { return; } if (window.confirm( `Are you sure you want to rename folder "${folder.name}" to "${newName.trim()}"?\n\n` + `This will update ${folder.hostCount} host(s) that currently use this folder.` )) { try { setRenameLoading(true); await renameFolder(folder.name, newName.trim()); toast.success(`Folder renamed from "${folder.name}" to "${newName.trim()}"`, { description: `Updated ${folder.hostCount} host(s)` }); // Refresh folder list await fetchFolders(); // Notify parent component about folder change if (onFolderChanged) { onFolderChanged(); } // Emit event for other components to refresh window.dispatchEvent(new CustomEvent('folders:changed')); } catch (err) { toast.error('Failed to rename folder'); } finally { setRenameLoading(false); } } }; const filteredFolders = useMemo(() => { if (!searchQuery.trim()) { return folders; } const query = searchQuery.toLowerCase(); return folders.filter(folder => folder.name.toLowerCase().includes(query) || folder.hosts.some(host => (host.name?.toLowerCase().includes(query)) || host.ip.toLowerCase().includes(query) ) ); }, [folders, searchQuery]); if (loading) { return (

Loading folders...

); } if (error) { return (

{error}

); } if (folders.length === 0) { return (

No Folders Found

Create some hosts with folders to manage them here

); } return (

Folder Management

{filteredFolders.length} folder(s) found

setSearchQuery(e.target.value)} className="pl-10" />
{filteredFolders.map((folder) => (

{folder.name}

{folder.hostCount} host(s)

Hosts using this folder:

{folder.hosts.slice(0, 5).map((host) => (
{host.name || host.ip} {host.name && ( ({host.ip}) )}
))} {folder.hosts.length > 5 && (
... and {folder.hosts.length - 5} more host(s)
)}
))}
); }