'use client'; import React, { useState } from 'react'; import { Inbox, Send, Trash, Archive, Star, File, RefreshCw, Plus as PlusIcon, Edit, ChevronDown, ChevronUp, Mail, Menu, Settings, Loader2, AlertOctagon, MessageSquare } from 'lucide-react'; import { Button } from '@/components/ui/button'; import { cn } from '@/lib/utils'; import { ScrollArea } from '@/components/ui/scroll-area'; import { Badge } from '@/components/ui/badge'; import { DropdownMenu, DropdownMenuTrigger, DropdownMenuContent, DropdownMenuItem } from '@/components/ui/dropdown-menu'; import { Tabs, TabsList, TabsTrigger, TabsContent } from '@/components/ui/tabs'; import { Input } from '@/components/ui/input'; import { Checkbox } from '@/components/ui/checkbox'; import { Label } from '@/components/ui/label'; interface Account { id: number | string; name: string; email: string; color: string; folders?: string[]; } interface EmailSidebarProps { accounts: Account[]; selectedAccount: Account | null; selectedFolders: Record; currentFolder: string; loading: boolean; unreadCount: Record>; showAddAccountForm: boolean; showFolders?: boolean; onFolderChange: (folder: string, accountId: string) => void; onRefresh: () => void; onComposeNew: () => void; onAccountSelect: (account: Account) => void; onShowAddAccountForm: (show: boolean) => void; onAddAccount: (formData: any) => Promise; onEditAccount: (account: Account) => void; onDeleteAccount: (account: Account) => void; onSelectEmail?: (emailId: string, accountId: string, folder: string) => void; onShowFoldersToggle?: (show: boolean) => void; } export default function EmailSidebar({ accounts, selectedAccount, selectedFolders, currentFolder, loading, unreadCount, showAddAccountForm, showFolders = true, onFolderChange, onRefresh, onComposeNew, onAccountSelect, onShowAddAccountForm, onAddAccount, onEditAccount, onDeleteAccount, onSelectEmail, onShowFoldersToggle }: EmailSidebarProps) { const [isSaving, setIsSaving] = useState(false); const [formData, setFormData] = useState({ email: '', password: '', displayName: '', host: '', port: '993', useSSL: true, smtpHost: '', smtpPort: '587', smtpUseSSL: false }); const [activeTab, setActiveTab] = useState('imap'); // Handle form submission const handleSubmit = async (e: React.FormEvent) => { e.preventDefault(); setIsSaving(true); try { await onAddAccount(formData); setFormData({ email: '', password: '', displayName: '', host: '', port: '993', useSSL: true, smtpHost: '', smtpPort: '587', smtpUseSSL: false }); onShowAddAccountForm(false); } catch (err) { console.error('Failed to add account:', err); } finally { setIsSaving(false); } }; // Handle input changes const handleChange = (e: React.ChangeEvent) => { const { name, value, type, checked } = e.target; setFormData(prev => ({ ...prev, [name]: type === 'checkbox' ? checked : value })); }; // Get the appropriate icon for a folder const getFolderIcon = (folder: string) => { const folderLower = folder.toLowerCase(); if (folderLower.includes('inbox')) { return ; } else if (folderLower.includes('sent')) { return ; } else if (folderLower.includes('trash')) { return ; } else if (folderLower.includes('archive')) { return ; } else if (folderLower.includes('draft')) { return ; } else if (folderLower.includes('spam') || folderLower.includes('junk')) { return ; } else { return ; } }; // Format folder names const formatFolderName = (folder: string) => { return folder.charAt(0).toUpperCase() + folder.slice(1).toLowerCase(); }; // Improve the renderFolderButton function to ensure consistent handling const renderFolderButton = (folder: string, accountId: string) => { // Ensure folder has a consistent format let prefixedFolder = folder; let baseFolderName = folder; let folderAccountId = accountId; // Extract parts if the folder has a prefix if (folder.includes(':')) { const parts = folder.split(':'); folderAccountId = parts[0]; baseFolderName = parts[1]; } else { // Add account prefix if missing prefixedFolder = `${accountId}:${folder}`; } // Only show folders that belong to this account if (folderAccountId !== accountId) { return null; } // Check if this folder is selected for this account // Must handle both prefixed and non-prefixed versions in the selected map const isSelected = (selectedFolders[accountId] === prefixedFolder) || (selectedFolders[accountId] === baseFolderName) || (selectedFolders[accountId]?.split(':')[1] === baseFolderName); // Get unread count - check all possible formats let folderUnreadCount = 0; // Check if this is an inbox folder (only show unread counts for inbox folders) // Use exact matching instead of includes() to avoid matching substrings in folder names const folderLower = baseFolderName.toLowerCase(); const isInboxFolder = folderLower === 'inbox'; // Only calculate unread count for inbox folders if (isInboxFolder && unreadCount && unreadCount[accountId]) { // Try the base folder name first if (typeof unreadCount[accountId][baseFolderName] === 'number') { folderUnreadCount = unreadCount[accountId][baseFolderName]; } // Then try the prefixed folder name else if (typeof unreadCount[accountId][prefixedFolder] === 'number') { folderUnreadCount = unreadCount[accountId][prefixedFolder]; } // Finally try with uppercase/lowercase variations else { // Check for case-insensitive match const folderMap = unreadCount[accountId]; for (const key in folderMap) { if (key.toLowerCase() === baseFolderName.toLowerCase() || key.toLowerCase() === prefixedFolder.toLowerCase()) { folderUnreadCount = folderMap[key]; break; } } } } return ( ); }; // Add Microsoft button logic const handleConnectMicrosoft = async () => { try { const response = await fetch('/api/courrier/microsoft'); const data = await response.json(); if (response.ok && data.authUrl) { // Redirect to Microsoft's authorization page window.location.href = data.authUrl; } else { console.error('Failed to initiate Microsoft authentication:', data.error); } } catch (error) { console.error('Error connecting Microsoft account:', error); } }; return (
{/* Courrier Title */}
COURRIER
{/* Compose button and refresh button */}
{/* Scrollable area for accounts and folders */}
{/* Accounts Section */}
Accounts
{/* Display all accounts */}
{/* Form for adding a new account - Content is identical to courrier page */} {showAddAccountForm && (

Add IMAP Account

IMAP SMTP
{ setFormData(prev => ({ ...prev, useSSL: checked === true })); }} />
{ setFormData(prev => ({ ...prev, smtpUseSSL: checked === true })); }} />
Note: SMTP settings needed for sending emails
{/* Add Microsoft option */}
)} {accounts.map((account) => (
onAccountSelect(account)} tabIndex={0} role="button" onKeyDown={e => { if (e.key === 'Enter' || e.key === ' ') onAccountSelect(account); }} >
{account.name} {/* More options button (⋮) */} {account.id !== 'loading-account' && ( onEditAccount(account)}> Edit onDeleteAccount(account)}> Delete )}
{/* Show folders for each account when selected and when folders are visible */} {selectedAccount?.id === account.id && showFolders && account.folders && account.folders.length > 0 && (
{account.folders.map((folder: string) => renderFolderButton(folder, account.id.toString()))}
)}
))}
); }