// js/components/widgets/ComissaoAdmin.jsx
// Painel de Comissão para admin/financeiro — V4 (sistema 4).
// Lista todas vendedoras com comissão atual + botão fechar mês + marcar pago.
// Criado em 2026-05-06.
// [Wave 36 v224.17 NUCLEAR EXTRACT 2026-05-24] 292L -> ~155L (-47%) · 11ª replicação NUCLEAR
// Padrão NUCLEAR small mixed (3 handlers RPC + JSX extractable) · par natural Wave 35 ComissaoVendedora
//
// Props:
//   user: usuário logado (admin ou financeiro)
//   allUsers: lista de app_users
//
// Deps runtime: sb, fmtMoney, toast, znxGuard, showConfirm (globals)
// Deps Wave 36: ZNX.lib['comissao-admin'].calcs + ZNX.widgets['comissao-admin'].{
//   CommissionAdminHeader, CommissionAdminKPIs, CommissionAdminTable, CommissionAdminFooter}
(function() {
  'use strict';
  const {useState, useEffect, useMemo, useRef} = React;

  // [Wave 36 v224.17 + v224.55 2026-05-28] vars+check MOVED to component body (preventivo)
  // regra_validacao_helpers_runtime_quando_ordem_scripts_uncertain

  function ComissaoAdmin({user, allUsers}) {
    // [v224.55 FIX-PREV-10 2026-05-28] vars+check em render time
    const caW = (window.ZNX && window.ZNX.widgets && window.ZNX.widgets['comissao-admin']) || {};
    const caCalcs = window.ZNX && window.ZNX.lib && window.ZNX.lib['comissao-admin'] && window.ZNX.lib['comissao-admin'].calcs;
    if(!caCalcs || !caW.CommissionAdminHeader || !caW.CommissionAdminKPIs || !caW.CommissionAdminTable || !caW.CommissionAdminFooter){
      const _msg = '[ComissaoAdmin v224.17 wave36] deps faltando: calcs='+!!caCalcs+', CommissionAdminHeader='+!!caW.CommissionAdminHeader+', CommissionAdminKPIs='+!!caW.CommissionAdminKPIs+', CommissionAdminTable='+!!caW.CommissionAdminTable+', CommissionAdminFooter='+!!caW.CommissionAdminFooter;
      console.error(_msg);
      if(window.Sentry && typeof window.Sentry.captureMessage === 'function') window.Sentry.captureMessage(_msg, 'error');
    }
    const now = new Date();
    const [year, setYear] = useState(now.getFullYear());
    const [month, setMonth] = useState(now.getMonth() + 1);
    const [provisorio, setProvisorio] = useState([]);
    const [persisted, setPersisted] = useState([]);
    const [loading, setLoading] = useState(true);
    const [closing, setClosing] = useState(false);
    const [error, setError] = useState(null);
    // [ONDA1-A 2026-05-11] regra_loading_state_obrigatorio + znxGuard server-side check
    // closeMonth + markPaid manipulam financeiro real. Sem inflight ref/disabled → double-click duplica payment.
    // Sem znxGuard → vendedora consegue chamar via DevTools.
    const _closingRef = useRef(false);
    const _payingRef = useRef(false);
    const [paying, setPaying] = useState(false);
    // [ONDA-A #9 2026-05-11] regra_idem_estavel — Map<paymentId, idemKey>.
    // Retry mantém mesma key; reset SÓ após sucesso confirmado.
    // TODO: commission_mark_paid ainda não aceita idempotency_key — passar quando RPC for atualizada.
    const _markPaidIdemMap = useRef(new Map());

    const sellers = useMemo(() => (allUsers || []).filter(u => u.role === 'vendedor' && u.active && u.auth_user_id), [allUsers]);

    function reload() {
      setLoading(true);
      setError(null);
      Promise.all([
        // Provisório de cada vendedora (calc on-the-fly)
        Promise.all(sellers.map(s =>
          sb.rpc('commission_calculate', { p_seller_id: s.auth_user_id, p_year: year, p_month: month })
            .then(r => r.error ? null : { ...r.data, app_user_id: s.id })
            .catch(() => null)
        )),
        // Persistidos do mês escolhido
        sb.from('commission_payments').select('*').eq('period_year', year).eq('period_month', month).order('seller_name')
      ]).then(([calcs, persistedRes]) => {
        setProvisorio(calcs.filter(Boolean));
        if (persistedRes.error) throw persistedRes.error;
        setPersisted(persistedRes.data || []);
        setLoading(false);
      }).catch(e => {
        setError(e.message);
        setLoading(false);
      });
    }

    useEffect(() => {
      if (sellers.length > 0) reload();
    }, [year, month, sellers.length]);

    async function closeMonth() {
      // [ONDA1-A 2026-05-11] znxGuard server-side check (regra_grant_security_definer_anon).
      // Sem isso, vendedora consegue invocar via DevTools.
      if (typeof znxGuard==='function' && !await znxGuard(['admin'])) return;
      if (_closingRef.current) { toast('⏳ Fechando, aguarde…'); return; }
      // [ONDA-D D1 2026-05-11] confirm() nativo → showConfirm (UX consistente).
      if (!await showConfirm({
        title: 'Fechar comissão do mês',
        message: `Fechar comissão de ${month}/${year} pra todas vendedoras?\n\nIsso vai PERSISTIR o cálculo. Pagamento ainda manual depois.`,
        confirmText: 'Fechar mês',
        confirmColor: '#1B2A4A'
      })) return;
      _closingRef.current = true;
      setClosing(true);
      try {
        const { data, error } = await sb.rpc('commission_close_month', { p_year: year, p_month: month });
        if (error) throw error;
        toast(`✅ ${data.sellers_processed} vendedoras processadas. Total: R$ ${Number(data.total_comissao_brl).toFixed(2)}`);
        reload();
      } catch (e) {
        toast('❌ ' + e.message);
      } finally {
        _closingRef.current = false;
        setClosing(false);
      }
    }

    async function markPaid(commissionId, sellerName, valor) {
      // [ONDA1-A 2026-05-11] znxGuard server-side + inflight (regra_loading_state_obrigatorio).
      // Sem isso, double-click marca pago 2x e vendedora consegue invocar via DevTools.
      if (typeof znxGuard==='function' && !await znxGuard(['admin'])) return;
      if (_payingRef.current) { toast('⏳ Processando pagamento…'); return; }
      // [ONDA-D D1 2026-05-11] confirm() nativo → showConfirm (UX consistente).
      if (!await showConfirm({
        title: 'Marcar comissão como paga',
        message: `Marcar comissão de ${sellerName} (R$ ${Number(valor).toFixed(2)}) como PAGA?`,
        confirmText: 'Marcar pago',
        confirmColor: '#16A34A'
      })) return;
      _payingRef.current = true;
      setPaying(true);
      // [ONDA-A #9] idem key estável por paymentId — lazy init, retry replay-safe.
      if (!_markPaidIdemMap.current.has(commissionId)) {
        _markPaidIdemMap.current.set(commissionId, (window.crypto?.randomUUID?.() || (Date.now() + '-' + Math.random())));
      }
      // [HOTFIX 20260512] commission_mark_paid aceita só (p_id, p_notes).
      // Não passar p_idem_key — PostgREST rejeita arg extra. Idem key fica
      // só no Map frontend (anti double-click). RPC já é idempotente pq
      // trigger anti-aprovacao-dupla bloqueia re-marcar como Pago.
      try {
        const { error } = await sb.rpc('commission_mark_paid', { p_id: commissionId, p_notes: null });
        if (error) throw error;
        // [ONDA-A #9] sucesso confirmado → reset entry
        _markPaidIdemMap.current.delete(commissionId);
        toast(`✅ Marcado como pago: ${sellerName}`);
        reload();
      } catch (e) {
        toast('❌ ' + e.message);
      } finally {
        _payingRef.current = false;
        setPaying(false);
      }
    }

    // [Wave 36 v224.17] merged + totals via lib (era useMemo inline L131-156)
    const merged = useMemo(() => caCalcs.mergeProvisorioPersisted(provisorio, persisted), [provisorio, persisted]);
    const totals = useMemo(() => caCalcs.calcTotals(merged), [merged]);

    return (
      <div style={{display:'flex',flexDirection:'column',gap:14}}>
        {caW.CommissionAdminHeader && <caW.CommissionAdminHeader month={month} year={year} setMonth={setMonth} setYear={setYear} merged={merged} onReload={reload} onCloseMonth={closeMonth} closing={closing}/>}
        {caW.CommissionAdminKPIs && <caW.CommissionAdminKPIs totals={totals} merged={merged}/>}
        {caW.CommissionAdminTable && <caW.CommissionAdminTable merged={merged} loading={loading} error={error} onMarkPaid={markPaid} paying={paying}/>}
        {caW.CommissionAdminFooter && <caW.CommissionAdminFooter/>}
      </div>
    );
  }

  window.ZNX = window.ZNX || {};
  window.ZNX.components = window.ZNX.components || {};
  window.ZNX.components.ComissaoAdmin = ComissaoAdmin;
  window.ComissaoAdmin = ComissaoAdmin;
  window.ZNX.refactor_phase_5_loaded = window.ZNX.refactor_phase_5_loaded || {};
  window.ZNX.refactor_phase_5_loaded.ComissaoAdmin = true;
  // [Wave 36 marker v224.17] confirma extract executado
  window.ComissaoAdmin_v224_17_wave36 = true;
})();
