// Account page — email magic-link login + saved shipping addresses.

// Reusable area autocomplete (Biteship) — also used inline on checkout.
const AreaAutocomplete = ({ value, onPick, placeholder }) => {
  const [q, setQ] = React.useState(value || "");
  const [results, setResults] = React.useState([]);
  const [busy, setBusy] = React.useState(false);
  const chosen = React.useRef(false);

  React.useEffect(() => {
    if (chosen.current) { chosen.current = false; return; }
    if (q.length < 3) { setResults([]); return; }
    const t = setTimeout(async () => {
      setBusy(true);
      try {
        const r = await fetch(`/api/shipping?action=areas&q=${encodeURIComponent(q)}`);
        const j = await r.json();
        setResults(j.areas || []);
      } catch { setResults([]); }
      finally { setBusy(false); }
    }, 350);
    return () => clearTimeout(t);
  }, [q]);

  return (
    <label style={{ display: "block", marginBottom: 18, position: "relative" }}>
      <span className="mono" style={{ fontSize: 10, letterSpacing: ".14em", textTransform: "uppercase", color: "var(--ink-mute)", display: "block", marginBottom: 4 }}>City / district / postal code</span>
      <span className="mono" style={{ fontSize: 10, color: "var(--ink-mute)", display: "block", marginBottom: 8, opacity: 0.7 }}>Type to search — min. 3 characters</span>
      <input
        value={q}
        onChange={(e) => setQ(e.target.value)}
        placeholder={placeholder || "e.g. Kebayoran Baru, Jakarta Selatan"}
        style={{ width: "100%", padding: "12px 14px", background: "transparent", border: "1px solid var(--hair-strong)", borderRadius: 0, fontFamily: "var(--sans)", fontSize: 15, color: "var(--ink)" }}
      />
      {busy && <span className="mono" style={{ fontSize: 10, position: "absolute", right: 12, top: 36, opacity: 0.5 }}>…</span>}
      {results.length > 0 && (
        <div style={{ position: "absolute", left: 0, right: 0, top: "100%", zIndex: 5, background: "var(--cream)", border: "1px solid var(--hair-strong)", borderTop: 0, maxHeight: 260, overflowY: "auto" }}>
          {results.map((a) => (
            <button key={a.id} type="button" onClick={() => { chosen.current = true; setQ(a.name); setResults([]); onPick(a); }} style={{ display: "block", width: "100%", textAlign: "left", padding: "12px 14px", borderBottom: "1px solid var(--hair)", fontSize: 13, lineHeight: 1.4 }}>
              {a.name}
            </button>
          ))}
        </div>
      )}
    </label>
  );
};
window.AreaAutocomplete = AreaAutocomplete;

const AddressForm = ({ initial, onSave, onCancel }) => {
  const [f, setF] = React.useState(initial || { label: "", recipient_name: "", phone: "", address: "", area_id: "", area_label: "", postal_code: "", is_default: false });
  const set = (k, v) => setF((s) => ({ ...s, [k]: v }));
  const valid = f.recipient_name && f.phone && f.address && f.area_id;
  return (
    <div style={{ border: "1px solid var(--hair-strong)", padding: "24px var(--pad-x)", marginTop: 16 }}>
      <Field label="Label (Home, Office…)" value={f.label} onChange={(e) => set("label", e.target.value)} placeholder="Home" />
      <Field label="Recipient name" value={f.recipient_name} onChange={(e) => set("recipient_name", e.target.value)} placeholder="Jane Doe" />
      <Field label="Phone" value={f.phone} onChange={(e) => set("phone", e.target.value)} placeholder="08xxxxxxxxxx" />
      <AreaAutocomplete value={f.area_label} onPick={(a) => setF((s) => ({ ...s, area_id: a.id, area_label: a.name, postal_code: String(a.postal_code || "") }))} />
      <Field label="Full street address" value={f.address} onChange={(e) => set("address", e.target.value)} placeholder="Street, building, house no., RT/RW" />
      <label style={{ display: "flex", alignItems: "center", gap: 10, margin: "4px 0 20px", cursor: "pointer" }}>
        <input type="checkbox" checked={f.is_default} onChange={(e) => set("is_default", e.target.checked)} />
        <span className="mono" style={{ fontSize: 11, letterSpacing: ".1em", textTransform: "uppercase" }}>Set as default</span>
      </label>
      <div style={{ display: "flex", gap: 12 }}>
        <button className="btn solid" style={{ opacity: valid ? 1 : 0.4, pointerEvents: valid ? "auto" : "none" }} onClick={() => onSave(f)}>Save address</button>
        {onCancel && <button className="btn" onClick={onCancel}>Cancel</button>}
      </div>
    </div>
  );
};
window.AddressForm = AddressForm;

