// POST /api/registration/confirm  { token }
//
// Marks a pending registration as confirmed, then hands it to the (feature-flagged)
// ERP onboarding module. The ERP step can never break confirmation: it is fail-soft and
// no-ops entirely while ERP_ONBOARDING_URL / ERP_SERVICE_TOKEN are unset.
//
// Registrations flagged `needs_manual_approval` (couriers, and clinics whose Standort has
// no e-mail domain on record) are NOT auto-onboarded — see the gate below. They stay in
// the DB with erp_status 'manual-approval' until an operator provisions them.
import { registrationTypeLabelDe } from '../../utils/registrationTypes'
import { asLang, serverMessages, typeLabelFor } from '../../utils/i18n'

const MAX_AGE_MS = 14 * 24 * 60 * 60 * 1000

export default defineEventHandler(async (event) => {
  const body = await readBody(event)
  const config = useRuntimeConfig()
  const token = String(body?.token ?? '').trim()

  // Two languages are in play and they are NOT the same thing:
  //   pageLang — the language on screen right now, used for this HTTP response;
  //   mailLang — the language stored on the registration row, used for the welcome mail.
  // Someone who registered in English must not be written to in German just because the
  // confirmation link was opened in a German browser (or by a mail client).
  const pageLang = asLang(body?.lang)

  if (!token) {
    return { status: 400, message: serverMessages(pageLang).api.noToken }
  }

  const registration = findByToken(token)
  if (!registration) {
    return { status: 404, message: serverMessages(pageLang).api.invalidToken }
  }

  const mailLang = asLang(registration.lang)
  // READ PATH. `registration.type` may be a retired value ('abgebende_klinik' /
  // 'beziehende_klinik') from a link that has been sitting in an inbox since before the
  // types were collapsed. Confirmation itself never looks at the type — it is keyed on the
  // token alone — and both label helpers normalise, so such a link confirms and reads
  // correctly instead of showing the raw key.
  const typeLabel = typeLabelFor(registration.type, pageLang)
  const typeLabelDe = registrationTypeLabelDe(registration.type)

  if (registration.status === 'confirmed') {
    // Whether credentials went out is recorded in the stored ERP payload (see
    // setErpResult below). Rows confirmed before that field existed read false,
    // which degrades to the generic confirmed text rather than a wrong promise.
    let credentialsSent = false
    try { credentialsSent = !!JSON.parse((registration as any).erp_payload || '{}')?.credentialsSent } catch { /* ignore */ }
    return {
      status: 200,
      alreadyConfirmed: true,
      message: serverMessages(pageLang).api.alreadyConfirmed,
      typeLabel,
      orgName: registration.org_name,
      needsManualApproval: !!registration.needs_manual_approval,
      credentialsSent,
    }
  }

  if (registration.status !== 'pending') {
    return { status: 410, message: serverMessages(pageLang).api.notValid }
  }

  const age = Date.now() - Date.parse(registration.created_at || '')
  if (Number.isFinite(age) && age > MAX_AGE_MS) {
    return { status: 410, message: serverMessages(pageLang).api.expired }
  }

  markConfirmed(registration.id)
  const confirmed = { ...registration, status: 'confirmed' as const }

  // ---- ERP onboarding (feature-flagged, fail-soft) -------------------------------------
  // GATED on needs_manual_approval. That flag marks exactly the registrations nothing
  // could verify — every courier, and clinics whose Standort has no e-mail domain on
  // record. Auto-onboarding them would mail live ERP credentials to an address nobody
  // checked, while the form, the confirmation mail and the welcome mail all promise a
  // manual review ("we will get back to you within one working day"). This gate is what
  // actually keeps that promise. Verified and test registrations stay fully automatic.
  let erp = { enabled: false, ok: false, status: 'disabled', message: '', credentialsSent: false } as any
  if (confirmed.needs_manual_approval) {
    erp = {
      enabled: false, ok: false, status: 'manual-approval',
      message: 'ERP-Onboarding zurückgestellt — Registrierung wartet auf manuelle Freigabe.',
      credentialsSent: false,
    }
  } else {
    try {
      erp = await runErpOnboarding(confirmed)
    } catch (err: any) {
      // runErpOnboarding already swallows its own errors; this is belt and braces.
      erp = { enabled: true, ok: false, status: 'error', message: err?.message || String(err), credentialsSent: false }
    }
  }
  setErpResult(registration.id, erp.status, erp.message, {
    ctx: erp.ctx ?? null,
    report: erp.report ?? null,
    credentialsSent: !!erp.credentialsSent,
  })

  // ---- welcome mail ---------------------------------------------------------------------
  const mail = buildWelcomeMail({
    to: confirmed.contact_email,
    contactName: confirmed.contact_name,
    orgName: confirmed.org_name,
    typeLabel: typeLabelFor(confirmed.type, mailLang),
    needsManualApproval: !!confirmed.needs_manual_approval,
    credentialsSent: !!erp.credentialsSent,
    lang: mailLang,
  })
  await sendMail({ to: confirmed.contact_email, subject: mail.subject, html: mail.html, text: mail.text })

  const notify = String(config.notifyEmail || '')
  if (notify) {
    const internal = buildInternalMail('Blut24: Registrierung bestätigt', [
      ['Einrichtung', confirmed.org_name],
      ['Typ', typeLabelDe],
      ['STOID', confirmed.stoid || '–'],
      ['E-Mail', confirmed.contact_email],
      ['Domain geprüft', confirmed.domain_verified ? 'ja' : 'nein'],
      ['Manuelle Freigabe nötig', confirmed.needs_manual_approval ? 'ja' : 'nein'],
      ['ERP-Onboarding', erp.status === 'manual-approval'
        ? 'zurückgestellt — manuelle Freigabe erforderlich'
        : erp.enabled ? `${erp.status}${erp.message ? ': ' + erp.message : ''}` : 'deaktiviert'],
      ['Zugangsdaten versendet', erp.credentialsSent ? 'ja' : 'nein'],
      ['Sprache', mailLang],
    ])
    await sendMail({ to: notify, subject: internal.subject, html: internal.html, text: internal.text })
  }

  return {
    status: 200,
    alreadyConfirmed: false,
    message: serverMessages(pageLang).api.confirmed,
    typeLabel,
    orgName: confirmed.org_name,
    needsManualApproval: !!confirmed.needs_manual_approval,
    credentialsSent: !!erp.credentialsSent,
  }
})
