(function () {
    'use strict';
    const baseUrl = window.projectsBaseUrl || '';
    const csrfToken = window.projectsCsrfToken || '';
    const collection = document.getElementById('projectsCollection');
    const duplicateModalElement = document.getElementById('duplicateProjectModal');
    const exportModalElement = document.getElementById('exportProjectModal');
    const importModalElement = document.getElementById('importProjectModal');
    if (!duplicateModalElement || !exportModalElement || !importModalElement) return;
    const duplicateModal = bootstrap.Modal.getOrCreateInstance(duplicateModalElement);
    const exportModal = bootstrap.Modal.getOrCreateInstance(exportModalElement);
    const importModal = bootstrap.Modal.getOrCreateInstance(importModalElement);
    let sourceCard = null;

    const slugify = value => String(value || '').toLowerCase().trim().replace(/[^a-z0-9]+/g, '-').replace(/^-+|-+$/g, '');
    async function readJson(response) {
        const text = await response.text();
        try { return JSON.parse(text); } catch (_) { throw new Error(text || `Request failed (${response.status}).`); }
    }
    function busy(button, active, label) {
        if (!button) return;
        if (active) { button.dataset.originalHtml = button.innerHTML; button.disabled = true; button.innerHTML = `<span class="spinner-border spinner-border-sm me-1"></span>${label}`; }
        else { button.disabled = false; button.innerHTML = button.dataset.originalHtml || button.innerHTML; }
    }
    function showDuplicate(card) {
        sourceCard = card;
        const name = card.dataset.name || 'Project';
        document.getElementById('duplicateProjectName').value = `${name} copy`;
        document.getElementById('duplicateProjectSlug').value = `${card.dataset.projectSlug}-copy`;
        document.getElementById('duplicateProjectDescription').value = card.dataset.description || '';
        const sqlite = card.dataset.database === 'sqlite';
        document.getElementById('duplicateShareChoice').classList.toggle('d-none', sqlite);
        document.getElementById('duplicateSqliteCopyChoice').classList.toggle('d-none', !sqlite);
        const preferred = duplicateModalElement.querySelector(`[name="connection_mode"][value="${sqlite ? 'sqlite_copy' : 'share'}"]`);
        if (preferred) preferred.checked = true;
        duplicateModal.show();
    }
    function showExport(card) {
        sourceCard = card;
        document.getElementById('exportProjectName').textContent = card.dataset.name || '';
        document.getElementById('exportProjectForm').action = `${baseUrl}/project/${encodeURIComponent(card.dataset.projectSlug)}/export`;
        const sqliteOption = document.getElementById('exportSqliteOption');
        sqliteOption.classList.toggle('d-none', card.dataset.database !== 'sqlite');
        if (card.dataset.database !== 'sqlite') sqliteOption.querySelector('input').checked = false;
        exportModal.show();
    }

    collection?.addEventListener('click', event => {
        const action = event.target.closest('[data-project-action="duplicate"], [data-project-action="export"]');
        if (!action) return;
        event.preventDefault();
        const card = action.closest('[data-project-card]');
        if (!card) return;
        action.dataset.projectAction === 'duplicate' ? showDuplicate(card) : showExport(card);
    });

    let duplicateSlugManual = false;
    document.getElementById('duplicateProjectSlug')?.addEventListener('input', () => { duplicateSlugManual = true; });
    document.getElementById('duplicateProjectName')?.addEventListener('input', event => {
        if (!duplicateSlugManual) document.getElementById('duplicateProjectSlug').value = slugify(event.target.value);
    });
    duplicateModalElement.addEventListener('show.bs.modal', () => { duplicateSlugManual = false; });
    document.getElementById('duplicateProjectForm')?.addEventListener('submit', async event => {
        event.preventDefault();
        if (!sourceCard || !event.currentTarget.reportValidity()) return;
        const button = document.getElementById('duplicateProjectSubmit');
        busy(button, true, 'Duplicating…');
        const payload = Object.fromEntries(new FormData(event.currentTarget).entries());
        payload._token = csrfToken;
        payload.include_custom = event.currentTarget.querySelector('[name="include_custom"]').checked;
        try {
            const response = await fetch(`${baseUrl}/project/${encodeURIComponent(sourceCard.dataset.projectSlug)}/duplicate`, { method: 'POST', headers: { 'Content-Type': 'application/json', Accept: 'application/json' }, body: JSON.stringify(payload) });
            const data = await readJson(response);
            if (!response.ok || !data.success) throw new Error(data.message || 'Project duplication failed.');
            duplicateModal.hide();
            const result = await Swal.fire({ title: 'Duplicate ready', text: data.message, icon: 'success', showCancelButton: true, confirmButtonText: 'Open duplicate', cancelButtonText: 'Stay in Projects' });
            if (result.isConfirmed) window.location.href = data.open_url;
            else window.location.reload();
        } catch (error) { Swal.fire('Could not duplicate project', error.message, 'error'); }
        finally { busy(button, false); }
    });

    const inspectForm = document.getElementById('importInspectForm');
    const commitForm = document.getElementById('importCommitForm');
    const packageInput = document.getElementById('projectPackageFile');
    const packageDrop = document.getElementById('projectPackageDrop');
    function setImportStep(step) {
        const review = step === 'review';
        inspectForm.classList.toggle('d-none', review);
        commitForm.classList.toggle('d-none', !review);
        document.querySelectorAll('[data-import-step-indicator]').forEach(item => item.classList.toggle('active', item.dataset.importStepIndicator === step));
    }
    function resetImport() {
        inspectForm.reset(); commitForm.reset(); setImportStep('upload');
        document.getElementById('importCodeConfirmation').classList.add('d-none');
        document.getElementById('importCodeConfirmation').querySelector('input').required = false;
        packageDrop.querySelector('strong').textContent = 'Choose a .ppphp project package';
    }
    importModalElement.addEventListener('hidden.bs.modal', resetImport);
    document.getElementById('openProjectImport')?.addEventListener('click', () => { resetImport(); importModal.show(); });
    packageInput?.addEventListener('change', () => { if (packageInput.files[0]) packageDrop.querySelector('strong').textContent = packageInput.files[0].name; });
    ['dragenter', 'dragover'].forEach(type => packageDrop?.addEventListener(type, event => { event.preventDefault(); packageDrop.classList.add('is-dragging'); }));
    ['dragleave', 'drop'].forEach(type => packageDrop?.addEventListener(type, event => { event.preventDefault(); packageDrop.classList.remove('is-dragging'); }));
    packageDrop?.addEventListener('drop', event => { if (event.dataTransfer?.files?.length) { packageInput.files = event.dataTransfer.files; packageInput.dispatchEvent(new Event('change')); } });
    inspectForm?.addEventListener('submit', async event => {
        event.preventDefault();
        if (!inspectForm.reportValidity()) return;
        const button = document.getElementById('inspectPackageSubmit');
        busy(button, true, 'Inspecting…');
        const form = new FormData(inspectForm); form.append('_token', csrfToken);
        try {
            const response = await fetch(`${baseUrl}/projects/import/inspect`, { method: 'POST', headers: { Accept: 'application/json' }, body: form });
            const data = await readJson(response);
            if (!response.ok || !data.success) throw new Error(data.message || 'Package inspection failed.');
            renderPreview(data);
            setImportStep('review');
        } catch (error) { Swal.fire('Package rejected', error.message, 'error'); }
        finally { busy(button, false); }
    });
    function renderPreview(data) {
        const summary = data.summary || {}; const content = summary.content || {}; const database = summary.database || {};
        document.getElementById('importPackageToken').value = data.token;
        document.getElementById('importProjectName').value = summary.name || 'Imported project';
        document.getElementById('importProjectSlug').value = summary.suggested_slug || 'imported-project';
        document.getElementById('importProjectDescription').value = summary.description || '';
        const warnings = [...(summary.warnings || [])];
        if (data.conflicts?.original_slug_exists) warnings.push(`The original slug was already in use, so “${data.conflicts.resolved_slug}” was suggested.`);
        if (summary.requires_code_confirmation) warnings.push(`${summary.executable_files.length} executable custom file(s) require your review.`);
        const preview = document.getElementById('importPackagePreview'); preview.replaceChildren();
        const heading = document.createElement('div'); heading.innerHTML = `<h6><i class="bi bi-patch-check-fill text-success me-1"></i> Package verified</h6><small class="text-muted">${summary.entry_count || 0} files · ${Math.round((summary.expanded_bytes || 0) / 1024)} KB expanded</small>`;
        const badge = document.createElement('span'); badge.className = 'badge text-bg-primary-subtle text-primary align-self-start'; badge.textContent = database.label || database.type || 'Database design';
        const copy = document.createElement('p'); copy.textContent = 'The checksum catalog and every archive path passed validation. Credentials are not contained in this package.';
        const chips = document.createElement('div'); chips.className = 'preview-chips';
        [`${content.configuration_files || 0} config files`, `${content.custom_files || 0} custom files`, database.sqlite_included ? 'SQLite data included' : 'No database data'].forEach(text => { const chip = document.createElement('span'); chip.textContent = text; chips.appendChild(chip); });
        preview.append(heading, badge, copy, chips);
        if (warnings.length) { const warning = document.createElement('div'); warning.className = 'preview-warning'; warning.innerHTML = '<i class="bi bi-exclamation-triangle-fill me-1"></i>' + warnings.join(' '); preview.appendChild(warning); }
        const code = document.getElementById('importCodeConfirmation'); code.classList.toggle('d-none', !summary.requires_code_confirmation); code.querySelector('input').required = !!summary.requires_code_confirmation;
    }
    document.getElementById('importBackButton')?.addEventListener('click', () => setImportStep('upload'));
    commitForm?.addEventListener('submit', async event => {
        event.preventDefault();
        if (!commitForm.reportValidity()) return;
        const button = document.getElementById('importProjectSubmit'); busy(button, true, 'Importing…');
        const payload = Object.fromEntries(new FormData(commitForm).entries()); payload._token = csrfToken;
        payload.allow_code = commitForm.querySelector('[name="allow_code"]').checked;
        try {
            const response = await fetch(`${baseUrl}/projects/import/commit`, { method: 'POST', headers: { 'Content-Type': 'application/json', Accept: 'application/json' }, body: JSON.stringify(payload) });
            const data = await readJson(response);
            if (!response.ok || !data.success) throw new Error(data.message || 'Project import failed.');
            importModal.hide();
            const result = await Swal.fire({ title: 'Project imported', text: data.message, icon: 'success', showCancelButton: true, confirmButtonText: 'Open project', cancelButtonText: 'Stay in Projects' });
            if (result.isConfirmed) window.location.href = data.open_url; else window.location.reload();
        } catch (error) { Swal.fire('Could not import project', error.message, 'error'); }
        finally { busy(button, false); }
    });
})();