// Payment status label from order status.
const payLabel = (s) => ({
  pending: "Awaiting payment", paid: "Paid", processing: "Paid",
  shipped: "Paid", delivered: "Paid", cancelled: "Cancelled", expired: "Expired",
}[s] || s);
// Shipping status label.
const shipLabel = (o) => {
  if (["pending"].includes(o.status)) return "—";
  if (o.shipping_status) return o.shipping_status.replace(/_/g, " ");
  return { paid: "Preparing", processing: "Preparing", shipped: "On the way", delivered: "Delivered", cancelled: "—", expired: "—" }[o.status] || "—";
};

const OrderHistory = ({ navigate }) => {
  const [orders, setOrders] = React.useState(null);
  const [err, setErr] = React.useState("");
  const [paying, setPaying] = React.useState(null);

  const load = React.useCallback(async () => {
    try {
      const token = await sbAccessToken();
      if (!token) return;
      const r = await fetch("/api/orders", { headers: { Authorization: "Bearer " + token } });
      const j = await r.json();
      if (!r.ok || j.error) throw new Error(j.error || "Failed to load orders");
      setOrders(j.orders || []);
    } catch (e) { setErr(e.message); setOrders([]); }
  }, []);
  React.useEffect(() => { load(); }, [load]);

  const continuePay = async (o) => {
    setPaying(o.id);
    try {
      if (o.snap_token && typeof loadSnap === "function") {
        const snap = await loadSnap();
        snap.pay(o.snap_token, {
          onSuccess: () => { setPaying(null); load(); },
          onPending: () => { setPaying(null); load(); },
          onError: () => setPaying(null),
          onClose: () => setPaying(null),
        });
      } else if (o.snap_redirect_url) {
        window.open(o.snap_redirect_url, "_blank");
        setPaying(null);
      } else {
        setPaying(null);
      }
    } catch { setPaying(null); }
  };

  if (orders === null && !err) return <p className="mono" style={{ fontSize: 11, letterSpacing: ".1em", textTransform: "uppercase", color: "var(--ink-mute)", marginTop: 24 }}>Loading orders…</p>;
  if (orders && orders.length === 0) return <p className="mono" style={{ fontSize: 12, color: "var(--ink-mute)", marginTop: 20 }}>No orders yet.</p>;

  return (
    <div style={{ marginTop: 24, display: "flex", flexDirection: "column", gap: 0 }}>
      {(orders || []).map((o) => (
        <div key={o.id} style={{ borderTop: "1px solid var(--hair)", padding: "20px 0" }}>
          <div style={{ display: "flex", justifyContent: "space-between", alignItems: "baseline", gap: 16, flexWrap: "wrap" }}>
            <button className="lnk" style={{ borderBottom: 0 }} onClick={() => navigate("/order/" + o.id)}>
              <span style={{ fontFamily: "var(--serif)", fontStyle: "italic", fontSize: 20 }}>{(o.items || []).map((i) => `${i.name} ×${i.qty}`).join(", ")}</span>
            </button>
            <span className="mono" style={{ fontSize: 12 }}>{formatIDR(o.total)}</span>
          </div>
          <div className="mono" style={{ fontSize: 10, letterSpacing: ".06em", color: "var(--ink-mute)", marginTop: 8 }}>
            {o.id} · {new Date(o.created_at).toLocaleDateString("id-ID", { day: "numeric", month: "short", year: "numeric" })}
          </div>
          <div style={{ display: "flex", gap: 24, marginTop: 12, flexWrap: "wrap", alignItems: "center" }}>
            <span className="mono" style={{ fontSize: 10, letterSpacing: ".12em", textTransform: "uppercase" }}>
              <span style={{ opacity: 0.5 }}>Payment: </span>{payLabel(o.status)}
            </span>
            <span className="mono" style={{ fontSize: 10, letterSpacing: ".12em", textTransform: "uppercase" }}>
              <span style={{ opacity: 0.5 }}>Shipping: </span>{shipLabel(o)}
            </span>
            {o.waybill_id && (
              <span className="mono" style={{ fontSize: 10, letterSpacing: ".12em", textTransform: "uppercase" }}>
                <span style={{ opacity: 0.5 }}>Resi: </span>{o.tracking_url ? <a className="lnk" style={{ fontSize: 10 }} href={o.tracking_url} target="_blank" rel="noreferrer">{o.waybill_id}</a> : o.waybill_id}
              </span>
            )}
            {o.status === "pending" && (
              <button className="btn solid" style={{ padding: "8px 14px", fontSize: 10 }} onClick={() => continuePay(o)}>
                {paying === o.id ? "Opening…" : "Continue payment"} <span className="arr">→</span>
              </button>
            )}
          </div>
        </div>
      ))}
      {err && <p className="mono" style={{ fontSize: 11, color: "#a23", marginTop: 16 }}>{err}</p>}
    </div>
  );
};

