From c143cc60289a3c4ed2ddf4845600ebb88aaf19b9 Mon Sep 17 00:00:00 2001 From: alma Date: Wed, 16 Apr 2025 12:53:02 +0200 Subject: [PATCH] mail page ui correction maj compose 11 --- app/mail/page.tsx | 514 ++++++++++++++++++++++++---------------------- 1 file changed, 274 insertions(+), 240 deletions(-) diff --git a/app/mail/page.tsx b/app/mail/page.tsx index 176bf70..85c6609 100644 --- a/app/mail/page.tsx +++ b/app/mail/page.tsx @@ -1,6 +1,6 @@ 'use client'; -import { useEffect, useState } from 'react'; +import { useEffect, useState, useMemo } from 'react'; import { useRouter } from 'next/navigation'; import { Card, CardContent, CardDescription, CardHeader, CardTitle } from '@/components/ui/card'; import { Input } from '@/components/ui/input'; @@ -31,6 +31,7 @@ interface Account { name: string; email: string; color: string; + folders?: string[]; } interface Email { @@ -426,8 +427,7 @@ export default function MailPage() { const router = useRouter(); const [loading, setLoading] = useState(true); const [accounts, setAccounts] = useState([ - { id: 1, name: 'Mail', email: 'alma@governance-labs.org', color: 'bg-blue-500' }, - { id: 2, name: 'Work', email: 'work@governance-labs.org', color: 'bg-green-500' } + { id: 1, name: 'Mail', email: 'alma@governance-labs.org', color: 'bg-blue-500' } ]); const [selectedAccount, setSelectedAccount] = useState(null); const [currentView, setCurrentView] = useState('inbox'); @@ -459,6 +459,7 @@ export default function MailPage() { const [showCc, setShowCc] = useState(false); const [contentLoading, setContentLoading] = useState(false); const [attachments, setAttachments] = useState([]); + const [folders, setFolders] = useState([]); // Move getSelectedEmail inside the component const getSelectedEmail = () => { @@ -495,18 +496,27 @@ export default function MailPage() { }, [router]); // Fetch emails from IMAP API - const loadEmails = async () => { + const loadEmails = async (view?: string, accountId?: number, folder?: string) => { try { - console.log('Starting to load emails...'); + console.log('Loading emails...', { view, accountId, folder }); setLoading(true); setError(null); - const response = await fetch('/api/mail'); - console.log('API response status:', response.status); + let url = '/api/mail'; + const params = new URLSearchParams(); + + if (view) params.append('view', view); + if (accountId) params.append('accountId', accountId.toString()); + if (folder) params.append('folder', folder); + + if (params.toString()) { + url += `?${params.toString()}`; + } + + const response = await fetch(url); if (!response.ok) { const errorData = await response.json(); - console.error('API error:', errorData); if (errorData.error === 'No stored credentials found') { router.push('/mail/login'); return; @@ -515,11 +525,17 @@ export default function MailPage() { } const data = await response.json(); - console.log('Received data:', data); - if (!data.emails || !Array.isArray(data.emails)) { - console.error('Invalid response format:', data); - throw new Error('Invalid response format: emails array not found'); + // Update accounts and folders if provided in the response + if (data.accounts) { + setAccounts([ + { id: 0, name: 'All', email: '', color: 'bg-gray-500' }, + ...data.accounts + ]); + } + + if (data.folders) { + setFolders(data.folders); } // Process the emails array from data.emails @@ -528,12 +544,10 @@ export default function MailPage() { date: new Date(email.date), read: email.read || false, starred: email.starred || false, - category: email.category || 'inbox', - body: decodeMimeContent(email.body) + category: email.category || 'inbox' })); setEmails(processedEmails); - console.log('Emails loaded successfully:', processedEmails.length); } catch (err) { console.error('Error loading emails:', err); setError(err instanceof Error ? err.message : 'Failed to load emails'); @@ -542,6 +556,36 @@ export default function MailPage() { } }; + // Update useEffect to load emails when view changes + useEffect(() => { + loadEmails(currentView, selectedAccount?.id); + }, [currentView, selectedAccount]); + + // Filter emails based on current view and selected account + const filteredEmails = useMemo(() => { + return emails.filter(email => { + // First filter by account if one is selected + if (selectedAccount && selectedAccount.id !== 0) { + if (email.accountId !== selectedAccount.id) return false; + } + + // Then filter by current view + switch (currentView) { + case 'inbox': + return !email.deleted && email.category === 'inbox'; + case 'starred': + return !email.deleted && email.starred; + case 'sent': + return !email.deleted && email.category === 'sent'; + case 'trash': + return email.deleted; + default: + // Handle folder views + return !email.deleted && email.category === currentView; + } + }); + }, [emails, currentView, selectedAccount]); + // Mock folders data const folders = [ { id: 1, name: 'Important' }, @@ -618,11 +662,11 @@ export default function MailPage() { headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ emailId }) }); - - const updatedEmails = emails.map(email => - email.id === emailId ? { ...email, starred: !email.starred } : email - ); - setEmails(updatedEmails); + + const updatedEmails = emails.map(email => + email.id === emailId ? { ...email, starred: !email.starred } : email + ); + setEmails(updatedEmails); } catch (error) { console.error('Error toggling star:', error); } @@ -882,21 +926,21 @@ export default function MailPage() { return ( <> -
- {/* Sidebar */} -
- {/* Courrier Title */} -
-
- - COURRIER -
+
+ {/* Sidebar */} +
+ {/* Courrier Title */} +
+
+ + COURRIER
+
- {/* Compose button */} + {/* Compose button */}
- -
+
+ +
{/* Accounts Section */} -
-
- - - {foldersDropdownOpen && ( -
- {accounts.map(account => ( -
- - +
+ + + {accountsDropdownOpen && ( +
+ {accounts.map(account => ( + + ))} +
+ )} +
- {/* Account Actions Dropdown */} - {showAccountActions === account.id && ( -
- - -
- )} -
- ))} - - {/* Add Account Button */} - -
- )} -
- - {/* Navigation */} -
-
+
{/* Main content area */} -
- {/* Email list */} -
+
+ {/* Email list */} +
{/* Email list header */} -
-
+
+
{emails.length > 0 && ( - )} -

- {currentView === 'starred' ? 'Starred' : currentView} -

-
-
+ /> + )} +

+ {currentView === 'starred' ? 'Starred' : currentView} +

+
+
{emails.length} emails +
+
+ + {/* Bulk Actions Bar */} + {showBulkActions && selectedEmails.length > 0 && ( +
+ {selectedEmails.length} selected +
+
+ )} - {/* Bulk Actions Bar */} - {showBulkActions && selectedEmails.length > 0 && ( -
- {selectedEmails.length} selected -
- -
-
- )} - - {/* Email List */} - {loading ? ( + {/* Email List */} + {loading ? (
-
-
- ) : ( +
+
+ ) : (
    {emails.map((email) => ( -
  • handleEmailSelect(email.id)} - > -
    + selectedEmail?.id === email.id ? 'bg-blue-50' : '' + } ${!email.read ? 'bg-blue-50/20' : ''}`} + onClick={() => handleEmailSelect(email.id)} + > +
    e.stopPropagation()} + onClick={(e) => e.stopPropagation()} onCheckedChange={(checked) => { if (checked) { setSelectedEmails([...selectedEmails, email.id.toString()]); @@ -1115,11 +1149,11 @@ export default function MailPage() { />

    - {email.fromName || email.from} -

    + {email.fromName || email.from} +

    {email.subject}

    -
    -
    +
    +
    {formatDate(email.date)}
    +
-
- - ))} - - )} -
+ + ))} + + )} +
- {/* Email preview panel */} -
- {selectedEmail ? ( -
-
-

{selectedEmail.subject}

-
- - - - + + + -
+
+
-
- - - {selectedEmail.fromName?.charAt(0) || selectedEmail.from.charAt(0)} - - -
-

- {selectedEmail.fromName || selectedEmail.from} -

-

- to {selectedEmail.to} -

-
-
- {formatDate(selectedEmail.date)} -
+
+ + + {selectedEmail.fromName?.charAt(0) || selectedEmail.from.charAt(0)} + + +
+

+ {selectedEmail.fromName || selectedEmail.from} +

+

+ to {selectedEmail.to} +

+
+ {formatDate(selectedEmail.date)} +
+
-
+
{(() => { try { const parsed = parseFullEmail(selectedEmail.body); @@ -1234,17 +1268,17 @@ export default function MailPage() { return selectedEmail.body; } })()} -
- ) : ( -
- -

Select an email to view its contents

-
- )} -
+
+ ) : ( +
+ +

Select an email to view its contents

+
+ )}
+ {/* Compose Email Modal - Updated Design */} {showCompose && (