// src/features/admin/ui/admin-students-payments.jsx
//
// Admin payment-tracking widgets for a single student. Wraps the v85 RPCs
// admin_record_student_payment + admin_list_student_payments. Mounted from
// admin-students-card.jsx inside the expand region. Exposes:
//   window.AdminStudentPaymentsButton    — opens the Add Payment modal
//   window.AdminStudentPaymentsLog        — payment history + balance pill
//   window.AdminStudentPaymentsSection    — convenience wrapper around both
//
// Money is stored as bigint cents in student_payments.amount_cents. The UI
// shows it as $X.YY. The same RPC bumps student_info.classes_purchased via
// the existing admin_add_student_credits() helper, so the existing classes-
// left math keeps working.

(function() {
  const fmtMoney = (cents, currency) => {
    if (cents == null) return '—';
    const sym = currency === 'EUR' ? '€' : currency === 'GBP' ? '£' : '$';
    const v = Math.abs(Number(cents)) / 100;
    const out = v.toLocaleString(undefined, { minimumFractionDigits: 2, maximumFractionDigits: 2 });
    return `${sym}${out}`;
  };
  const fmtDate = (iso) => {
    if (!iso) return '';
    try {
      const d = new Date(iso);
      if (isNaN(d.getTime())) return String(iso);
      return d.toLocaleDateString(undefined, { month: 'short', day: 'numeric', year: 'numeric' });
    } catch { return String(iso); }
  };

  const lbl = { display:'block', fontSize:10, fontWeight:700, textTransform:'uppercase', letterSpacing:'0.06em', color:'oklch(52% 0.04 265)', marginBottom:5 };
  const fld = { width:'100%', padding:'10px 12px', borderRadius:8, border:'1.5px solid oklch(88% 0.015 265)', fontSize:14, minHeight:42, fontFamily:"'Plus Jakarta Sans', sans-serif", color:'oklch(22% 0.06 265)', background:'#fff', outline:'none', boxSizing:'border-box' };

  // ── Add Payment Modal ────────────────────────────────────────────────
  const AddPaymentModal = ({ student, onClose, onSaved }) => {
    const data = window.useAdminData();
    const todayStr = new Date().toISOString().slice(0, 10);
    const [classes,     setClasses]     = React.useState('');
    const [amountInput, setAmountInput] = React.useState('');
    const [currency,    setCurrency]    = React.useState('USD');
    const [note,        setNote]        = React.useState('');
    const [date,        setDate]        = React.useState(todayStr);
    const [busy,        setBusy]        = React.useState(false);
    const [err,         setErr]         = React.useState('');

    const submit = async (e) => {
      e.preventDefault();
      setErr('');

      const nClasses = parseInt(classes, 10);
      if (!Number.isFinite(nClasses) || nClasses <= 0) {
        setErr('Classes must be a positive whole number.');
        return;
      }
      // Allow "$1,200.50" / "1200.50" / "1200" / "1,200" — strip everything that
      // isn't a digit or a decimal point, then validate.
      const cleaned = String(amountInput).replace(/[^0-9.]/g, '');
      const parts = cleaned.split('.');
      if (parts.length > 2) {
        setErr('Amount has too many decimal points.');
        return;
      }
      const nAmount = parseFloat(cleaned);
      if (!Number.isFinite(nAmount) || nAmount < 0) {
        setErr('Amount must be 0 or more.');
        return;
      }
      // Round to nearest cent to avoid float noise (e.g. 12.345 → 1235).
      const amountCents = Math.round(nAmount * 100);

      setBusy(true);
      try {
        const newId = await data.recordStudentPayment({
          userId: student.id,
          classes: nClasses,
          amountCents,
          currency,
          note,
          paymentDate: date,
        });
        // Refresh admin data so classesBalance + classesPurchased reflect.
        await data.refresh();
        if (typeof onSaved === 'function') onSaved(newId);
        onClose();
      } catch (e2) {
        setErr(e2.message || 'Could not record payment.');
      } finally {
        setBusy(false);
      }
    };

    return (
      <div style={{ position:'fixed', inset:0, background:'rgba(10,12,24,0.4)', display:'flex', alignItems:'center', justifyContent:'center', zIndex:9000 }} onClick={onClose}>
        <div style={{ background:'#fff', borderRadius:14, padding:'24px', width:'min(440px, calc(100vw - 24px))', maxHeight:'92vh', overflowY:'auto', boxShadow:'0 20px 60px rgba(0,0,0,0.18)', fontFamily:"'Plus Jakarta Sans', sans-serif", boxSizing:'border-box' }} onClick={e => e.stopPropagation()}>
          <div style={{ fontWeight:700, fontSize:17, color:'oklch(18% 0.03 265)', marginBottom:4 }}>Record payment</div>
          <div style={{ fontSize:12, color:'oklch(58% 0.03 265)', marginBottom:18 }}>
            {student.name} paid for some classes. We'll bump their balance and keep a record.
          </div>
          <form onSubmit={submit}>
            <div style={{ display:'grid', gridTemplateColumns:'1fr 1fr', gap:12, marginBottom:14 }}>
              <div>
                <label style={lbl}>Classes</label>
                <input
                  type="number"
                  min="1"
                  step="1"
                  inputMode="numeric"
                  value={classes}
                  onChange={e => setClasses(e.target.value)}
                  placeholder="8"
                  required
                  style={fld}
                />
              </div>
              <div>
                <label style={lbl}>Amount</label>
                <input
                  type="text"
                  inputMode="decimal"
                  value={amountInput}
                  onChange={e => setAmountInput(e.target.value)}
                  placeholder="240.00"
                  required
                  style={fld}
                />
              </div>
            </div>
            <div style={{ display:'grid', gridTemplateColumns:'1fr 1fr', gap:12, marginBottom:14 }}>
              <div>
                <label style={lbl}>Currency</label>
                <select value={currency} onChange={e => setCurrency(e.target.value)} style={fld}>
                  <option value="USD">USD ($)</option>
                  <option value="EUR">EUR (€)</option>
                  <option value="GBP">GBP (£)</option>
                  <option value="CAD">CAD ($)</option>
                  <option value="AUD">AUD ($)</option>
                </select>
              </div>
              <div>
                <label style={lbl}>Payment date</label>
                <input type="date" value={date} onChange={e => setDate(e.target.value)} required style={fld} />
              </div>
            </div>
            <div style={{ marginBottom:14 }}>
              <label style={lbl}>Note (optional)</label>
              <input
                value={note}
                onChange={e => setNote(e.target.value)}
                placeholder="e.g. Q1 renewal, Venmo, check #122"
                style={fld}
              />
            </div>
            {err && (
              <div role="alert" style={{ background:'oklch(95% 0.06 25)', color:'oklch(40% 0.15 25)', padding:'9px 12px', borderRadius:8, fontSize:12, marginBottom:12 }}>
                {err}
              </div>
            )}
            <div style={{ display:'flex', gap:10 }}>
              <button type="submit" disabled={busy} style={{ flex:1, background:'oklch(34% 0.13 150)', color:'#fff', border:'none', borderRadius:9, padding:'12px 0', fontWeight:600, fontSize:14, cursor:busy?'wait':'pointer', fontFamily:"'Plus Jakarta Sans', sans-serif", opacity:busy?0.7:1, minHeight:44 }}>
                {busy ? 'Saving…' : 'Record payment'}
              </button>
              <button type="button" onClick={onClose} style={{ padding:'12px 16px', background:'oklch(95% 0.01 265)', border:'none', borderRadius:9, fontSize:13, cursor:'pointer', color:'oklch(46% 0.04 265)', fontFamily:"'Plus Jakarta Sans', sans-serif", fontWeight:600, minHeight:44 }}>Cancel</button>
            </div>
          </form>
        </div>
      </div>
    );
  };

  // ── Add Payment Button ───────────────────────────────────────────────
  const AdminStudentPaymentsButton = ({ student, onSaved }) => {
    const [open, setOpen] = React.useState(false);
    return (
      <>
        <button
          type="button"
          onClick={() => setOpen(true)}
          style={{ background:'oklch(34% 0.13 150)', color:'#fff', border:'none', borderRadius:8, padding:'7px 12px', fontSize:11, fontWeight:600, cursor:'pointer', fontFamily:"'Plus Jakarta Sans', sans-serif" }}
        >
          + Add payment
        </button>
        {open && <AddPaymentModal student={student} onClose={() => setOpen(false)} onSaved={onSaved} />}
      </>
    );
  };

  // ── Payment History Log + Balance Pill ───────────────────────────────
  // Loads on mount, refreshes when an Add Payment lands (signalled by the
  // refreshKey state). Renders a Out-of-paid pill when classesBalance <= 0.
  const AdminStudentPaymentsLog = ({ student }) => {
    const data = window.useAdminData();
    const [rows,    setRows]    = React.useState(null); // null = loading, [] = empty
    const [err,     setErr]     = React.useState('');
    const [refresh, setRefresh] = React.useState(0);

    // `data` is the window.ADMIN_DATA singleton (returned by useAdminData);
    // its reference is stable across renders. We deliberately read from it
    // inside the effect rather than putting it in the dep array, so we don't
    // re-fetch on every render — only when student.id or refresh changes.
    React.useEffect(() => {
      let cancelled = false;
      setErr('');
      setRows(null);
      window.ADMIN_DATA.listStudentPayments(student.id)
        .then(r => { if (!cancelled) setRows(r || []); })
        .catch(e => { if (!cancelled) { setErr(e.message || 'Could not load payments.'); setRows([]); } });
      return () => { cancelled = true; };
    }, [student.id, refresh]);

    const totalPaid = (rows || []).reduce((a, p) => {
      if (!a[p.currency]) a[p.currency] = 0;
      a[p.currency] += Number(p.amount_cents) || 0;
      return a;
    }, {});
    const totalClasses = (rows || []).reduce((a, p) => a + (Number(p.classes_added) || 0), 0);
    const balance = Number(student.classesBalance) || 0;
    const outOfPaid = balance <= 0 && totalClasses > 0;

    return (
      <div style={{ marginTop:14, padding:'12px 14px', background:'oklch(98.5% 0.005 60)', borderRadius:8, border:'1px solid oklch(93% 0.01 265)' }}>
        <div style={{ display:'flex', alignItems:'center', justifyContent:'space-between', gap:10, marginBottom:10, flexWrap:'wrap' }}>
          <div style={{ display:'flex', alignItems:'center', gap:10, flexWrap:'wrap' }}>
            <div style={{ fontSize:10, fontWeight:700, textTransform:'uppercase', letterSpacing:'0.06em', color:'oklch(52% 0.04 265)' }}>Payments</div>
            {outOfPaid && (
              <span style={{ background:'oklch(94% 0.08 25)', color:'oklch(38% 0.18 25)', borderRadius:6, padding:'3px 8px', fontSize:10, fontWeight:700, textTransform:'uppercase', letterSpacing:'0.06em' }}>
                Out of paid classes — needs renewal
              </span>
            )}
            {!outOfPaid && balance > 0 && balance <= 2 && totalClasses > 0 && (
              <span style={{ background:'oklch(95% 0.1 80)', color:'oklch(40% 0.14 75)', borderRadius:6, padding:'3px 8px', fontSize:10, fontWeight:700, textTransform:'uppercase', letterSpacing:'0.06em' }}>
                Almost done — {balance} left
              </span>
            )}
          </div>
          <AdminStudentPaymentsButton student={student} onSaved={() => setRefresh(n => n + 1)} />
        </div>
        {rows === null ? (
          <div style={{ fontSize:12, color:'oklch(58% 0.03 265)' }}>Loading…</div>
        ) : err ? (
          <div role="alert" style={{ fontSize:12, color:'oklch(40% 0.15 25)' }}>{err}</div>
        ) : rows.length === 0 ? (
          <div style={{ fontSize:12, color:'oklch(58% 0.03 265)' }}>
            No payments recorded yet. Click <strong>+ Add payment</strong> when this student pays.
          </div>
        ) : (
          <>
            <div style={{ display:'flex', flexWrap:'wrap', gap:14, marginBottom:10, fontSize:12, color:'oklch(34% 0.04 265)' }}>
              <div><strong>{totalClasses}</strong> classes paid in total</div>
              {Object.keys(totalPaid).map(cur => (
                <div key={cur}><strong>{fmtMoney(totalPaid[cur], cur)}</strong> {cur}</div>
              ))}
            </div>
            <div style={{ display:'flex', flexDirection:'column', gap:6 }}>
              {rows.map(p => (
                <div key={p.id} style={{ display:'grid', gridTemplateColumns:'auto 1fr auto', gap:10, alignItems:'baseline', background:'#fff', border:'1px solid oklch(94% 0.01 265)', borderRadius:7, padding:'7px 10px', fontSize:12, color:'oklch(28% 0.05 265)' }}>
                  <div style={{ fontWeight:600 }}>{fmtDate(p.payment_date)}</div>
                  <div>
                    <strong>{p.classes_added}</strong> {p.classes_added === 1 ? 'class' : 'classes'}
                    {' · '}
                    <strong>{fmtMoney(p.amount_cents, p.currency)}</strong>
                    {p.note && <span style={{ color:'oklch(56% 0.03 265)' }}> — {p.note}</span>}
                  </div>
                </div>
              ))}
            </div>
          </>
        )}
      </div>
    );
  };

  // ── Convenience wrapper (button + log in one block) ──────────────────
  // For places that want both in a single mount.
  const AdminStudentPaymentsSection = ({ student }) => (
    <AdminStudentPaymentsLog student={student} />
  );

  Object.assign(window, {
    AdminStudentPaymentsButton,
    AdminStudentPaymentsLog,
    AdminStudentPaymentsSection,
  });
})();
