/**
 * Alpine.js CSP-safe lazy component loader.
 *
 * Scans the DOM for x-data attributes that match known lazy components.
 * Only imports the JS modules for components actually present on the page.
 * After all needed modules are loaded, calls Alpine.start().
 *
 * Dynamic import() is CSP-compliant (no eval / new Function).
 */
import Alpine from '@alpinejs/csp';

/**
 * Map of Alpine component name → dynamic import function.
 * Each module registers itself via Alpine.data() as a side effect.
 */
const lazyComponentMap = {
    // --- Components only needed on specific pages ---
    'adminSubmenu':    () => import('./components/admin-submenu.js'),
    'passwordToggle':  () => import('./components/password-toggle.js'),

    // --- Modal components (only on release pages) ---
    'nfoModal':        () => import('./components/nfo-modal.js'),
    'filelistModal':   () => import('./components/filelist-modal.js'),
    'previewModal':    () => import('./components/preview-modal.js'),
    'mediainfoModal':  () => import('./components/mediainfo-modal.js'),
    'imageModal':      () => import('./components/image-modal.js'),

    // --- Page-specific components ---
    'moviesPage':      () => import('./components/movies-page.js'),
    'qualityFilter':   () => import('./components/quality-filter.js'),
    'contentToggle':   () => import('./components/content-toggle.js'),
    'contentDelete':   () => import('./components/content-toggle.js'),  // same file
    'releaseReport':   () => import('./components/release-report.js'),
    'adminReleaseReports': () => import('./components/release-report.js'),  // same file
    'adminReleaseList': () => import('./components/admin/release-list.js'),
    'showAddForm':     () => import('./components/admin/show-add.js'),
    'profileEdit':     () => import('./components/profile-edit.js'),
    'profilePage':     () => import('./components/profile-edit.js'),    // same file
    'copyToClipboard': () => import('./components/profile-edit.js'),    // same file
    'cartPage':        () => import('./components/cart-page.js'),
    'releaseMultiOps': () => import('./components/cart-page.js'),  // same file
    'seriesSeasonLoader': () => import('./components/series-season-loader.js'),
    'authPage':        () => import('./components/auth-page.js'),
    'otpInput':        () => import('./components/auth-page.js'),       // same file
    'loginMode':       () => import('./components/login-mode.js'),
    'passkeyLogin':    () => import('./components/passkey-login.js'),
    'passkeyManage':   () => import('./components/passkey-manage.js'),
    'adminUserPasskeys': () => import('./components/admin-user-passkeys.js'),

    // --- Admin components (includes Chart.js — heavy) ---
    'adminDashboard':  () => import('./components/admin/dashboard.js'),
    'adminGroups':     () => import('./components/admin/groups.js'),
    'adminFeatures':   () => import('./components/admin/features.js'),
    'adminUserEdit':   () => import('./components/admin/features.js'),  // same file
    'adminUserList':   () => import('./components/admin/user-list.js'),
    'adminDeletedUsers': () => import('./components/admin/features.js'), // same file
    'adminInvitations': () => import('./components/admin/features.js'), // same file
    'adminRegexForm':  () => import('./components/admin/features.js'),  // same file
    'tinyMceEditor':   () => import('./components/admin/features.js'),  // same file
    'verifyUser':      () => import('./components/admin/verify-user.js'),
    'tmuxEdit':        () => import('./components/admin/features.js'),  // same file
};

/**
 * Extract Alpine component names from all x-data attributes in the DOM.
 * Handles: x-data="componentName", x-data="componentName()", x-data="{ ... }" (skipped).
 */
function getUsedComponentNames() {
    const names = new Set();
    document.querySelectorAll('[x-data]').forEach(el => {
        const raw = (el.getAttribute('x-data') || '').trim();
        // Skip inline objects like { show: true }
        if (!raw || raw.startsWith('{')) return;
        // Extract identifier before ( or whitespace
        const match = raw.match(/^([a-zA-Z_$][a-zA-Z0-9_$]*)/);
        if (match) names.add(match[1]);
    });
    return names;
}

/**
 * Load only the lazy components found on the current page, then start Alpine.
 */
export function loadAndStart() {
    const usedNames = getUsedComponentNames();
    const imports = new Set(); // deduplicate (multiple names → same file)

    for (const name of usedNames) {
        if (lazyComponentMap[name]) {
            imports.add(lazyComponentMap[name]);
        }
    }

    if (imports.size === 0) {
        Alpine.start();
        enableTransitions();
        return;
    }

    // Load all needed modules in parallel, then start Alpine
    Promise.all([...imports].map(fn => fn()))
        .then(() => {
            Alpine.start();
            enableTransitions();
        })
        .catch(err => {
            console.error('[lazy-loader] Failed to load component:', err);
            Alpine.start();
            enableTransitions();
        });
}

function enableTransitions() {
    requestAnimationFrame(() => {
        requestAnimationFrame(() => {
            document.documentElement.removeAttribute('data-loading');
        });
    });
}
