// CheckoutModal, required payment step before premium is granted.
//
// Two paths, chosen automatically from the admin's Payment-Settings:
//  1) LIVE/SANDBOX PayPal: when PayPal is enabled AND a Client-ID is configured,
//     we load the official PayPal JS SDK and render real PayPal Buttons. The order
//     is created/captured via the backend (/api/pay/paypal/...) when reachable,
//     and falls back to a client-side order otherwise (works in PayPal Sandbox).
//  2) TEST checkout: when no PayPal keys are configured (e.g. the local demo / preview),
//     a clearly-labelled simulated checkout is shown. Premium is granted ONLY after the
//     user actively completes the (test) payment, never on opening.
//
// Premium is granted by the parent's onSuccess(cycle) callback, which only runs once a
// payment has actually completed.

// ---- PayPal SDK loader (singleton) ----
let _ppPromise = null;
let _ppLoadedClientId = null;
function loadPayPalSdk(clientId, currency) {
  if (window.paypal && _ppLoadedClientId === clientId) return Promise.resolve(window.paypal);
  // Client-ID changed → drop the old SDK so the new keys take effect.
  if (_ppLoadedClientId && _ppLoadedClientId !== clientId) {
    document.querySelectorAll('script[data-pp-sdk]').forEach(s => s.remove());
    try { delete window.paypal; } catch { window.paypal = undefined; }
    _ppPromise = null;
  }
  if (_ppPromise) return _ppPromise;
  _ppLoadedClientId = clientId;
  _ppPromise = new Promise((resolve, reject) => {
    const s = document.createElement('script');
    s.src = `https://www.paypal.com/sdk/js?client-id=${encodeURIComponent(clientId)}&currency=${encodeURIComponent(currency || 'EUR')}&intent=capture`;
    s.setAttribute('data-pp-sdk', '1');
    s.onload = () => resolve(window.paypal);
    s.onerror = () => { _ppPromise = null; reject(new Error('PayPal SDK konnte nicht geladen werden.')); };
    document.head.appendChild(s);
  });
  return _ppPromise;
}

// Read the effective PayPal config (sandbox vs live keys).
const paypalConfig = (settings) => {
  const pay = (settings && settings.payments) || {};
  const p = pay.paypal || {};
  const sandbox = pay.sandboxMode !== false;
  const clientId = (sandbox ? p.testClientId : p.clientId) || '';
  return { enabled: !!p.enabled && clientId.trim().length > 10, clientId: clientId.trim(), sandbox };
};

const CURRENCY_SYMBOL = { EUR: '€', USD: '$', CHF: 'CHF ' };

const CYCLE_META = {
  monthly: { label: 'Monats-Abo', unit: '/Monat', note: 'Wird monatlich automatisch abgebucht. Jederzeit kündbar.' },
  yearly:  { label: 'Jahres-Abo', unit: '/Jahr',  note: 'Wird jährlich automatisch abgebucht. Jederzeit kündbar.' },
  once:    { label: 'Einmalkauf', unit: 'für 1 Monat', note: 'Einmalige Zahlung. Premium läuft nach einem Monat ab und verlängert sich NICHT automatisch.' },
};

const priceForCycle = (cycle, premium) =>
  cycle === 'yearly' ? premium.priceYearly
  : cycle === 'once' ? (premium.priceOnce ?? 0)
  : premium.priceMonthly;

