/**
 * Admin Panel - API Client & Utils
 * @version 2.0.0
 */

const API_BASE = 'api/admin.php';

// ================================
// Estado Global
// ================================
window.AdminState = {
    token: localStorage.getItem('admin_token'),
    currentUser: null,
    sites: [],
    currentSiteId: null,
    charts: {
        sites: null,
        events: null
    }
};

// ================================
// API Client
// ================================
const Api = {
    /**
     * Fazer requisição à API
     */
    async request(action, method = 'GET', body = null, showSpinner = false) {
        if (showSpinner) UI.showLoading();
        
        try {
            const options = {
                method,
                headers: {
                    'Content-Type': 'application/json'
                }
            };
            
            if (AdminState.token) {
                options.headers['Authorization'] = `Bearer ${AdminState.token}`;
            }
            
            if (body && method !== 'GET') {
                options.body = JSON.stringify(body);
            }
            
            const response = await fetch(`${API_BASE}?action=${action}`, options);
            
            // Se o servidor retornou erro 500/502/503 (DB down, etc), não deslogar
            if (response.status >= 500) {
                let data = {};
                try { data = await response.json(); } catch(e) {}
                throw new Error(data.message || 'Server error ' + response.status);
            }
            
            const data = await response.json();

            // Tratar 401 de forma diferente para login vs outras rotas
            if (response.status === 401) {
                // Para login, retornar os dados (contém mensagem de erro real)
                if (action === 'login') {
                    return data;
                }
                // Para outras rotas, significa sessão expirada - mas tentar 1x antes de deslogar
                if (!this._retrying) {
                    this._retrying = true;
                    try {
                        const retryResult = await this.request(action, method, body, false);
                        return retryResult;
                    } catch(e) {
                        Auth.logout();
                        throw new Error('Session expired');
                    } finally {
                        this._retrying = false;
                    }
                }
                Auth.logout();
                throw new Error('Session expired');
            }

            return data;
        } finally {
            if (showSpinner) UI.hideLoading();
        }
    },

    /**
     * GET request
     */
    async get(action, showSpinner = false) {
        return this.request(action, 'GET', null, showSpinner);
    },

    /**
     * POST request
     */
    async post(action, data, showSpinner = false) {
        return this.request(action, 'POST', data, showSpinner);
    },

    /**
     * PUT request
     */
    async put(action, data, showSpinner = false) {
        return this.request(action, 'PUT', data, showSpinner);
    },

    /**
     * DELETE request
     */
    async delete(action, showSpinner = false) {
        return this.request(action, 'DELETE', null, showSpinner);
    }
};

// ================================
// UI Utilities
// ================================
const UI = {
    /**
     * Mostrar loading overlay
     */
    showLoading(text = 'Carregando...') {
        const overlay = document.getElementById('loading-overlay');
        const textEl = document.getElementById('loading-text');
        if (textEl) textEl.textContent = text;
        if (overlay) overlay.classList.add('show');
    },

    /**
     * Esconder loading overlay
     */
    hideLoading() {
        const overlay = document.getElementById('loading-overlay');
        if (overlay) overlay.classList.remove('show');
    },

    /**
     * Mostrar toast notification
     */
    toast(message, type = 'info', duration = 3000) {
        let container = document.getElementById('toast-container');
        if (!container) {
            container = document.createElement('div');
            container.id = 'toast-container';
            container.className = 'toast-container';
            document.body.appendChild(container);
        }
        
        const toast = document.createElement('div');
        toast.className = `toast ${type}`;
        
        const icons = {
            success: 'fa-check-circle',
            error: 'fa-times-circle',
            warning: 'fa-exclamation-triangle',
            info: 'fa-info-circle'
        };
        
        toast.innerHTML = `
            <i class="fas ${icons[type] || icons.info}"></i>
            <span>${message}</span>
        `;
        
        container.appendChild(toast);
        
        setTimeout(() => {
            toast.style.animation = 'slideIn 0.3s ease reverse';
            setTimeout(() => toast.remove(), 300);
        }, duration);
    },

    /**
     * Confirmar ação
     */
    confirm(message, onConfirm, onCancel = null) {
        if (window.confirm(message)) {
            if (onConfirm) onConfirm();
        } else {
            if (onCancel) onCancel();
        }
    },

    /**
     * Prompt com validação
     */
    prompt(message, expectedValue, onSuccess) {
        const result = window.prompt(message);
        if (result === expectedValue) {
            onSuccess();
        } else if (result !== null) {
            UI.toast('Operação cancelada. Valor incorreto.', 'warning');
        }
    },

    /**
     * Copiar texto para clipboard
     */
    async copyToClipboard(text) {
        try {
            await navigator.clipboard.writeText(text);
            UI.toast('Copiado!', 'success', 1500);
            return true;
        } catch (err) {
            // Fallback
            const textarea = document.createElement('textarea');
            textarea.value = text;
            document.body.appendChild(textarea);
            textarea.select();
            document.execCommand('copy');
            document.body.removeChild(textarea);
            UI.toast('Copiado!', 'success', 1500);
            return true;
        }
    },

    /**
     * Adicionar classe loading a um botão
     */
    btnLoading(btn, loading = true) {
        if (loading) {
            btn.classList.add('loading');
            btn.disabled = true;
        } else {
            btn.classList.remove('loading');
            btn.disabled = false;
        }
    },

    /**
     * Mostrar/esconder elemento
     */
    show(selector) {
        const el = typeof selector === 'string' ? document.querySelector(selector) : selector;
        if (el) el.classList.remove('hidden');
    },

    hide(selector) {
        const el = typeof selector === 'string' ? document.querySelector(selector) : selector;
        if (el) el.classList.add('hidden');
    },

    /**
     * Atualizar texto de um elemento
     */
    setText(selector, text) {
        const el = document.querySelector(selector);
        if (el) el.textContent = text;
    },

    /**
     * Atualizar HTML de um elemento
     */
    setHtml(selector, html) {
        const el = document.querySelector(selector);
        if (el) el.innerHTML = html;
    },

    /**
     * Obter valor de input
     */
    getValue(selector) {
        const el = document.querySelector(selector);
        return el ? el.value : '';
    },

    /**
     * Definir valor de input
     */
    setValue(selector, value) {
        const el = document.querySelector(selector);
        if (el) el.value = value;
    }
};