const Account = ({ navigate }) => {
  const { ready, user, email, signIn, signInWithPassword, signUp, resetPassword, updatePassword, signOut, configured } = useAuth();
  const { addresses, save, remove } = useAddresses(user);
  const [loginEmail, setLoginEmail] = React.useState("");
  const [loginPassword, setLoginPassword] = React.useState("");
  const [confirmPassword, setConfirmPassword] = React.useState("");
  const [loginPhone, setLoginPhone] = React.useState("");
  const [tab, setTab] = React.useState("password"); // "password" | "magic"
  const [pwMode, setPwMode] = React.useState("signin"); // "signin" | "signup"
  const [sent, setSent] = React.useState(false);
  const [resetSent, setResetSent] = React.useState(false);
  const [signUpDone, setSignUpDone] = React.useState(false);
  const [adding, setAdding] = React.useState(false);
  const [editing, setEditing] = React.useState(null);
  const [err, setErr] = React.useState("");
  const [busy, setBusy] = React.useState(false);
  const [newPw, setNewPw] = React.useState("");
  const [newPwConfirm, setNewPwConfirm] = React.useState("");
  const [pwDone, setPwDone] = React.useState(false);
  const [pwErr, setPwErr] = React.useState("");
  const [pwBusy, setPwBusy] = React.useState(false);
  const [pwModal, setPwModal] = React.useState(false);

  const closePwModal = () => { setPwModal(false); setNewPw(""); setNewPwConfirm(""); setPwErr(""); setPwDone(false); };

  const doUpdatePassword = async () => {
    setPwErr("");
    if (newPw.length < 8) { setPwErr("Password must be at least 8 characters."); return; }
    if (newPw !== newPwConfirm) { setPwErr("Passwords don't match."); return; }
    setPwBusy(true);
    const { error } = await updatePassword(newPw);
    setPwBusy(false);
    if (error) { setPwErr(error.message); } else { setPwDone(true); setNewPw(""); setNewPwConfirm(""); }
  };

  const switchTab = (t) => { setTab(t); setErr(""); setSent(false); setResetSent(false); setSignUpDone(false); setPwMode("signin"); };
  const switchPwMode = (m) => { setPwMode(m); setErr(""); setLoginPassword(""); setConfirmPassword(""); setLoginPhone(""); setResetSent(false); setSignUpDone(false); };

  const doMagicLink = async () => {
    setBusy(true); setErr("");
    const { error } = await signIn(loginEmail.trim());
    setBusy(false);
    if (error) setErr(error.message); else setSent(true);
  };

  const doPassword = async () => {
    setBusy(true); setErr("");
    const { error } = await signInWithPassword(loginEmail.trim(), loginPassword);
    setBusy(false);
    if (error) {
      if (error.message.toLowerCase().includes("invalid login")) {
        setErr("Email or password incorrect. Try magic link if you haven't set a password.");
      } else {
        setErr(error.message);
      }
    }
  };

  const doSignUp = async () => {
    setErr("");
    if (!loginEmail.includes("@")) { setErr("Enter a valid email."); return; }
    if (loginPassword.length < 8) { setErr("Password must be at least 8 characters."); return; }
    if (loginPassword !== confirmPassword) { setErr("Passwords don't match."); return; }
    if (!loginPhone.trim()) { setErr("Phone number is required."); return; }
    setBusy(true);
    await signUp(loginEmail.trim(), loginPassword, loginPhone.trim());
    setBusy(false);
    // Always show generic success — don't reveal if email is already registered
    setSignUpDone(true);
  };

  const doForgotPassword = async () => {
    if (!loginEmail.includes("@")) { setErr("Enter your email above first."); return; }
    setBusy(true); setErr("");
    const { error } = await resetPassword(loginEmail.trim());
    setBusy(false);
    if (error) setErr(error.message); else setResetSent(true);
  };

  const tabStyle = (active) => ({
    fontFamily: "var(--mono, monospace)", fontSize: 10, letterSpacing: ".14em", textTransform: "uppercase",
    padding: "10px 20px", border: "1px solid var(--hair-strong)", borderBottom: active ? "1px solid var(--cream)" : "1px solid var(--hair-strong)",
    background: active ? "var(--cream)" : "transparent", color: active ? "var(--ink)" : "var(--ink-mute)",
    cursor: "pointer", marginBottom: -1, position: "relative", zIndex: active ? 1 : 0,
  });

  return (
    <main>
      <section style={{ padding: "60px var(--pad-x) 120px", maxWidth: 720, margin: "0 auto" }}>
        <h1 className="d-l" style={{ fontStyle: "italic", margin: "0 0 40px" }}>Account</h1>

        {!configured && (
          <p className="mono" style={{ fontSize: 12, lineHeight: 1.7, color: "var(--ink-mute)" }}>
            Accounts aren't configured yet. Set <code>window.SUPABASE_ANON_KEY</code> in index.html.
          </p>
        )}

        {configured && !ready && <span className="mono" style={{ fontSize: 11, letterSpacing: ".16em", textTransform: "uppercase", color: "var(--ink-mute)" }}>Loading…</span>}

        {configured && ready && !user && (
          <div>
            <p style={{ fontFamily: "var(--serif)", fontStyle: "italic", fontSize: 24, marginTop: 0 }}>Sign in to save your address for next time.</p>

            {/* Tab bar */}
            <div style={{ display: "flex", borderBottom: "1px solid var(--hair-strong)", marginTop: 24, marginBottom: 0, maxWidth: 420 }}>
              <button style={tabStyle(tab === "password")} onClick={() => switchTab("password")}>Password</button>
              <button style={tabStyle(tab === "magic")} onClick={() => switchTab("magic")}>Magic link</button>
            </div>

            {/* Magic link tab */}
            {tab === "magic" && (
              <div style={{ border: "1px solid var(--hair-strong)", borderTop: 0, padding: "24px 20px", maxWidth: 420 }}>
                {sent ? (
                  <p className="mono" style={{ fontSize: 12, letterSpacing: ".06em", lineHeight: 1.7, margin: 0 }}>
                    ✓ Check your email — we sent a sign-in link to <b>{loginEmail}</b>. Open it on this device.
                  </p>
                ) : (
                  <>
                    <Field label="Email" type="email" value={loginEmail} onChange={(e) => setLoginEmail(e.target.value)} placeholder="you@email.com" />
                    {err && <p className="mono" style={{ fontSize: 11, color: "#a23", marginTop: -8, marginBottom: 16 }}>{err}</p>}
                    <button className="btn solid" style={{ opacity: loginEmail.includes("@") && !busy ? 1 : 0.4, pointerEvents: loginEmail.includes("@") && !busy ? "auto" : "none" }} onClick={doMagicLink}>
                      {busy ? "Sending…" : <>Send sign-in link <span className="arr">→</span></>}
                    </button>
                  </>
                )}
              </div>
            )}

            {/* Password tab */}
            {tab === "password" && (
              <div style={{ border: "1px solid var(--hair-strong)", borderTop: 0, padding: "24px 20px", maxWidth: 420 }}>
                {resetSent ? (
                  <p className="mono" style={{ fontSize: 12, letterSpacing: ".06em", lineHeight: 1.7, margin: 0 }}>
                    ✓ If that email is registered, a reset link is on its way. Check your inbox.
                  </p>
                ) : signUpDone ? (
                  <div>
                    <p className="mono" style={{ fontSize: 12, letterSpacing: ".06em", lineHeight: 1.7, margin: "0 0 16px" }}>
                      ✓ Check your email to confirm your account. Open the link on this device.
                    </p>
                    <p className="mono" style={{ fontSize: 11, color: "var(--ink-mute)", margin: 0 }}>
                      Already have an account?{" "}
                      <button className="lnk" style={{ fontSize: 11 }} onClick={() => { setSignUpDone(false); setPwMode("signin"); setLoginPassword(""); setConfirmPassword(""); }}>Sign in instead</button>
                    </p>
                  </div>
                ) : pwMode === "signup" ? (
                  <>
                    <div style={{ borderLeft: "3px solid var(--ink)", paddingLeft: 14, marginBottom: 20 }}>
                      <div className="mono" style={{ fontSize: 9, letterSpacing: ".15em", textTransform: "uppercase", color: "var(--ink-mute)", marginBottom: 4 }}>Member benefit</div>
                      <p style={{ margin: 0, fontSize: 14, lineHeight: 1.4 }}>
                        Member price: <strong>Rp140.000</strong> · Guest: Rp150.000<br/>
                        <span style={{ fontSize: 12, color: "var(--ink-mute)" }}>Save Rp10.000 on every bottle you order here.</span>
                      </p>
                    </div>
                    <Field label="Email" type="email" value={loginEmail} onChange={(e) => setLoginEmail(e.target.value)} placeholder="you@email.com" />
                    <Field label="Phone number *" type="tel" value={loginPhone} onChange={(e) => setLoginPhone(e.target.value)} placeholder="08xxxxxxxxxx" />
                    <Field label="Password" type="password" value={loginPassword} onChange={(e) => setLoginPassword(e.target.value)} placeholder="Min. 8 characters" />
                    <Field label="Confirm password" type="password" value={confirmPassword} onChange={(e) => setConfirmPassword(e.target.value)} placeholder="••••••••" />
                    {err && <p className="mono" style={{ fontSize: 11, color: "#a23", marginTop: -8, marginBottom: 16 }}>{err}</p>}
                    <div style={{ display: "flex", alignItems: "center", gap: 20, flexWrap: "wrap" }}>
                      <button className="btn solid" style={{ opacity: loginEmail.includes("@") && loginPassword && confirmPassword && loginPhone && !busy ? 1 : 0.4, pointerEvents: loginEmail.includes("@") && loginPassword && confirmPassword && loginPhone && !busy ? "auto" : "none" }} onClick={doSignUp}>
                        {busy ? "Creating account…" : <>Create account <span className="arr">→</span></>}
                      </button>
                    </div>
                    <p className="mono" style={{ fontSize: 11, color: "var(--ink-mute)", marginTop: 20, marginBottom: 0 }}>
                      Already have an account?{" "}
                      <button className="lnk" style={{ fontSize: 11 }} onClick={() => switchPwMode("signin")}>Sign in</button>
                    </p>
                  </>
                ) : (
                  <>
                    <Field label="Email" type="email" value={loginEmail} onChange={(e) => setLoginEmail(e.target.value)} placeholder="you@email.com" />
                    <Field label="Password" type="password" value={loginPassword} onChange={(e) => setLoginPassword(e.target.value)} placeholder="••••••••" />
                    {err && <p className="mono" style={{ fontSize: 11, color: "#a23", marginTop: -8, marginBottom: 16 }}>{err}</p>}
                    <div style={{ display: "flex", alignItems: "center", gap: 20, flexWrap: "wrap" }}>
                      <button className="btn solid" style={{ opacity: loginEmail.includes("@") && loginPassword && !busy ? 1 : 0.4, pointerEvents: loginEmail.includes("@") && loginPassword && !busy ? "auto" : "none" }} onClick={doPassword}>
                        {busy ? "Signing in…" : <>Sign in <span className="arr">→</span></>}
                      </button>
                      <button className="lnk" style={{ fontSize: 11 }} onClick={doForgotPassword}>Forgot password?</button>
                    </div>
                    <p className="mono" style={{ fontSize: 11, color: "var(--ink-mute)", marginTop: 20, marginBottom: 0 }}>
                      New here?{" "}
                      <button className="lnk" style={{ fontSize: 11 }} onClick={() => switchPwMode("signup")}>Create an account</button>
                    </p>
                  </>
                )}
              </div>
            )}
          </div>
        )}

        {configured && ready && user && (
          <div>
            <div style={{ display: "flex", justifyContent: "space-between", alignItems: "center", borderBottom: "1px solid var(--hair-strong)", paddingBottom: 20, marginBottom: 32 }}>
              <span className="mono" style={{ fontSize: 12, letterSpacing: ".08em" }}>{email}</span>
              <button className="lnk" onClick={() => signOut()}>Sign out</button>
            </div>

            <div style={{ display: "flex", justifyContent: "space-between", alignItems: "baseline" }}>
              <h2 className="d-m" style={{ fontStyle: "italic", margin: 0 }}>Saved addresses</h2>
              {!adding && !editing && <button className="lnk" onClick={() => setAdding(true)}>+ Add address</button>}
            </div>

            {addresses.length === 0 && !adding && (
              <p className="mono" style={{ fontSize: 12, letterSpacing: ".06em", color: "var(--ink-mute)", marginTop: 20 }}>No addresses saved yet.</p>
            )}

            <div style={{ marginTop: 24, display: "flex", flexDirection: "column", gap: 16 }}>
              {addresses.map((a) => editing === a.id ? (
                <AddressForm key={a.id} initial={a} onSave={async (v) => { await save(v); setEditing(null); }} onCancel={() => setEditing(null)} />
              ) : (
                <div key={a.id} style={{ borderTop: "1px solid var(--hair)", paddingTop: 16, display: "flex", justifyContent: "space-between", gap: 16 }}>
                  <div>
                    <div style={{ fontFamily: "var(--serif)", fontStyle: "italic", fontSize: 20 }}>
                      {a.label || "Address"} {a.is_default && <span className="mono" style={{ fontSize: 9, letterSpacing: ".14em", textTransform: "uppercase", border: "1px solid var(--ink)", padding: "2px 6px", verticalAlign: "middle", marginLeft: 8 }}>Default</span>}
                    </div>
                    <div className="mono" style={{ fontSize: 12, color: "var(--ink-mute)", marginTop: 6, lineHeight: 1.5 }}>{a.recipient_name} · {a.phone}<br />{a.address}<br />{a.area_label}</div>
                  </div>
                  <div style={{ display: "flex", flexDirection: "column", gap: 8, textAlign: "right", flex: "0 0 auto" }}>
                    <button className="lnk" style={{ fontSize: 10 }} onClick={() => setEditing(a.id)}>Edit</button>
                    <button className="lnk" style={{ fontSize: 10, opacity: 0.6 }} onClick={() => remove(a.id)}>Delete</button>
                  </div>
                </div>
              ))}
            </div>

            {adding && <AddressForm onSave={async (v) => { await save(v); setAdding(false); }} onCancel={() => setAdding(false)} />}

            <div style={{ marginTop: 56 }}>
              <h2 className="d-m" style={{ fontStyle: "italic", margin: "0 0 8px" }}>Order history</h2>
              <OrderHistory navigate={navigate} />
            </div>

            <div style={{ marginTop: 56, borderTop: "1px solid var(--hair-strong)", paddingTop: 40, display: "flex", justifyContent: "space-between", alignItems: "center" }}>
              <span className="mono" style={{ fontSize: 12, letterSpacing: ".08em" }}>Password</span>
              <button className="lnk" style={{ fontSize: 11 }} onClick={() => setPwModal(true)}>Set / change password</button>
            </div>

            {pwModal && (
              <div onClick={closePwModal} style={{ position: "fixed", inset: 0, background: "rgba(15,14,12,0.55)", zIndex: 100, display: "flex", alignItems: "center", justifyContent: "center", padding: 24 }}>
                <div onClick={(e) => e.stopPropagation()} style={{ background: "var(--cream)", padding: "40px", width: "100%", maxWidth: 400, position: "relative" }}>
                  <button onClick={closePwModal} className="mono" style={{ position: "absolute", top: 16, right: 20, fontSize: 11, opacity: 0.5 }}>✕</button>
                  <h2 className="d-m" style={{ fontStyle: "italic", margin: "0 0 24px" }}>
                    {pwDone ? "Done." : "Set password."}
                  </h2>
                  {pwDone ? (
                    <>
                      <p className="mono" style={{ fontSize: 12, lineHeight: 1.7, margin: "0 0 24px" }}>✓ Password updated successfully.</p>
                      <button className="btn solid" onClick={closePwModal}>Close</button>
                    </>
                  ) : (
                    <>
                      <Field label="New password" type="password" value={newPw} onChange={(e) => setNewPw(e.target.value)} placeholder="Min. 8 characters" />
                      <Field label="Confirm new password" type="password" value={newPwConfirm} onChange={(e) => setNewPwConfirm(e.target.value)} placeholder="••••••••" />
                      {pwErr && <p className="mono" style={{ fontSize: 11, color: "#a23", marginTop: -8, marginBottom: 16 }}>{pwErr}</p>}
                      <button className="btn solid" style={{ opacity: newPw && newPwConfirm && !pwBusy ? 1 : 0.4, pointerEvents: newPw && newPwConfirm && !pwBusy ? "auto" : "none" }} onClick={doUpdatePassword}>
                        {pwBusy ? "Saving…" : <>Save password <span className="arr">→</span></>}
                      </button>
                    </>
                  )}
                </div>
              </div>
            )}
          </div>
        )}
      </section>
    </main>
  );
};

window.Account = Account;
