Files
breakpilot-lehrer/website/app/mail/_components/useMail.ts
Benjamin Admin b4613e26f3 [split-required] Split 500-850 LOC files (batch 2)
backend-lehrer (10 files):
- game/database.py (785 → 5), correction_api.py (683 → 4)
- classroom_engine/antizipation.py (676 → 5)
- llm_gateway schools/edu_search already done in prior batch

klausur-service (12 files):
- orientation_crop_api.py (694 → 5), pdf_export.py (677 → 4)
- zeugnis_crawler.py (676 → 5), grid_editor_api.py (671 → 5)
- eh_templates.py (658 → 5), mail/api.py (651 → 5)
- qdrant_service.py (638 → 5), training_api.py (625 → 4)

website (6 pages):
- middleware (696 → 8), mail (733 → 6), consent (628 → 8)
- compliance/risks (622 → 5), export (502 → 5), brandbook (629 → 7)

studio-v2 (3 components):
- B2BMigrationWizard (848 → 3), CleanupPanel (765 → 2)
- dashboard-experimental (739 → 2)

admin-lehrer (4 files):
- uebersetzungen (769 → 4), manager (670 → 2)
- ChunkBrowserQA (675 → 6), dsfa/page (674 → 5)

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-25 08:24:01 +02:00

110 lines
3.1 KiB
TypeScript

'use client'
import { useState, useEffect, useCallback } from 'react'
import type { Email, Account } from './types'
import { API_BASE } from './types'
export function useMail() {
const [emails, setEmails] = useState<Email[]>([])
const [accounts, setAccounts] = useState<Account[]>([])
const [selectedEmail, setSelectedEmail] = useState<Email | null>(null)
const [selectedAccount, setSelectedAccount] = useState<string>('all')
const [selectedFolder, setSelectedFolder] = useState('inbox')
const [loading, setLoading] = useState(true)
const [searchQuery, setSearchQuery] = useState('')
const fetchEmails = useCallback(async () => {
try {
setLoading(true)
const params = new URLSearchParams()
if (selectedAccount !== 'all') {
params.append('account_id', selectedAccount)
}
if (selectedFolder === 'unread') {
params.append('unread_only', 'true')
}
if (searchQuery) {
params.append('search', searchQuery)
}
const res = await fetch(`${API_BASE}/api/v1/mail/inbox?${params}`)
if (res.ok) {
const data = await res.json()
setEmails(data.emails || [])
}
} catch (err) {
console.error('Failed to fetch emails:', err)
} finally {
setLoading(false)
}
}, [selectedAccount, selectedFolder, searchQuery])
const fetchAccounts = useCallback(async () => {
try {
const res = await fetch(`${API_BASE}/api/v1/mail/accounts`)
if (res.ok) {
const data = await res.json()
setAccounts(data.accounts || [])
}
} catch (err) {
console.error('Failed to fetch accounts:', err)
}
}, [])
useEffect(() => {
fetchAccounts()
}, [fetchAccounts])
useEffect(() => {
fetchEmails()
}, [fetchEmails])
const analyzeEmail = async (emailId: string) => {
try {
const res = await fetch(`${API_BASE}/api/v1/mail/analyze/${emailId}`, {
method: 'POST',
})
if (res.ok) {
const data = await res.json()
setSelectedEmail((prev) => prev ? { ...prev, ...data, aiAnalyzed: true } : null)
setEmails((prev) =>
prev.map((e) => (e.id === emailId ? { ...e, ...data, aiAnalyzed: true } : e))
)
}
} catch (err) {
console.error('Failed to analyze email:', err)
}
}
const markAsRead = async (emailId: string) => {
try {
await fetch(`${API_BASE}/api/v1/mail/inbox/${emailId}/read`, {
method: 'POST',
})
setEmails((prev) =>
prev.map((e) => (e.id === emailId ? { ...e, isRead: true } : e))
)
} catch (err) {
console.error('Failed to mark as read:', err)
}
}
const handleEmailClick = (email: Email) => {
setSelectedEmail(email)
if (!email.isRead) {
markAsRead(email.id)
}
}
const totalUnread = accounts.reduce((sum, acc) => sum + acc.unreadCount, 0)
return {
emails, accounts,
selectedEmail, setSelectedEmail,
selectedAccount, setSelectedAccount,
selectedFolder, setSelectedFolder,
loading, searchQuery, setSearchQuery,
analyzeEmail, handleEmailClick, totalUnread,
}
}