import { useState, useEffect } from 'react'; import { Save, TestTube, Loader2, CheckCircle2, XCircle, ArrowLeft, Server, Mail, FileText } from 'lucide-react'; import { useAuth } from '@/contexts/AuthContext'; import { RichTextEditor } from './RichTextEditor'; import { sanitizeHtml } from '@/utils/sanitizeHtml'; interface MailSettings { host: string; port: string; user: string; pass: string; tls: boolean; } const emptySettings: MailSettings = { host: '', port: '', user: '', pass: '', tls: true, }; interface SettingsPageProps { onBack?: () => void; onSaved?: () => void; } export function SettingsPage({ onBack, onSaved }: SettingsPageProps) { const { getToken } = useAuth(); const [imap, setImap] = useState({ ...emptySettings, port: '993' }); const [smtp, setSmtp] = useState({ ...emptySettings, port: '465' }); const [signature, setSignature] = useState(''); const [saving, setSaving] = useState(false); const [testing, setTesting] = useState(false); const [testResult, setTestResult] = useState<{ imap: boolean; smtp: boolean } | null>(null); const [saved, setSaved] = useState(false); const [error, setError] = useState(''); const [loadingSettings, setLoadingSettings] = useState(true); // Load existing settings useEffect(() => { (async () => { try { const token = await getToken(); const res = await fetch('/api/settings', { headers: { Authorization: `Bearer ${token}` }, }); const data = await res.json(); if (data.imap) { setImap({ host: data.imap.host || '', port: String(data.imap.port || '993'), user: data.imap.user || '', pass: data.imap.pass || '', tls: data.imap.tls !== false, }); } if (data.smtp) { setSmtp({ host: data.smtp.host || '', port: String(data.smtp.port || '465'), user: data.smtp.user || '', pass: data.smtp.pass || '', tls: data.smtp.tls !== false, }); } if (data.signature !== undefined) { setSignature(data.signature); } } catch (e) { console.error('Failed to load settings:', e); } finally { setLoadingSettings(false); } })(); }, [getToken]); const handleSave = async () => { setError(''); setSaving(true); setSaved(false); try { const token = await getToken(); // Sanitize signature HTML before sending to API let sanitizedSignature: string; try { sanitizedSignature = sanitizeHtml(signature); } catch (sanitizeError: any) { throw new Error(`Failed to sanitize signature: ${sanitizeError.message}`); } const res = await fetch('/api/settings', { method: 'POST', headers: { 'Content-Type': 'application/json', Authorization: `Bearer ${token}`, }, body: JSON.stringify({ imap, smtp, signature: sanitizedSignature }), }); if (!res.ok) { const data = await res.json(); throw new Error(data.error || 'Failed to save settings'); } setSaved(true); onSaved?.(); setTimeout(() => setSaved(false), 3000); } catch (e: any) { setError(e.message); } finally { setSaving(false); } }; const handleTest = async () => { setTestResult(null); setTesting(true); setError(''); try { const token = await getToken(); const res = await fetch('/api/settings/test', { method: 'POST', headers: { 'Content-Type': 'application/json', Authorization: `Bearer ${token}`, }, body: JSON.stringify({ imap, smtp }), }); const data = await res.json(); setTestResult(data); } catch (e: any) { setError(e.message); } finally { setTesting(false); } }; const inputStyles = 'w-full rounded-lg border border-gray-200 bg-gray-50 px-3.5 py-2.5 text-[14px] text-gray-900 outline-none placeholder:text-gray-400 focus:border-blue-300 focus:bg-white focus:ring-2 focus:ring-blue-100'; const InputField = ({ label, value, onChange, placeholder, type = 'text', }: { label: string; value: string; onChange: (v: string) => void; placeholder: string; type?: string; }) => (
onChange(e.target.value)} className={inputStyles} placeholder={placeholder} />
); if (loadingSettings) { return (
); } return (
{/* Header */}
{onBack && ( )}

Mail Settings

{error && (
{error}
)} {saved && (
Settings saved successfully
)} {testResult && (
{testResult.imap ? ( ) : ( )} IMAP: {testResult.imap ? 'Connected successfully' : 'Connection failed'}
{testResult.smtp ? ( ) : ( )} SMTP: {testResult.smtp ? 'Connected successfully' : 'Connection failed'}
)} {/* IMAP Settings */}

IMAP Settings

For receiving emails

setImap({ ...imap, host: v })} placeholder="imap.gmail.com" /> setImap({ ...imap, port: v })} placeholder="993" /> setImap({ ...imap, user: v })} placeholder="you@gmail.com" /> setImap({ ...imap, pass: v })} placeholder="App password" type="password" />
{/* SMTP Settings */}

SMTP Settings

For sending emails

setSmtp({ ...smtp, host: v })} placeholder="smtp.gmail.com" /> setSmtp({ ...smtp, port: v })} placeholder="465" /> setSmtp({ ...smtp, user: v })} placeholder="you@gmail.com" /> setSmtp({ ...smtp, pass: v })} placeholder="App password" type="password" />
{/* Email Signature */}

Email Signature

Automatically added to your emails

This signature will be automatically added to all new emails and replies. Use the toolbar to format your signature with bold, italic, underline, links, lists, and colors.

{/* Action buttons */}
); }