/** * POST /api/report * * Signalement d'erreur / proposition de modification sur une fiche * Fallback Resend (pas de table NocoDB créée) * * Body : { fiche_id: number, message: string, email: string } * Rate limit : 5/IP/jour * Envoi vers jules@trans-former.fr via Resend API */ import { checkRateLimitJson } from '~/server/utils/rateLimitJson' const EMAIL_JULES = process.env.EMAIL_JULES || 'jules@trans-former.fr' export default defineEventHandler(async (event) => { // 1. IP const ip = getHeader(event, 'x-forwarded-for')?.split(',')[0].trim() || event.node.req.socket?.remoteAddress || '0.0.0.0' // 2. Rate limit 5/IP/jour const allowed = checkRateLimitJson(ip, 'report', 5) if (!allowed) { throw createError({ statusCode: 429, statusMessage: 'Limite de 5 signalements par jour atteinte.', }) } // 3. Lire le body const body = await readBody(event) const fiche_id: number = Number(body?.fiche_id ?? 0) const message: string = (body?.message ?? '').trim() const email: string = (body?.email ?? '').trim() // 4. Validation if (!fiche_id || fiche_id <= 0) { throw createError({ statusCode: 400, statusMessage: 'fiche_id invalide.' }) } if (!message || message.length < 5 || message.length > 500) { throw createError({ statusCode: 400, statusMessage: 'Message requis (5-500 caractères).' }) } const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/ if (!email || !emailRegex.test(email)) { throw createError({ statusCode: 400, statusMessage: 'Email invalide.' }) } // 5. Envoi via Resend const resendApiKey = process.env.RESEND_API_KEY if (!resendApiKey) { console.error('[report] RESEND_API_KEY manquante') throw createError({ statusCode: 500, statusMessage: 'Configuration email manquante.' }) } const submittedAt = new Date().toLocaleString('fr-FR', { timeZone: 'Europe/Paris' }) try { await $fetch('https://api.resend.com/emails', { method: 'POST', headers: { Authorization: `Bearer ${resendApiKey}`, 'Content-Type': 'application/json', }, body: JSON.stringify({ from: 'AEP Signalement ', to: EMAIL_JULES, subject: `[AEP] Signalement fiche #${fiche_id}`, html: `

Signalement fiche AEP #${fiche_id}

Date : ${submittedAt}

Email expéditeur : ${email}

Message :

${message.replace(/\n/g, '
')}

Voir la fiche : https://aep.trans-former.fr/fiche/${fiche_id}

`, }), }) } catch (e: any) { console.error('[report] Erreur Resend:', e?.message ?? e) throw createError({ statusCode: 502, statusMessage: 'Erreur envoi email — réessaie dans quelques instants.', }) } return { ok: true, message: 'Signalement envoyé, merci !' } })