Filter by
$(document).ready(function () { var DEBUG = true function log () { if (!DEBUG) return var args = Array.prototype.slice.call(arguments) args.unshift('[W2C Import]') console.log.apply(console, args) } function warn () { if (!DEBUG) return var args = Array.prototype.slice.call(arguments) args.unshift('[W2C Import]') console.warn.apply(console, args) } function error () { var args = Array.prototype.slice.call(arguments) args.unshift('[W2C Import]') console.error.apply(console, args) } log('script loaded BUILD=direct-upload-v5', { href: window.location.href, readyState: document.readyState, hasAjaxLink: $('#ajaxlink').length > 0, directUploadUrl: $('#w2c_direct_upload_url').val() || null, uploadAjaxUrl: $('#w2c_upload_ajax_url').val() || null }) // --- Configure page: AJAX upload (shows real HTTP errors instead of endless spinner) --- var $submitBtn = $('button[name="submitW2CcustomImportModule"], input[name="submitW2CcustomImportModule"]') var $forms = $submitBtn.closest('form') if (!$forms.length) { $forms = $('#module_form, form.form-horizontal').filter(function () { return $(this).find('[name="W2CCUSTOMIMPORT_UPLOAD"], [name="submitW2CcustomImportModule"]').length > 0 }) } // Start from CSV already on server (FTP) — skips browser upload entirely $('#w2c_start_server_csv').on('click', function () { var name =($.trim($('#w2c_server_csv').val() || '')) var moduleUrl = $('#w2c_module_url').val() || '' var $form = $('button[name="submitW2CcustomImportModule"], input[name="submitW2CcustomImportModule"]').closest('form') if (!$form.length) { $form = $('#module_form') } function formFlag (fieldName) { var checked = $form.find('[name="' + fieldName + '"]:checked').val() if (typeof checked !== 'undefined') { return parseInt(checked, 10) === 1 ? 1 : 0 } var raw = $form.find('[name="' + fieldName + '"]').val() return parseInt(raw, 10) === 1 ? 1 : 0 } if (!name) { alert('Enter the CSV filename (must already be in modules/w2ccustomimport/cache/)') return } if (!/\.csv$/i.test(name)) { alert('Filename must end with .csv') return } if (name.indexOf('/') >= 0 || name.indexOf('\\') >= 0 || name.indexOf('..') >= 0) { alert('Enter only the filename, not a path') return } if (!moduleUrl) { alert('Module URL missing — hard refresh the page') return } // Use the toggles currently shown on the form (Dry run / Import images) var dryRun = formFlag('W2CCUSTOMIMPORT_DRY_RUN') var liveImages = formFlag('W2CCUSTOMIMPORT_LIVE_MODE') var reportUrl = moduleUrl + '&menu=report&file=' + encodeURIComponent(name) + '&dry_run=' + dryRun + '&live_images=' + liveImages log('Starting from server file', { name: name, dryRun: dryRun, liveImages: liveImages, reportUrl: reportUrl }) if (dryRun === 1) { if (!window.confirm('Dry run is ON — nothing will be saved.\n\nClick Cancel, turn Dry run OFF (and Import images ON if you want images), then start again.\n\nClick OK to continue with dry run anyway.')) { return } } window.location.href = reportUrl }) if ($forms.length) { log('configure form found — using AJAX upload', $forms.length) $forms.on('submit', function (e) { e.preventDefault() e.stopImmediatePropagation() var $form = $(this) var $file = $form.find('input[type="file"][name="W2CCUSTOMIMPORT_UPLOAD"]') var file = $file.length && $file[0].files && $file[0].files[0] ? $file[0].files[0] : null var startedAt = Date.now() log('AJAX UPLOAD start', { action: $form.attr('action'), dryRun: $form.find('[name="W2CCUSTOMIMPORT_DRY_RUN"]:checked').val() || $form.find('[name="W2CCUSTOMIMPORT_DRY_RUN"]').val(), liveImages: $form.find('[name="W2CCUSTOMIMPORT_LIVE_MODE"]:checked').val() || $form.find('[name="W2CCUSTOMIMPORT_LIVE_MODE"]').val(), file: file ? { name: file.name, size: file.size, type: file.type } : null }) if (!file) { error('No CSV selected') alert('Please choose a CSV file first.') return false } log('CSV size MB:', (file.size / 1024 / 1024).toFixed(2)) var directUrl = $('#w2c_direct_upload_url').val() || '' var directToken = $('#w2c_direct_upload_token').val() || '' var moduleUrl = $('#w2c_module_url').val() || '' var actionUrl = directUrl || $('#w2c_upload_ajax_url').val() || '' if (!actionUrl) { error('Missing upload URL — hard refresh after deploy') alert('Upload URL missing. Hard refresh (Ctrl+F5) after deploying files.') return false } $submitBtn.prop('disabled', true) var originalText = $submitBtn.text() $submitBtn.text('Uploading…') var beat = 0 var heartbeat = setInterval(function () { beat++ warn('upload still in flight…', beat + 's', { elapsedMs: Date.now() - startedAt }) }, 1000) // Minimal payload — do not post entire HelperForm to admin var formData = new FormData() formData.append('W2CCUSTOMIMPORT_UPLOAD', file, file.name) formData.append('W2CCUSTOMIMPORT_DRY_RUN', $form.find('[name="W2CCUSTOMIMPORT_DRY_RUN"]:checked').val() || $form.find('[name="W2CCUSTOMIMPORT_DRY_RUN"]').val() || '0') formData.append('W2CCUSTOMIMPORT_LIVE_MODE', $form.find('[name="W2CCUSTOMIMPORT_LIVE_MODE"]:checked').val() || $form.find('[name="W2CCUSTOMIMPORT_LIVE_MODE"]').val() || '0') formData.append('W2CCUSTOMIMPORT_REPLACE_IMAGES', $form.find('[name="W2CCUSTOMIMPORT_REPLACE_IMAGES"]:checked').val() || $form.find('[name="W2CCUSTOMIMPORT_REPLACE_IMAGES"]').val() || '0') formData.append('W2CCUSTOMIMPORT_RAW_IMAGES', $form.find('[name="W2CCUSTOMIMPORT_RAW_IMAGES"]:checked').val() || $form.find('[name="W2CCUSTOMIMPORT_RAW_IMAGES"]').val() || '0') formData.append('IMPORT_PRODUCTS_IMG_URL', $form.find('[name="IMPORT_PRODUCTS_IMG_URL"]').val() || '') formData.append('IMPORT_CATEGORIES_IMG_URL', $form.find('[name="IMPORT_CATEGORIES_IMG_URL"]').val() || '') formData.append('IMPORT_SEPARATOR', $form.find('[name="IMPORT_SEPARATOR"]').val() || ',') if (directUrl && directToken) { formData.append('w2c_upload_token', directToken) log('Uploading via DIRECT FO endpoint (no admin session)', directUrl) } else { formData.append('task', 'upload_csv') formData.append('ajax', '1') log('Uploading via AdminCustomAjax fallback', actionUrl) } fetch(actionUrl, { method: 'POST', body: formData, credentials: 'same-origin', headers: { 'X-Requested-With': 'XMLHttpRequest' } }).then(function (res) { var ms = Date.now() - startedAt log('UPLOAD HTTP response', { status: res.status, statusText: res.statusText, ok: res.ok, contentType: res.headers.get('content-type'), ms: ms }) return res.text().then(function (text) { return { res: res, text: text, ms: ms } }) }).then(function (result) { clearInterval(heartbeat) var text = result.text || '' var data = null try { data = JSON.parse(text) } catch (err) { error('Response was NOT JSON. First 500 chars:', text.substring(0, 500)) $submitBtn.prop('disabled', false).text(originalText) alert('Upload failed: not JSON. HTTP ' + result.res.status + ' — see console.') return } log('UPLOAD JSON', data) if (data.success && data.file && moduleUrl) { var reportUrl = moduleUrl + '&menu=report&file=' + encodeURIComponent(data.file) log('Navigating to report page', reportUrl) window.location.href = reportUrl return } if (data.success && data.redirect) { log('Navigating to redirect', data.redirect) window.location.href = data.redirect return } error('Upload rejected', data) $submitBtn.prop('disabled', false).text(originalText) alert(data.message || 'Upload failed') }).catch(function (err) { clearInterval(heartbeat) error('UPLOAD network/fetch error', err, { elapsedMs: Date.now() - startedAt }) $submitBtn.prop('disabled', false).text(originalText) alert('Upload network error. See console.') }) return false }) $submitBtn.on('click', function () { log('Import button clicked') }) } // --- Progress / report page: AJAX batches --- if ($('#ajaxlink').length) { var url = $('#ajaxlink').val() var item_per_call = parseInt($('#csv_ajax_rows_by_call').val(), 10) || 5 var total_items = parseInt($('#csvrows').val(), 10) || 0 var csv_file_name = $('#csvfile').val() var dry_run = parseInt($('#dry_run').val(), 10) === 1 ? 1 : 0 var check_images = parseInt($('#check_images').val(), 10) === 1 ? 1 : 0 var total_pages = Math.ceil(total_items / item_per_call) || 1 log('progress page ready', { url: url, csv_file_name: csv_file_name, total_items: total_items, item_per_call: item_per_call, total_pages: total_pages, dry_run: dry_run, check_images: check_images }) $('#process-title').html(dry_run ? 'Validating...' : 'Processing...') requestPages(1, total_pages).done(function () { log('all batches finished OK') }).fail(function () { error('batch chain stopped with failure — see previous console errors') }) } function requestPages (startPage, endPage) { function currentIssueFilter () { return $('#issues-filter').attr('data-filter') || 'all' } function applyIssueFilter () { var filter = currentIssueFilter() var $rows = $('#issues-table tbody tr') var visible = 0 $rows.each(function () { var sev = $(this).attr('data-severity') || 'error' var show = filter === 'all' || sev === filter $(this).toggle(show) if (show) { visible++ } }) var total = $rows.length if (total > 0) { $('#issues-filter-count').text('— showing ' + visible + ' / ' + total) } else { $('#issues-filter-count').text('') } } $('#issues-filter').on('click', 'button[data-filter]', function () { var filter = $(this).attr('data-filter') || 'all' $('#issues-filter').attr('data-filter', filter) $('#issues-filter button').removeClass('active') $(this).addClass('active') applyIssueFilter() }) function appendIssues (issues) { if (!issues || !issues.length) { return } var $tbody = $('#issues-table tbody') var $hint = $('#issues-empty-hint') if ($hint.length) { $hint.hide() } issues.forEach(function (issue) { var severity = (issue.severity || 'error').toLowerCase() if (severity !== 'warning') { severity = 'error' } var labelClass = severity === 'warning' ? 'warning' : 'danger' var rowHtml = '
Filter by