const CheckoutModal = ({ open, onClose, cycle = 'monthly', settings, user, onSuccess }) => {
  const [status, setStatus] = React.useState('idle'); // idle | processing | success | error
  const [errMsg, setErrMsg] = React.useState('');
  const [serverPP, setServerPP] = React.useState(null); // env-driven config from backend (production)
  const ppRef = React.useRef(null);
  const [ppReady, setPpReady] = React.useState(false);

  const premium = (settings && settings.premium) || {};
  const localPP = paypalConfig(settings);
  // Production: the backend exposes the (public) PayPal client-ID from its env vars.
  // Demo/local: fall back to the keys the admin typed into Settings → Payments.
  const pp = (serverPP && serverPP.enabled) ? serverPP : localPP;
  const currency = (serverPP && serverPP.currency) || premium.currency || 'EUR';
  const sym = CURRENCY_SYMBOL[currency] || (currency + ' ');
  const meta = CYCLE_META[cycle] || CYCLE_META.monthly;
  const amount = Number(priceForCycle(cycle, premium) || 0);
  const planLabel = `${premium.name || 'Premium'} – ${meta.label}`;

  // Reset state whenever the modal (re)opens.
  React.useEffect(() => {
    if (open) { setStatus('idle'); setErrMsg(''); setPpReady(false); }
  }, [open, cycle]);

  // On open, ask the backend for its (public) env-driven PayPal config.
  // If there's no backend (local demo / preview), this silently no-ops.
  React.useEffect(() => {
    if (!open) return;
    let cancelled = false;
    fetch('/api/pay/config', { headers: { 'Accept': 'application/json' } })
      .then(r => r.ok ? r.json() : null)
      .then(cfg => { if (!cancelled && cfg && cfg.paypal) setServerPP({ ...cfg.paypal, currency: cfg.currency }); })
      .catch(() => {});
    return () => { cancelled = true; };
  }, [open]);

  const complete = () => { setStatus('success'); onSuccess && onSuccess(cycle); };

  // ---- Real PayPal Buttons (only when keys are configured) ----
  React.useEffect(() => {
    if (!open || !pp.enabled || status !== 'idle') return;
    let cancelled = false;
    loadPayPalSdk(pp.clientId, currency).then((paypal) => {
      if (cancelled || !paypal || !ppRef.current) return;
      ppRef.current.innerHTML = '';
      const buttons = paypal.Buttons({
        style: { layout: 'vertical', shape: 'pill', color: 'gold', label: 'paypal', height: 48 },
        createOrder: async (data, actions) => {
          // Prefer the backend (records the payment + uses server-side credentials/amount).
          try {
            const r = await fetch('/api/pay/paypal/create', {
              method: 'POST', headers: { 'Content-Type': 'application/json' },
              body: JSON.stringify({ cycle }),
            });
            if (r.ok) { const o = await r.json(); if (o && o.id) return o.id; }
          } catch (e) { /* backend not reachable → client-side order */ }
          return actions.order.create({
            intent: 'CAPTURE',
            purchase_units: [{
              amount: { value: amount.toFixed(2), currency_code: currency },
              description: planLabel,
            }],
            application_context: { brand_name: premium.name || 'Malfino.de', user_action: 'PAY_NOW' },
          });
        },
        onApprove: async (data, actions) => {
          setStatus('processing');
          // Prefer backend capture (also flips premium server-side in the DB).
          try {
            const r = await fetch('/api/pay/paypal/capture', {
              method: 'POST', headers: { 'Content-Type': 'application/json' },
              body: JSON.stringify({ orderId: data.orderID, cycle }),
            });
            if (r.ok) { const j = await r.json(); if (j && j.status === 'COMPLETED') { complete(); return; } }
          } catch (e) { /* fall back to client capture */ }
          try {
            const cap = await actions.order.capture();
            if (cap && cap.status === 'COMPLETED') { complete(); return; }
          } catch (e) {}
          setErrMsg('Die Zahlung konnte nicht abgeschlossen werden. Bitte erneut versuchen.');
          setStatus('error');
        },
        onCancel: () => { setStatus('idle'); },
        onError: () => { setErrMsg('Es gab ein Problem mit PayPal. Bitte erneut versuchen.'); setStatus('error'); },
      });
      buttons.render(ppRef.current).then(() => { if (!cancelled) setPpReady(true); }).catch(() => {});
    }).catch((e) => { if (!cancelled) { setErrMsg(e.message || 'PayPal nicht verfügbar.'); } });
    return () => { cancelled = true; };
  }, [open, pp.enabled, pp.clientId, currency, cycle, status]);

  if (!open) return null;

  // Simulated (test) payment for the demo / when no keys are set.
  const payTest = () => {
    setStatus('processing');
    setTimeout(() => { complete(); }, 1400);
  };

  return (
    <div className="fixed inset-0 z-[70] flex items-center justify-center p-4">
      <div className="absolute inset-0 bg-ink/50 backdrop-blur-sm" onClick={status === 'processing' ? undefined : onClose}></div>
      <div className="relative w-full max-w-md bg-paper rounded-3xl ring-2 ring-line shadow-2xl overflow-hidden max-h-[92vh] flex flex-col">

        {/* Header */}
        <div className="p-6 pb-4 bg-cream border-b-2 border-line flex items-start gap-3">
          <span className="inline-flex w-12 h-12 rounded-2xl bg-sun text-ink items-center justify-center text-2xl shadow-pop">⭐</span>
          <div className="flex-1">
            <div className="font-display text-2xl font-extrabold leading-tight">{premium.name || 'Premium'}</div>
            <div className="text-[13px] text-inkSoft mt-1">{meta.label} · {sym}{amount.toFixed(2)} {meta.unit}</div>
          </div>
          {status !== 'processing' && (
            <button onClick={onClose} className="p-2 rounded-full hover:bg-ink/5 -mt-1 -mr-1" aria-label="Schließen"><IconClose/></button>
          )}
        </div>

        <div className="p-6 grid gap-4 overflow-y-auto scroll-soft">
          {status === 'success' ? (
            <div className="text-center py-4">
              <div className="mx-auto w-16 h-16 rounded-full bg-emerald-600 text-white flex items-center justify-center text-3xl pop-in">✓</div>
              <div className="font-display text-2xl font-extrabold mt-4">Zahlung erfolgreich!</div>
              <p className="text-inkSoft text-sm mt-2 max-w-[34ch] mx-auto leading-relaxed">
                Du bist jetzt <strong>{premium.name || 'Premium'}</strong>-Mitglied. Viel Spaß mit allen Vorteilen!
              </p>
              <Btn size="lg" className="mt-6" onClick={onClose}>Los geht's</Btn>
            </div>
          ) : (
            <>
              {/* Order summary */}
              <div className="rounded-2xl bg-cream ring-1 ring-line p-4">
                <div className="flex items-baseline justify-between">
                  <span className="font-bold">{planLabel}</span>
                  <span className="font-display text-xl font-extrabold">{sym}{amount.toFixed(2)}</span>
                </div>
                <div className="text-[12px] text-inkSoft mt-1 leading-relaxed">{meta.note}</div>
              </div>

              {status === 'error' && (
                <div className="rounded-xl bg-coral/15 ring-1 ring-coral text-coralDeep text-[13px] font-semibold px-3 py-2.5">{errMsg}</div>
              )}

              {status === 'processing' ? (
                <div className="text-center py-6">
                  <div className="mx-auto w-10 h-10 rounded-full border-[3px] border-line border-t-coral animate-spin"></div>
                  <div className="text-sm text-inkSoft mt-3 font-semibold">Zahlung wird verarbeitet…</div>
                </div>
              ) : pp.enabled ? (
                <div>
                  <div className="text-[12px] font-bold uppercase tracking-wider text-inkSoft mb-2">
                    Bezahlen mit PayPal {pp.sandbox && <span className="ml-1 normal-case font-semibold text-amber-700">(Sandbox)</span>}
                  </div>
                  <div ref={ppRef} className="min-h-[52px]"></div>
                  {!ppReady && <div className="text-[12px] text-inkSoft text-center py-2">PayPal wird geladen…</div>}
                </div>
              ) : (
                <div>
                  <div className="rounded-xl bg-sky/30 ring-1 ring-sky text-[12px] leading-relaxed px-3 py-2.5 mb-3">
                    <strong>Test-Modus:</strong> Es ist noch kein Zahlungsanbieter hinterlegt. Hinterlege im Admin unter <strong>Einstellungen → Bezahlung</strong> deine PayPal-Zugangsdaten, um echte Zahlungen freizuschalten. Bis dahin wird der Kauf nur simuliert.
                  </div>
                  <Btn size="lg" className="w-full" leading={<span aria-hidden="true">🅿️</span>} onClick={payTest}>
                    Jetzt {sym}{amount.toFixed(2)} bezahlen (Test)
                  </Btn>
                </div>
              )}

              <button onClick={onClose} disabled={status === 'processing'}
                className="text-[13px] text-inkSoft hover:text-ink font-semibold mx-auto disabled:opacity-50">
                Abbrechen
              </button>

              <div className="text-[11px] text-inkSoft/80 text-center leading-relaxed">
                🔒 Sichere Bezahlung. Mit dem Kauf stimmst du den AGB &amp; Widerrufsbestimmungen zu.
              </div>
            </>
          )}
        </div>
      </div>
    </div>
  );
};

Object.assign(window, { CheckoutModal, paypalConfig });