// ================================
// Formatters
// ================================
const Format = {
    /**
     * Formatar valor em BRL
     */
    brl(value) {
        return new Intl.NumberFormat('pt-BR', {
            style: 'currency',
            currency: 'BRL'
        }).format(value || 0);
    },

    /**
     * Formatar número
     */
    number(value) {
        return new Intl.NumberFormat('pt-BR').format(value || 0);
    },

    /**
     * Formatar data
     */
    date(dateStr) {
        if (!dateStr) return '-';
        return new Date(dateStr).toLocaleDateString('pt-BR');
    },

    /**
     * Formatar data e hora
     */
    datetime(dateStr) {
        if (!dateStr) return '-';
        return new Date(dateStr).toLocaleString('pt-BR');
    },

    /**
     * Formatar hora
     */
    time(dateStr) {
        if (!dateStr) return '-';
        return new Date(dateStr).toLocaleTimeString('pt-BR', {
            hour: '2-digit',
            minute: '2-digit'
        });
    },

    /**
     * Formatar tipo de evento para exibição
     */
    eventType(type) {
        const types = {
            'page_view': '👁️ Visualização',
            'visit': '👁️ Visualização',
            'index_view': '🏠 Página Inicial',
            'consulta': '🔍 Consulta',
            'consulta_placa': '🚗 Consulta Placa',
            'consulta_debitos': '🔍 Consulta Débitos',
            'consulta_iniciada': '🔎 Consulta Iniciada',
            'consulta_realizada': '✅ Consulta Realizada',
            'consulta_erro': '❌ Erro Consulta',
            'cnpj_consulta': '🏢 CNPJ',
            'pix_gerado': '💰 PIX Gerado',
            'pix_iniciado': '💰 PIX Gerado',
            'pix_generated': '💰 PIX Gerado',
            'pix_generation_success': '✅ PIX Sucesso',
            'pix_copiado': '📋 PIX Copiado',
            'pix_codigo_copiado': '📋 PIX Copiado',
            'pix_modal_aberto': '📱 Modal PIX Aberto',
            'pix_modal_fechado': '❌ Modal PIX Fechado',
            'debitos_view': '📄 Página Débitos',
            'debito_selecionado': '📋 Débito Selecionado',
            'pagamento_iniciado': '💳 Pagamento Iniciado',
            'payment_confirmed': '✅ Pagamento Confirmado',
            'concluido': '✅ Concluído',
            'Concluído': '✅ Concluído',
            'erro': '❌ Erro',
            'session_start': '🚀 Sessão Iniciada'
        };
        return types[type] || type;
    },

    /**
     * Obter classe de badge para tipo de evento
     */
    eventBadgeClass(type) {
        const classes = {
            'page_view': 'bg-info',
            'visit': 'bg-info',
            'index_view': 'bg-info',
            'consulta': 'bg-primary',
            'consulta_placa': 'bg-primary',
            'consulta_debitos': 'bg-primary',
            'consulta_iniciada': 'bg-secondary',
            'consulta_realizada': 'bg-success',
            'consulta_erro': 'bg-danger',
            'cnpj_consulta': 'bg-dark',
            'pix_gerado': 'bg-success',
            'pix_iniciado': 'bg-success',
            'pix_generated': 'bg-success',
            'pix_generation_success': 'bg-success',
            'pix_copiado': 'bg-warning',
            'pix_codigo_copiado': 'bg-warning',
            'pix_modal_aberto': 'bg-info',
            'pix_modal_fechado': 'bg-secondary',
            'debitos_view': 'bg-info',
            'debito_selecionado': 'bg-purple',
            'pagamento_iniciado': 'bg-warning',
            'payment_confirmed': 'bg-success',
            'concluido': 'bg-primary',
            'Concluído': 'bg-primary',
            'erro': 'bg-danger',
            'session_start': 'bg-secondary'
        };
        return classes[type] || 'bg-secondary';
    },

    /**
     * Mascarar API Key
     */
    maskApiKey(key) {
        if (!key || key.length < 12) return key;
        return key.substring(0, 8) + '...' + key.substring(key.length - 4);
    },

    /**
     * Formatar localização
     */
    location(city, region) {
        if (!city) return '-';
        return region ? `${city}, ${region}` : city;
    }
};

