/*
|--------------------------------------------------------------------------
| Agência PSI
|--------------------------------------------------------------------------
| Criado e desenvolvido por Leonardo Nohama
|
| Tecnologia aplicada à escuta.
| Estrutura para o cuidado.
|
| Arquivo: src/composables/useFeriados.js
| Data: 2026
| Local: São Carlos/SP — Brasil
|--------------------------------------------------------------------------
| © 2026 — Todos os direitos reservados
|--------------------------------------------------------------------------
*/

import { ref, computed } from 'vue';
import { supabase } from '@/lib/supabase/client';
import { tenantDb } from '@/lib/supabase/tenantClient';
import { getFeriadosNacionais } from '@/utils/feriadosBR';
import { useMelissaCacheStore, MELISSA_CACHE_TTL } from '@/stores/melissaCacheStore';

// opts.cache (opt-in): habilita stale-while-revalidate via melissaCacheStore.
// Default false pra preservar comportamento em páginas SaaS/admin que
// editam feriados (esperam invalidação imediata após criar/remover).
export function useFeriados(opts = {}) {
    const useCache = !!opts.cache;
    const cache = useCache ? useMelissaCacheStore() : null;

    const ano = ref(new Date().getFullYear());
    const loading = ref(false);
    const municipais = ref([]); // linhas da tabela `feriados`

    // ── Nacionais (algoritmo, sem DB) ─────────────────────────
    const nacionais = computed(() => getFeriadosNacionais(ano.value).map((f) => ({ ...f, tipo: 'nacional' })));

    // ── Todos juntos, ordenados por data ─────────────────────
    const todos = computed(() => [...nacionais.value, ...municipais.value.map((f) => ({ ...f, tipo: f.tipo || 'municipal' }))].sort((a, b) => a.data.localeCompare(b.data)));

    // ── Feriados de um mês (1–12) ─────────────────────────────
    function doMes(mes) {
        const m = String(mes).padStart(2, '0');
        const prefix = `${ano.value}-${m}`;
        return todos.value.filter((f) => f.data.startsWith(prefix));
    }

    // ── Próximos N dias ───────────────────────────────────────
    function proximos(dias = 30) {
        const hoje = new Date();
        const limite = new Date(hoje);
        limite.setDate(limite.getDate() + dias);
        const hojeISO = toISO(hoje);
        const limiteISO = toISO(limite);
        return todos.value.filter((f) => f.data >= hojeISO && f.data <= limiteISO);
    }

    function toISO(d) {
        return `${d.getFullYear()}-${String(d.getMonth() + 1).padStart(2, '0')}-${String(d.getDate()).padStart(2, '0')}`;
    }

    async function _doFetch(tenantId, cacheKey) {
        const { data, error } = await tenantDb().from('feriados')
            .select('*')
            .gte('data', `${ano.value}-01-01`)
            .lte('data', `${ano.value}-12-31`)
            .order('data');
        if (error) throw error;
        const rows = data || [];
        if (cache && cacheKey) cache.set('feriados', rows, cacheKey);
        municipais.value = rows;
        return rows;
    }

    // ── Load municipais do Supabase ───────────────────────────
    async function load(tenantId, year) {
        if (year) ano.value = year;
        if (!tenantId) return;

        if (cache) {
            const cacheKey = `${tenantId}:${ano.value}`;
            const cached = cache.get('feriados', cacheKey, MELISSA_CACHE_TTL.feriados);
            if (cached) {
                municipais.value = cached;
                _doFetch(tenantId, cacheKey).catch((e) => {
                    // eslint-disable-next-line no-console
                    console.warn('[useFeriados] revalidate', e);
                });
                return;
            }
            loading.value = true;
            try { await _doFetch(tenantId, cacheKey); }
            finally { loading.value = false; }
            return;
        }

        // Comportamento legado (sem cache) — páginas de admin que editam.
        loading.value = true;
        try {
            const { data, error } = await tenantDb().from('feriados')
                .select('*')
                .gte('data', `${ano.value}-01-01`)
                .lte('data', `${ano.value}-12-31`)
                .order('data');
            if (error) throw error;
            municipais.value = data || [];
        } finally {
            loading.value = false;
        }
    }

    // ── Criar feriado municipal ───────────────────────────────
    async function criar(payload) {
        const { data, error } = await tenantDb().from('feriados').insert(payload).select().single();
        if (error) throw error;
        municipais.value = [...municipais.value, data].sort((a, b) => a.data.localeCompare(b.data));
        if (cache) cache.invalidate('feriados');
        return data;
    }

    // ── Remover feriado municipal ─────────────────────────────
    async function remover(id) {
        const { error } = await tenantDb().from('feriados').delete().eq('id', id);
        if (error) throw error;
        municipais.value = municipais.value.filter((f) => f.id !== id);
        if (cache) cache.invalidate('feriados');
    }

    // ── Verificar duplicata ───────────────────────────────────
    function isDuplicata(data, nome) {
        return todos.value.some((f) => f.data === data && f.nome.trim().toLowerCase() === nome.trim().toLowerCase());
    }

    // ── Converter para eventos do FullCalendar (background) ──
    function toFcEvents(lista) {
        return lista.map((f) => ({
            id: `feriado_${f.id || f.data}_${f.nome}`,
            title: f.nome,
            start: f.data,
            allDay: true,
            display: 'background',
            color: 'rgba(251, 191, 36, 0.25)',
            extendedProps: { _feriado: true, tipo: f.tipo }
        }));
    }

    const fcEvents = computed(() => toFcEvents(todos.value));

    return {
        ano,
        loading,
        nacionais,
        municipais,
        todos,
        fcEvents,
        load,
        criar,
        remover,
        doMes,
        proximos,
        isDuplicata
    };
}
