/* global React */
// =============================================================
// BuyDialog: email-capture modal that opens before Stripe Checkout.
//
// Two network calls on submit:
//   1. POST /api/lead  · fire-and-forget. Captures the email as a
//      lead even if the user abandons Stripe. Errors swallowed so a
//      lead-server hiccup never blocks a paying customer.
//   2. POST /api/checkout/create · authoritative. Returns the Stripe
//      Checkout Session URL; we redirect the tab there.
//
// The dimmy://buy fallback remains as a tertiary link for users who
// already have the app installed and prefer the in-app purchase flow.
// =============================================================
const { useEffect: useBDE, useRef: useBDR, useState: useBDS } = React;

const LICENSE_BACKEND = "https://license.dimmy.app";

function BuyDialog({ open, onClose, tier, billing }) {
  const [email, setEmail] = useBDS("");
  const [status, setStatus] = useBDS("idle"); // idle | submitting | error
  const [errorMsg, setErrorMsg] = useBDS("");
  const inputRef = useBDR(null);

  // Restore last-used email from localStorage so a returning visitor
  // doesn't retype it. Read once on open, then update on submit.
  useBDE(() => {
    if (!open) return;
    setStatus("idle");
    setErrorMsg("");
    try {
      const saved = localStorage.getItem("dimmy-email") || "";
      if (saved && !email) setEmail(saved);
    } catch (_) {}
    // Autofocus after the modal paints. requestAnimationFrame so the
    // input is in the DOM before focus() is called.
    requestAnimationFrame(() => inputRef.current && inputRef.current.focus());
  }, [open]);

  // Esc to close, click backdrop to close. Body scroll locked while open.
  useBDE(() => {
    if (!open) return;
    const onKey = (e) => { if (e.key === "Escape") onClose && onClose(); };
    window.addEventListener("keydown", onKey);
    const prev = document.body.style.overflow;
    document.body.style.overflow = "hidden";
    return () => {
      window.removeEventListener("keydown", onKey);
      document.body.style.overflow = prev;
    };
  }, [open, onClose]);

  if (!open) return null;

  const validEmail = /^[^@\s]+@[^@\s]+\.[^@\s]+$/.test(email.trim());
  const locale = (typeof document !== "undefined" && document.documentElement && document.documentElement.lang) || "en";

  // tier the backend expects: "monthly" | "annual" | "lifetime".
  // The site uses billing="monthly|annual" for Pro and tier="lifetime"
  // for Lifetime, so we normalise here at the call boundary.
  const backendTier = tier === "lifetime" ? "lifetime" : (billing === "annual" ? "annual" : "monthly");

  // dimmy:// fallback URL matches what Pricing.jsx used to point CTAs at.
  // Lets users who already have the app skip the web checkout entirely.
  const inAppUrl = tier === "lifetime"
    ? `dimmy://buy?tier=lifetime&source=web`
    : `dimmy://buy?tier=pro&billing=${billing || "annual"}&source=web`;

  const tierLabel = tier === "lifetime"
    ? "Lifetime · €99 once"
    : (billing === "annual" ? "Pro Annual · €39/year" : "Pro Monthly · €4.99/month");

  async function submit(e) {
    e.preventDefault();
    if (!validEmail || status === "submitting") return;
    const clean = email.trim().toLowerCase();
    try { localStorage.setItem("dimmy-email", clean); } catch (_) {}

    setStatus("submitting");
    setErrorMsg("");

    // Lead capture · non-blocking. We don't await this on the redirect
    // path; a failed lead save must NEVER stop a paying customer.
    try {
      fetch(`${LICENSE_BACKEND}/api/lead`, {
        method: "POST",
        headers: { "Content-Type": "application/json" },
        body: JSON.stringify({ email: clean, tier: backendTier, locale, source: "buy_dialog" }),
      }).catch(() => {});
    } catch (_) {}

    // Checkout session · authoritative.
    try {
      const r = await fetch(`${LICENSE_BACKEND}/api/checkout/create`, {
        method: "POST",
        headers: { "Content-Type": "application/json" },
        body: JSON.stringify({ tier: backendTier, email: clean }),
      });
      const data = await r.json().catch(() => ({}));
      if (!r.ok || !data.url) {
        const msg = data && data.error
          ? String(data.error)
          : `Checkout failed (${r.status}). Try again or email hi@dimmy.app.`;
        setStatus("error");
        setErrorMsg(msg);
        return;
      }
      window.location.href = data.url;
    } catch (err) {
      setStatus("error");
      setErrorMsg("Network error reaching checkout. Try again.");
    }
  }

  return (
    <div
      role="dialog"
      aria-modal="true"
      aria-label="Continue to checkout"
      onClick={(e) => { if (e.target === e.currentTarget) onClose && onClose(); }}
      style={{
        position: "fixed", inset: 0, zIndex: 1000,
        background: "rgba(0,0,0,0.62)",
        backdropFilter: "blur(8px)", WebkitBackdropFilter: "blur(8px)",
        display: "flex", alignItems: "center", justifyContent: "center",
        padding: 20,
        animation: "fade-up 220ms cubic-bezier(0.2,0.8,0.2,1)",
      }}
    >
      <div style={{
        width: "100%", maxWidth: 440,
        background: "var(--bg)",
        border: "1px solid var(--line-strong)",
        borderRadius: 18,
        padding: 28,
        boxShadow: "0 30px 80px rgba(0,0,0,0.5)",
      }}>
        <div style={{
          fontFamily: "var(--font-mono)", fontSize: 11,
          color: "#38BDF8", letterSpacing: "0.14em", textTransform: "uppercase",
          marginBottom: 8,
        }}>{tierLabel}</div>

        <h3 style={{
          fontFamily: "var(--font-display)", fontWeight: 700,
          fontSize: 24, letterSpacing: "-0.02em", lineHeight: 1.15,
          margin: 0, color: "var(--fg)",
        }}>One step before checkout.</h3>

        <p style={{
          fontSize: 14, color: "var(--fg-muted)", lineHeight: 1.55,
          marginTop: 10, marginBottom: 22, textWrap: "pretty",
        }}>
          We pass your email to Stripe so checkout is one click less.
          Same email activates Dimmy after payment.
        </p>

        <form onSubmit={submit}>
          <label htmlFor="bd-email" style={{
            display: "block", fontSize: 12, fontFamily: "var(--font-mono)",
            color: "var(--fg-faint)", letterSpacing: "0.06em",
            textTransform: "uppercase", marginBottom: 8,
          }}>Email</label>

          <input
            ref={inputRef}
            id="bd-email"
            type="email"
            autoComplete="email"
            placeholder="you@domain.com"
            value={email}
            onChange={(e) => setEmail(e.target.value)}
            disabled={status === "submitting"}
            style={{
              width: "100%", padding: "12px 14px", borderRadius: 10,
              background: "var(--bg-elev)",
              border: "1px solid var(--line-strong)",
              color: "var(--fg)", fontSize: 15,
              fontFamily: "var(--font-sans)",
              outline: "none",
              transition: "border-color 160ms",
            }}
          />

          {status === "error" && (
            <div style={{
              marginTop: 12, padding: "10px 12px", borderRadius: 8,
              background: "rgba(239,68,68,0.10)",
              border: "1px solid rgba(239,68,68,0.35)",
              color: "#FCA5A5", fontSize: 13, lineHeight: 1.45,
            }}>{errorMsg}</div>
          )}

          <button
            type="submit"
            disabled={!validEmail || status === "submitting"}
            style={{
              marginTop: 16, width: "100%",
              padding: "13px 16px", borderRadius: 10,
              background: validEmail && status !== "submitting" ? "#38BDF8" : "var(--line)",
              color: validEmail && status !== "submitting" ? "var(--bg-deep)" : "var(--fg-faint)",
              border: 0, fontWeight: 600, fontSize: 14,
              fontFamily: "var(--font-sans)",
              cursor: validEmail && status !== "submitting" ? "pointer" : "not-allowed",
              transition: "transform 160ms, background 200ms",
            }}
          >
            {status === "submitting" ? "Opening Stripe..." : "Continue to checkout"}
          </button>
        </form>

        <div style={{
          marginTop: 18, paddingTop: 16,
          borderTop: "1px solid var(--line)",
          display: "flex", justifyContent: "space-between", alignItems: "center",
          gap: 12, flexWrap: "wrap",
        }}>
          <a href={inAppUrl} style={{
            fontSize: 12, fontFamily: "var(--font-mono)",
            color: "var(--fg-muted)", textDecoration: "none",
          }}>Already have Dimmy? Pay in-app →</a>

          <button type="button" onClick={() => onClose && onClose()} style={{
            background: "transparent", border: 0,
            color: "var(--fg-faint)", fontSize: 12,
            fontFamily: "var(--font-mono)", cursor: "pointer",
            padding: 0,
          }}>Cancel (Esc)</button>
        </div>

        <p style={{
          marginTop: 16, fontSize: 11, color: "var(--fg-faint)",
          lineHeight: 1.55, fontFamily: "var(--font-mono)",
        }}>
          Payment via Stripe. 30-day refund. We never see your card.
        </p>
      </div>
    </div>
  );
}

window.BuyDialog = BuyDialog;