// ================================
// Helpers
// ================================
const Helpers = {
    /**
     * Gerar senha aleatória
     */
    generatePassword(length = 12) {
        const chars = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789!@#$%';
        let password = '';
        for (let i = 0; i < length; i++) {
            password += chars.charAt(Math.floor(Math.random() * chars.length));
        }
        return password;
    },

    /**
     * Debounce function
     */
    debounce(func, wait) {
        let timeout;
        return function executedFunction(...args) {
            const later = () => {
                clearTimeout(timeout);
                func(...args);
            };
            clearTimeout(timeout);
            timeout = setTimeout(later, wait);
        };
    },

    /**
     * Throttle function
     */
    throttle(func, limit) {
        let inThrottle;
        return function(...args) {
            if (!inThrottle) {
                func.apply(this, args);
                inThrottle = true;
                setTimeout(() => inThrottle = false, limit);
            }
        };
    },

    /**
     * Verificar se é super admin
     */
    isSuperAdmin() {
        return AdminState.currentUser?.is_super_admin === true;
    },

    /**
     * Obter ID do site do usuário
     */
    getUserSiteId() {
        return AdminState.currentUser?.site_id || null;
    },

    /**
     * Query string builder
     */
    buildQuery(params) {
        return Object.entries(params)
            .filter(([_, v]) => v !== null && v !== undefined && v !== '')
            .map(([k, v]) => `${k}=${encodeURIComponent(v)}`)
            .join('&');
    }
};

// ================================
// Modal Lazy Loader
// ================================
const Modal = {
    _cache: {},
    _container: null,

    /**
     * Inicializa container de modais
     */
    init() {
        if (!this._container) {
            this._container = document.getElementById('modals-container');
            if (!this._container) {
                this._container = document.createElement('div');
                this._container.id = 'modals-container';
                document.body.appendChild(this._container);
            }
        }
    },

    /**
     * Carrega e exibe um modal
     */
    async load(name) {
        this.init();

        // Verificar se já está no DOM
        let modal = document.getElementById(`modal-${name}`);
        if (modal) {
            return new bootstrap.Modal(modal);
        }

        // Verificar cache
        if (this._cache[name]) {
            this._container.insertAdjacentHTML('beforeend', this._cache[name]);
            modal = document.getElementById(`modal-${name}`);
            return new bootstrap.Modal(modal);
        }

        // Carregar do servidor
        try {
            const response = await fetch(`assets/modals/${name}.html`);
            if (!response.ok) throw new Error('Modal not found');

            const html = await response.text();
            this._cache[name] = html;
            this._container.insertAdjacentHTML('beforeend', html);

            modal = document.getElementById(`modal-${name}`);
            if (modal) {
                return new bootstrap.Modal(modal);
            }
        } catch (error) {
            // Silenciar em produção
        }
        return null;
    },

    /**
     * Fecha e remove modal do DOM
     */
    close(name) {
        const modal = document.getElementById(`modal-${name}`);
        if (modal) {
            const bsModal = bootstrap.Modal.getInstance(modal);
            if (bsModal) bsModal.hide();
        }
    }
};

// Expor globalmente para compatibilidade
window.Api = Api;
window.UI = UI;
window.Format = Format;
window.Helpers = Helpers;
window.Modal = Modal;

// Funções de compatibilidade com código legado
window.apiRequest = (action, method, body, showSpinner) => Api.request(action, method, body, showSpinner);
window.showLoading = UI.showLoading;
window.hideLoading = UI.hideLoading;
window.formatBRL = Format.brl;
window.formatEventType = Format.eventType;
window.getBadgeClass = Format.eventBadgeClass;
window.copyToClipboard = (id) => {
    const el = document.getElementById(id);
    if (el) UI.copyToClipboard(el.value);
};
