/**
 * CSV Viewer functionality
 * Automatically processes and displays CSV data when pasted
 * Using Papa Parse for robust CSV handling
 */

document.addEventListener('DOMContentLoaded', function() {
    // DOM Elements
    const csvInput = document.getElementById('csvInput');
    const delimiterSelect = document.getElementById('delimiter');
    const hasHeaderCheckbox = document.getElementById('hasHeader');
    const outputDiv = document.getElementById('output');

    // Variables to store data
    let csvData = [];
    let headers = [];
    let currentSortColumn = null;
    let sortDirection = 1; // 1 for ascending, -1 for descending
    
    // Add input event listener with debounce to process CSV when pasted
    let debounceTimer;
    csvInput.addEventListener('input', function() {
        clearTimeout(debounceTimer);
        debounceTimer = setTimeout(function() {
            if (csvInput.value.trim() !== '') {
                processCSV();
            }
        }, 300); // 300ms debounce delay
    });

    // Add paste event listener to format CSV data on paste
    csvInput.addEventListener('paste', function(e) {
        // Let the paste happen naturally, then process after a brief delay
        setTimeout(function() {
            const text = csvInput.value;
            if (text && text.length > 0) {
                // Auto-detect delimiter
                autoDetectDelimiter(text);
                // Process immediately after paste
                processCSV();
            }
        }, 50); // Slightly longer delay to ensure paste completes
    });
    
    // Add change listeners to delimiter and header options to reprocess data
    delimiterSelect.addEventListener('change', function() {
        if (csvInput.value.trim() !== '') {
            processCSV();
        }
    });
    
    hasHeaderCheckbox.addEventListener('change', function() {
        if (csvInput.value.trim() !== '') {
            processCSV();
        }
    });

    /**
     * Auto-detect the delimiter in pasted CSV data
     */
    function autoDetectDelimiter(text) {
        // Count occurrences of common delimiters
        const firstFewLines = text.split('\n').slice(0, 5).join('\n');
        const counts = {
            ',': (firstFewLines.match(/,/g) || []).length,
            ';': (firstFewLines.match(/;/g) || []).length,
            '\t': (firstFewLines.match(/\t/g) || []).length,
            '|': (firstFewLines.match(/\|/g) || []).length
        };
        
        // Find the most common delimiter
        let maxCount = 0;
        let detectedDelimiter = ','; // default
        
        for (const [delimiter, count] of Object.entries(counts)) {
            if (count > maxCount) {
                maxCount = count;
                detectedDelimiter = delimiter;
            }
        }
        
        // Set the delimiter dropdown
        if (maxCount > 0) {
            delimiterSelect.value = detectedDelimiter === '\t' ? '\\t' : detectedDelimiter;
        }
    }

    /**
     * Process the CSV data based on selected options
     */
    function processCSV() {
        const csvText = csvInput.value.trim();
        if (!csvText) {
            outputDiv.innerHTML = '<h3>Output</h3><p class="alert alert-info">Paste CSV data above to view it as a table.</p>';
            return;
        }

        try {
            // Show processing message
            outputDiv.innerHTML = '<h3>Output</h3><p class="alert alert-info">Processing data...</p>';
            
            // Parse CSV using Papa Parse
            const delimiter = delimiterSelect.value;
            const hasHeader = hasHeaderCheckbox.checked;
            
            // Enhanced parsing options
            Papa.parse(csvText, {
                delimiter: delimiter,
                header: hasHeader,
                skipEmptyLines: 'greedy', // Skip truly empty lines
                dynamicTyping: true, // Automatically convert numeric values
                trimHeaders: true, // Trim whitespace from headers
                complete: function(results) {
                    if (results.errors.length > 0) {
                        showError('Error parsing CSV: ' + results.errors[0].message);
                        return;
                    }
                    
                    if (results.data.length === 0 || (results.data.length === 1 && Object.keys(results.data[0]).length === 0)) {
                        showError('No valid data found. Please check your CSV format and delimiter.');
                        return;
                    }
                    
                    csvData = results.data;
                    
                    // Handle headers
                    if (hasHeader) {
                        if (results.meta.fields && results.meta.fields.length > 0) {
                            headers = results.meta.fields.map(h => h.trim());
                        } else {
                            // Fallback if no headers detected
                            headers = Object.keys(results.data[0] || {}).map((_, i) => `Column${i + 1}`);
                        }
                    } else {
                        headers = Object.keys(results.data[0] || {}).map((_, i) => `Column${i + 1}`);
                    }
                    
                    // Preview the data
                    previewData();
                },
                error: function(error) {
                    showError('Error processing CSV: ' + error.message);
                }
            });
        } catch (error) {
            showError('Error processing CSV: ' + error.message);
        }
    }

    /**
     * Preview the CSV data in a table with sortable columns
     */
    function previewData() {
        if (csvData.length === 0) {
            showError('No data to preview.');
            return;
        }
        
        // Limit preview to first 500 rows
        const previewData = csvData.slice(0, 500);
        
        // Generate table HTML
        let tableHtml = '<h3>Data Preview</h3>';
        tableHtml += `<p>Showing ${previewData.length} of ${csvData.length} rows</p>`;
        tableHtml += '<div class="table-responsive"><table class="tool-table">';
        
        // Table headers with sort functionality
        tableHtml += '<thead><tr>';
        headers.forEach(header => {
            const isSorted = header === currentSortColumn;
            const sortClass = isSorted ? (sortDirection > 0 ? 'sort-asc' : 'sort-desc') : '';
            tableHtml += `<th class="${sortClass}" data-column="${header}">${header} ${isSorted ? (sortDirection > 0 ? '↑' : '↓') : ''}</th>`;
        });
        tableHtml += '</tr></thead>';
        
        // Table body with improved cell formatting
        tableHtml += '<tbody>';
        previewData.forEach(row => {
            tableHtml += '<tr>';
            headers.forEach(header => {
                const cellValue = row[header];
                // Format cell value based on type
                let formattedValue = '';
                
                if (cellValue === null || cellValue === undefined) {
                    formattedValue = '<span class="empty-cell">(empty)</span>';
                } else if (typeof cellValue === 'string') {
                    formattedValue = escapeHtml(cellValue);
                } else {
                    formattedValue = String(cellValue);
                }
                
                tableHtml += `<td>${formattedValue}</td>`;
            });
            tableHtml += '</tr>';
        });
        tableHtml += '</tbody></table></div>';
        
        // Add stats summary
        const totalRows = csvData.length;
        const totalColumns = headers.length;
        tableHtml += `<div class="data-stats">
            <div class="stat-item">
                <span class="stat-label">Total Rows:</span>
                <span class="stat-value">${totalRows}</span>
            </div>
            <div class="stat-item">
                <span class="stat-label">Total Columns:</span>
                <span class="stat-value">${totalColumns}</span>
            </div>
        </div>`;
        
        // Display in output div
        outputDiv.innerHTML = tableHtml;
        
        // Add click event listeners to table headers for sorting
        const tableHeaders = outputDiv.querySelectorAll('th');
        tableHeaders.forEach(th => {
            th.addEventListener('click', () => {
                const column = th.getAttribute('data-column');
                sortData(column);
            });
        });
    }
    
    /**
     * Escape HTML special characters to prevent XSS
     */
    function escapeHtml(unsafe) {
        return unsafe
            .replace(/&/g, "&amp;")
            .replace(/</g, "&lt;")
            .replace(/>/g, "&gt;")
            .replace(/"/g, "&quot;")
            .replace(/'/g, "&#039;");
    }
    
    /**
     * Sort data by column
     */
    function sortData(column) {
        // Toggle sort direction if clicking the same column
        if (column === currentSortColumn) {
            sortDirection *= -1;
        } else {
            currentSortColumn = column;
            sortDirection = 1;
        }
        
        // Sort the data
        csvData.sort((a, b) => {
            const valueA = a[column] !== undefined ? a[column] : '';
            const valueB = b[column] !== undefined ? b[column] : '';
            
            // Try to sort numerically if possible
            if (typeof valueA === 'number' && typeof valueB === 'number') {
                return (valueA - valueB) * sortDirection;
            }
            
            // Handle dates
            const dateA = new Date(valueA);
            const dateB = new Date(valueB);
            if (!isNaN(dateA) && !isNaN(dateB)) {
                return (dateA - dateB) * sortDirection;
            }
            
            // Otherwise sort alphabetically
            return String(valueA).localeCompare(String(valueB)) * sortDirection;
        });
        
        // Update the preview
        previewData();
    }

    /**
     * Show error message
     */
    function showError(message) {
        // Clear any existing alerts
        clearAlerts();
        
        const alert = document.createElement('div');
        alert.className = 'alert alert-error';
        alert.textContent = message;
        
        // Insert at the top of the output div
        const firstChild = outputDiv.querySelector('h3') ? 
            outputDiv.querySelector('h3').nextSibling : 
            outputDiv.firstChild;
            
        outputDiv.insertBefore(alert, firstChild);
    }
    
    /**
     * Show success message
     */
    function showSuccess(message) {
        const alert = document.createElement('div');
        alert.className = 'alert alert-success';
        alert.textContent = message;
        
        // Insert after the heading
        const firstChild = outputDiv.querySelector('h3') ? 
            outputDiv.querySelector('h3').nextSibling : 
            outputDiv.firstChild;
            
        outputDiv.insertBefore(alert, firstChild);
        
        // Auto-hide success message after 3 seconds
        setTimeout(() => {
            if (alert.parentNode === outputDiv) {
                alert.remove();
            }
        }, 3000);
    }
    
    /**
     * Clear all alert messages
     */
    function clearAlerts() {
        const alerts = outputDiv.querySelectorAll('.alert');
        alerts.forEach(alert => alert.remove());
    }
    
    // Check if there's already content in the textarea on page load
    if (csvInput.value.trim() !== '') {
        processCSV();
    }
});
