/** * Mail list component with pagination. * Shows list of mails in selected folder with seen/flagged indicators. */ import React from 'react'; import clsx from 'clsx'; import { useTranslation } from 'react-i18next'; import type { Mail } from '@/api/mail'; import { decodeMimeHeader } from '@/api/mail'; import { EmptyState } from '@/components/ui/EmptyState'; import { Pagination } from '@/components/ui/Pagination'; export interface MailListProps { mails: Mail[]; selectedMailId: string | null; onSelectMail: (mail: Mail) => void; loading: boolean; currentPage: number; total: number; pageSize: number; onPageChange: (page: number) => void; selectedMailIds: Set; onToggleSelect: (mailId: string) => void; onSelectAll: () => void; sortBy?: 'date' | 'from' | 'subject'; sortOrder?: 'asc' | 'desc'; onSortChange?: (sortBy: 'date' | 'from' | 'subject', sortOrder: 'asc' | 'desc') => void; } function formatDate(dateStr: string): string { const date = new Date(dateStr); const now = new Date(); if (date.toDateString() === now.toDateString()) { return date.toLocaleTimeString([], { hour: '2-digit', minute: '2-digit' }); } return date.toLocaleDateString([], { month: 'short', day: 'numeric' }); } export function MailList({ mails, selectedMailId, onSelectMail, loading, currentPage, total, pageSize, onPageChange, selectedMailIds, onToggleSelect, onSelectAll, sortBy = 'date', sortOrder = 'desc', onSortChange, }: MailListProps) { const { t } = useTranslation(); const totalPages = Math.ceil(total / pageSize); const allSelected = mails.length > 0 && mails.every((m) => selectedMailIds.has(m.id)); const handleSortFieldChange = (e: React.ChangeEvent) => { const newSortBy = e.target.value as 'date' | 'from' | 'subject'; onSortChange?.(newSortBy, sortOrder); }; const handleSortOrderToggle = () => { const newOrder = sortOrder === 'asc' ? 'desc' : 'asc'; onSortChange?.(sortBy, newOrder); }; if (loading) { return (
{t('common.loading')}
); } if (mails.length === 0) { return ( ); } return (
{/* Select-all + Sort header in one row */}
{selectedMailIds.size > 0 && ( {t('mail.selectedCount', { count: selectedMailIds.size })} )}
{onSortChange && (
)}
{/* Mail list — scrolls, pagination stays fixed */}
    {mails.map((mail) => (
  • onToggleSelect(mail.id)} className="w-4 h-4 rounded border-secondary-300 text-primary-600 focus:ring-primary-500" aria-label={t('mail.selectMail')} data-testid={`mail-checkbox-${mail.id}`} />
  • ))}
{totalPages > 1 && (
)}
); }