diff --git a/public/userarea/clone_parts_to_visible.php b/public/userarea/clone_parts_to_visible.php
index 23a4f3a..a2a9222 100644
--- a/public/userarea/clone_parts_to_visible.php
+++ b/public/userarea/clone_parts_to_visible.php
@@ -14,6 +14,7 @@ $targetList = $data['target_iddatadb_list'] ?? [];
// (comportamento di default richiesto, coerente con la checkbox pre-spuntata)
$cloneNotes = array_key_exists('clone_notes', $data) ? !empty($data['clone_notes']) : true;
$cloneAnalyses = !empty($data['clone_analyses']);
+$overwrite = !empty($data['overwrite']);
$targetIds = array_values(array_unique(array_filter(array_map('intval', (array)$targetList), function ($v) use ($sourceIddatadb) {
return $v > 0 && $v !== $sourceIddatadb;
@@ -93,6 +94,28 @@ try {
$details = [];
$totalClonedParts = 0;
$totalClonedAnalyses = 0;
+ $totalDeletedParts = 0;
+
+ // 2b. Se overwrite: elimina le parti esistenti dei target (e i loro figli)
+ if ($overwrite) {
+ $stmtSelectExisting = $pdo->prepare("SELECT id FROM identification_parts WHERE iddatadb = ?");
+ $stmtDeleteCFByPart = $pdo->prepare("DELETE FROM identification_parts_customfields WHERE part_id = ?");
+ $stmtDeleteAnByPart = $pdo->prepare("DELETE FROM identification_parts_analyses WHERE part_id = ?");
+ $stmtDeletePart = $pdo->prepare("DELETE FROM identification_parts WHERE id = ?");
+
+ foreach ($targetIds as $targetIddatadb) {
+ $stmtSelectExisting->execute([$targetIddatadb]);
+ $existingIds = $stmtSelectExisting->fetchAll(PDO::FETCH_COLUMN);
+
+ foreach ($existingIds as $existingPartId) {
+ $existingPartId = (int)$existingPartId;
+ $stmtDeleteCFByPart->execute([$existingPartId]);
+ $stmtDeleteAnByPart->execute([$existingPartId]);
+ $stmtDeletePart->execute([$existingPartId]);
+ $totalDeletedParts++;
+ }
+ }
+ }
// 3. Clone source parts to each target record
foreach ($targetIds as $targetIddatadb) {
diff --git a/public/userarea/exportLims_gridData.js b/public/userarea/exportLims_gridData.js
index 3c1730a..44bb57a 100644
--- a/public/userarea/exportLims_gridData.js
+++ b/public/userarea/exportLims_gridData.js
@@ -5,7 +5,7 @@
* Single export + batch export (Export All) with validation.
*/
(function () {
- 'use strict';
+ "use strict";
let pendingConfirmHandler = null;
let batchRunning = false;
@@ -17,7 +17,7 @@
// ── Helpers ──────────────────────────────────────────────────────────
function cleanupBackdrop() {
- document.querySelectorAll(".modal-backdrop").forEach(b => b.remove());
+ document.querySelectorAll(".modal-backdrop").forEach((b) => b.remove());
document.body.classList.remove("modal-open");
document.body.style.paddingRight = "";
const overlay = document.querySelector(".overlay.toggle-icon");
@@ -29,7 +29,9 @@
}
function getRowIndexByIddatadb(iddatadb) {
- return (window.gridData || []).findIndex(r => String(r.iddatadb) === String(iddatadb));
+ return (window.gridData || []).findIndex(
+ (r) => String(r.iddatadb) === String(iddatadb),
+ );
}
// ── Validation ──────────────────────────────────────────────────────
@@ -40,21 +42,31 @@
headers: { "Content-Type": "application/json" },
body: JSON.stringify({ rows: rowsToValidate }),
});
- if (!response.ok) throw new Error(`Validation HTTP error: ${response.status}`);
+ if (!response.ok)
+ throw new Error(`Validation HTTP error: ${response.status}`);
return response.json();
}
function clearValidationErrors() {
// Clear from gridData
- (window.gridData || []).forEach(row => { delete row._validationErrors; delete row._exportError; });
-
- document.querySelectorAll(".grid-cell.validation-error").forEach(cell => {
- cell.classList.remove("validation-error");
- cell.querySelectorAll(".input-validation-error").forEach(el => el.classList.remove("input-validation-error"));
- const tooltip = cell.querySelector(".validation-tooltip");
- if (tooltip) tooltip.remove();
+ (window.gridData || []).forEach((row) => {
+ delete row._validationErrors;
+ delete row._exportError;
});
- document.querySelectorAll(".grid-row.validation-row-error").forEach(row => row.classList.remove("validation-row-error"));
+
+ document
+ .querySelectorAll(".grid-cell.validation-error")
+ .forEach((cell) => {
+ cell.classList.remove("validation-error");
+ cell.querySelectorAll(".input-validation-error").forEach((el) =>
+ el.classList.remove("input-validation-error"),
+ );
+ const tooltip = cell.querySelector(".validation-tooltip");
+ if (tooltip) tooltip.remove();
+ });
+ document
+ .querySelectorAll(".grid-row.validation-row-error")
+ .forEach((row) => row.classList.remove("validation-row-error"));
clearAllRowErrors();
}
@@ -67,7 +79,7 @@
gridRow.classList.add("validation-row-error");
const messages = [];
- errors.forEach(err => {
+ errors.forEach((err) => {
messages.push(err.message);
if (!err.field) return;
@@ -76,19 +88,26 @@
const label = err.field.substring("field_label:".length);
const headers = document.querySelectorAll(".grid-header");
let targetIndex = null;
- headers.forEach(h => {
- if (h.textContent.trim() === label) targetIndex = h.getAttribute("data-index");
+ headers.forEach((h) => {
+ if (h.textContent.trim() === label)
+ targetIndex = h.getAttribute("data-index");
});
if (targetIndex) {
- cell = gridRow.querySelector(`.grid-cell[data-index="${targetIndex}"]`);
+ cell = gridRow.querySelector(
+ `.grid-cell[data-index="${targetIndex}"]`,
+ );
}
} else {
- cell = gridRow.querySelector(`.grid-cell[data-col="${err.field}"]`);
+ cell = gridRow.querySelector(
+ `.grid-cell[data-col="${err.field}"]`,
+ );
}
if (cell) {
cell.classList.add("validation-error");
- cell.querySelectorAll("input, select").forEach(el => el.classList.add("input-validation-error"));
+ cell.querySelectorAll("input, select").forEach((el) =>
+ el.classList.add("input-validation-error"),
+ );
let tooltip = cell.querySelector(".validation-tooltip");
if (!tooltip) {
tooltip = document.createElement("div");
@@ -109,34 +128,43 @@
formData.append("iddatadb", iddatadb);
if (batchUuid) formData.append("batch_uuid", batchUuid);
- const response = await fetch("export_to_lims.php", { method: "POST", body: formData });
- if (!response.ok) throw new Error(`HTTP error! status: ${response.status}`);
+ const response = await fetch("export_to_lims.php", {
+ method: "POST",
+ body: formData,
+ });
+ if (!response.ok)
+ throw new Error(`HTTP error! status: ${response.status}`);
const data = await response.json();
if (data.success) {
// Update gridData
const idx = getRowIndexByIddatadb(iddatadb);
if (idx >= 0) {
- window.gridData[idx].status = 'l';
+ window.gridData[idx].status = "l";
window.gridData[idx].commessaweb = data.commessaweb;
}
// Update visible DOM row
const gridRow = getGridRow(iddatadb);
if (gridRow) {
- const statusBadge = gridRow.querySelector('.grid-cell[data-col="status"] .status-badge');
+ const statusBadge = gridRow.querySelector(
+ '.grid-cell[data-col="status"] .status-badge',
+ );
if (statusBadge) {
statusBadge.classList.remove("status-i", "status-P");
statusBadge.classList.add("status-l");
statusBadge.textContent = "To LIMS";
}
- const statusCell = gridRow.querySelector('.grid-cell[data-col="status"]');
+ const statusCell = gridRow.querySelector(
+ '.grid-cell[data-col="status"]',
+ );
if (statusCell && data.commessaweb) {
let cwSpan = statusCell.querySelector(".commessaweb-code");
if (!cwSpan) {
cwSpan = document.createElement("span");
cwSpan.className = "commessaweb-code";
- cwSpan.style.cssText = "display:block; font-size:0.75em; color:#555; margin-top:2px;";
+ cwSpan.style.cssText =
+ "display:block; font-size:0.75em; color:#555; margin-top:2px;";
statusCell.appendChild(cwSpan);
}
cwSpan.textContent = data.commessaweb;
@@ -164,7 +192,8 @@
const label = document.getElementById("exportResponseModalLabel");
if (data.success) {
- msg.innerHTML = `${data.message.replace(/\n/g, "
")}` +
+ msg.innerHTML =
+ `${data.message.replace(/\n/g, "
")}` +
`
ID CommessaWeb: ${data.idcommessaweb}` +
`
Codice CommessaWeb: ${data.commessaweb}` +
(data.totalPhotos > 0 ? `
Foto: ${data.totalPhotos}` : "");
@@ -186,10 +215,14 @@
row.classList.remove("batch-disabled");
row.classList.add("batch-exporting");
if (btnCell) {
- btnCell.querySelectorAll(".action-btn").forEach(b => { b.dataset.prevDisplay = b.style.display; b.style.display = "none"; });
+ btnCell.querySelectorAll(".action-btn").forEach((b) => {
+ b.dataset.prevDisplay = b.style.display;
+ b.style.display = "none";
+ });
const spinner = document.createElement("span");
spinner.className = "batch-row-spinner";
- spinner.innerHTML = ' Exporting...';
+ spinner.innerHTML =
+ ' Exporting...';
btnCell.appendChild(spinner);
}
} else {
@@ -197,7 +230,10 @@
if (btnCell) {
const spinner = btnCell.querySelector(".batch-row-spinner");
if (spinner) spinner.remove();
- btnCell.querySelectorAll(".action-btn").forEach(b => { b.style.display = b.dataset.prevDisplay || ""; delete b.dataset.prevDisplay; });
+ btnCell.querySelectorAll(".action-btn").forEach((b) => {
+ b.style.display = b.dataset.prevDisplay || "";
+ delete b.dataset.prevDisplay;
+ });
}
}
}
@@ -213,32 +249,56 @@
errorEl.className = "batch-error-msg";
errorEl.textContent = "Warning — click for details";
errorEl.addEventListener("click", () => {
- document.getElementById("exportResponseMessage").innerHTML = message.replace(/\n/g, "
");
- document.getElementById("exportResponseModalLabel").textContent = "Error (id: " + iddatadb + ")";
- new bootstrap.Modal(document.getElementById("exportResponseModal"), { keyboard: false }).show();
+ document.getElementById("exportResponseMessage").innerHTML =
+ message.replace(/\n/g, "
");
+ document.getElementById(
+ "exportResponseModalLabel",
+ ).textContent = "Error (id: " + iddatadb + ")";
+ new bootstrap.Modal(
+ document.getElementById("exportResponseModal"),
+ { keyboard: false },
+ ).show();
});
btnCell.appendChild(errorEl);
}
}
function clearAllRowErrors() {
- document.querySelectorAll(".grid-row.batch-row-error").forEach(row => {
- row.classList.remove("batch-row-error");
- const msg = row.querySelector(".batch-error-msg");
- if (msg) msg.remove();
- });
+ document
+ .querySelectorAll(".grid-row.batch-row-error")
+ .forEach((row) => {
+ row.classList.remove("batch-row-error");
+ const msg = row.querySelector(".batch-error-msg");
+ if (msg) msg.remove();
+ });
}
function disableAllRowButtons() {
- document.querySelectorAll(".grid-row[data-id]").forEach(row => row.classList.add("batch-disabled"));
- const toggle = document.querySelector(".actions-dropdown .dropdown-toggle");
- if (toggle) { toggle.disabled = true; toggle.style.opacity = "0.5"; toggle.style.pointerEvents = "none"; }
+ document
+ .querySelectorAll(".grid-row[data-id]")
+ .forEach((row) => row.classList.add("batch-disabled"));
+ const toggle = document.querySelector(
+ ".actions-dropdown .dropdown-toggle",
+ );
+ if (toggle) {
+ toggle.disabled = true;
+ toggle.style.opacity = "0.5";
+ toggle.style.pointerEvents = "none";
+ }
}
function enableAllRowButtons() {
- document.querySelectorAll(".grid-row[data-id]").forEach(row => row.classList.remove("batch-disabled"));
- const toggle = document.querySelector(".actions-dropdown .dropdown-toggle");
- if (toggle) { toggle.disabled = false; toggle.style.opacity = ""; toggle.style.pointerEvents = ""; }
+ document
+ .querySelectorAll(".grid-row[data-id]")
+ .forEach((row) => row.classList.remove("batch-disabled"));
+ const toggle = document.querySelector(
+ ".actions-dropdown .dropdown-toggle",
+ );
+ if (toggle) {
+ toggle.disabled = false;
+ toggle.style.opacity = "";
+ toggle.style.pointerEvents = "";
+ }
}
// ── Single row export: validate → confirm → send ────────────────────
@@ -250,40 +310,61 @@
if (gridRow) {
setRowExporting(gridRow, true);
const spinner = gridRow.querySelector(".batch-row-spinner");
- if (spinner) spinner.innerHTML = ' Validating...';
+ if (spinner)
+ spinner.innerHTML =
+ ' Validating...';
}
validateRows([{ iddatadb: parseInt(iddatadb), index: rowIndex }])
- .then(validationData => {
- if (gridRow) { setRowExporting(gridRow, false); gridRow.classList.remove("batch-disabled"); }
+ .then((validationData) => {
+ if (gridRow) {
+ setRowExporting(gridRow, false);
+ gridRow.classList.remove("batch-disabled");
+ }
if (!validationData.success) {
- showExportResult({ success: false, message: validationData.message || "Validation error" });
+ showExportResult({
+ success: false,
+ message: validationData.message || "Validation error",
+ });
return;
}
const result = validationData.results[rowIndex];
if (result && !result.valid) {
- if (gridRow) showValidationErrors(gridRow, iddatadb, result.errors);
+ if (gridRow)
+ showValidationErrors(gridRow, iddatadb, result.errors);
return;
}
showConfirmAndExport(iddatadb, rowIndex);
})
- .catch(error => {
- if (gridRow) { setRowExporting(gridRow, false); gridRow.classList.remove("batch-disabled"); }
- showExportResult({ success: false, message: "Validation error: " + error.message });
+ .catch((error) => {
+ if (gridRow) {
+ setRowExporting(gridRow, false);
+ gridRow.classList.remove("batch-disabled");
+ }
+ showExportResult({
+ success: false,
+ message: "Validation error: " + error.message,
+ });
});
}
function showConfirmAndExport(iddatadb, rowIndex) {
- const confirmModalElement = document.getElementById("exportConfirmModal");
+ const confirmModalElement =
+ document.getElementById("exportConfirmModal");
if (!confirmModalElement) return;
- const confirmModal = new bootstrap.Modal(confirmModalElement, { keyboard: false });
+ const confirmModal = new bootstrap.Modal(confirmModalElement, {
+ keyboard: false,
+ });
document.getElementById("exportIddatadb").textContent = iddatadb;
confirmModal.show();
const confirmBtn = document.getElementById("exportConfirmBtn");
- if (!confirmBtn) { confirmModal.hide(); return; }
+ if (!confirmBtn) {
+ confirmModal.hide();
+ return;
+ }
const confirmHandler = async () => {
pendingConfirmHandler = null;
@@ -294,24 +375,36 @@
try {
const data = await sendExport(iddatadb);
- if (gridRow) { setRowExporting(gridRow, false); gridRow.classList.remove("batch-disabled"); }
- if (!data.success) showRowError(gridRow, iddatadb, data.message || "Unknown error");
+ if (gridRow) {
+ setRowExporting(gridRow, false);
+ gridRow.classList.remove("batch-disabled");
+ }
+ if (!data.success)
+ showRowError(
+ gridRow,
+ iddatadb,
+ data.message || "Unknown error",
+ );
showExportResult(data);
} catch (error) {
- if (gridRow) { setRowExporting(gridRow, false); gridRow.classList.remove("batch-disabled"); }
+ if (gridRow) {
+ setRowExporting(gridRow, false);
+ gridRow.classList.remove("batch-disabled");
+ }
showRowError(gridRow, iddatadb, error.message);
showExportResult({ success: false, message: error.message });
}
};
- if (pendingConfirmHandler) confirmBtn.removeEventListener("click", pendingConfirmHandler);
+ if (pendingConfirmHandler)
+ confirmBtn.removeEventListener("click", pendingConfirmHandler);
pendingConfirmHandler = confirmHandler;
confirmBtn.addEventListener("click", confirmHandler, { once: true });
}
// ── Single row click (event delegation) ─────────────────────────────
- $(document).on('click', '.export-lims-btn', function (e) {
+ $(document).on("click", ".export-lims-btn", function (e) {
e.preventDefault();
if (batchRunning) return;
@@ -322,24 +415,34 @@
// Check unsaved changes for this row
const dataRow = window.gridData?.[rowIndex];
if (dataRow && dataRow._dirty) {
- const unsavedModal = new bootstrap.Modal(document.getElementById("exportUnsavedModal"), { keyboard: false });
+ const unsavedModal = new bootstrap.Modal(
+ document.getElementById("exportUnsavedModal"),
+ { keyboard: false },
+ );
unsavedModal.show();
- document.getElementById("saveAndExportBtn")?.addEventListener("click", () => {
- unsavedModal.hide();
- // Save first, then export
- const formData = window.buildSavePayload(rowIndex);
- fetch('save_edited_row.php', { method: 'POST', body: formData })
- .then(r => r.json())
- .then(result => {
- if (result.success) {
- dataRow._dirty = false;
- startExportConfirmFlow(iddatadb, rowIndex);
- } else {
- alert('Save failed: ' + result.message);
- }
- });
- }, { once: true });
+ document.getElementById("saveAndExportBtn")?.addEventListener(
+ "click",
+ () => {
+ unsavedModal.hide();
+ // Save first, then export
+ const formData = window.buildSavePayload(rowIndex);
+ fetch("save_edited_row.php", {
+ method: "POST",
+ body: formData,
+ })
+ .then((r) => r.json())
+ .then((result) => {
+ if (result.success) {
+ dataRow._dirty = false;
+ startExportConfirmFlow(iddatadb, rowIndex);
+ } else {
+ alert("Save failed: " + result.message);
+ }
+ });
+ },
+ { once: true },
+ );
return;
}
@@ -349,18 +452,33 @@
// ── Batch export (Export All) ───────────────────────────────────────
function collectEligibleRows() {
- // Read from gridData, not DOM
+ // Read from gridData, not DOM. Se i filtri sono attivi, limita al target set.
+ const target =
+ typeof window.getTargetGridIds === "function"
+ ? window.getTargetGridIds()
+ : null;
const eligible = [];
(window.gridData || []).forEach((row, index) => {
- if (row.status !== 'l') {
- eligible.push({ iddatadb: row.iddatadb, index, row: getGridRow(row.iddatadb) });
- }
+ if (row.status === "l") return;
+ if (target && !target.has(parseInt(row.iddatadb, 10))) return;
+ eligible.push({
+ iddatadb: row.iddatadb,
+ index,
+ row: getGridRow(row.iddatadb),
+ });
});
return eligible;
}
function hasUnsavedChanges() {
- return (window.gridData || []).some(r => r._dirty);
+ const target =
+ typeof window.getTargetGridIds === "function"
+ ? window.getTargetGridIds()
+ : null;
+ return (window.gridData || []).some(
+ (r) =>
+ r._dirty && (!target || target.has(parseInt(r.iddatadb, 10))),
+ );
}
async function validateAndFilter(eligibleRows) {
@@ -369,7 +487,8 @@
index,
}));
const validationData = await validateRows(rowsToValidate);
- if (!validationData.success) throw new Error(validationData.message || "Validation error");
+ if (!validationData.success)
+ throw new Error(validationData.message || "Validation error");
const validRows = [];
let invalidCount = 0;
@@ -377,7 +496,12 @@
for (const item of eligibleRows) {
const result = validationData.results[item.index];
if (result && !result.valid) {
- if (item.row) showValidationErrors(item.row, item.iddatadb, result.errors);
+ if (item.row)
+ showValidationErrors(
+ item.row,
+ item.iddatadb,
+ result.errors,
+ );
invalidCount++;
} else {
validRows.push(item);
@@ -410,54 +534,92 @@
if (validRows.length === 0) {
document.getElementById("exportResponseMessage").innerHTML =
`No valid rows for export.
${invalidCount} rows with validation errors.`;
- document.getElementById("exportResponseModalLabel").textContent = "Validation Failed";
- new bootstrap.Modal(document.getElementById("exportResponseModal"), { keyboard: false }).show();
+ document.getElementById(
+ "exportResponseModalLabel",
+ ).textContent = "Validation Failed";
+ new bootstrap.Modal(
+ document.getElementById("exportResponseModal"),
+ { keyboard: false },
+ ).show();
return;
}
- const confirmModal = new bootstrap.Modal(document.getElementById("exportBatchConfirmModal"), { keyboard: false });
+ const confirmModal = new bootstrap.Modal(
+ document.getElementById("exportBatchConfirmModal"),
+ { keyboard: false },
+ );
let countText = String(validRows.length);
- if (invalidCount > 0) countText += ` (${invalidCount} excluded due to errors)`;
- document.getElementById("exportBatchCount").textContent = countText;
+ if (invalidCount > 0)
+ countText += ` (${invalidCount} excluded due to errors)`;
+ document.getElementById("exportBatchCount").textContent =
+ countText;
confirmModal.show();
- const confirmBtn = document.getElementById("exportBatchConfirmBtn");
- if (pendingBatchConfirmHandler) confirmBtn.removeEventListener("click", pendingBatchConfirmHandler);
+ const confirmBtn = document.getElementById(
+ "exportBatchConfirmBtn",
+ );
+ if (pendingBatchConfirmHandler)
+ confirmBtn.removeEventListener(
+ "click",
+ pendingBatchConfirmHandler,
+ );
pendingBatchConfirmHandler = () => {
pendingBatchConfirmHandler = null;
confirmModal.hide();
startBatchExport(validRows);
};
- confirmBtn.addEventListener("click", pendingBatchConfirmHandler, { once: true });
+ confirmBtn.addEventListener(
+ "click",
+ pendingBatchConfirmHandler,
+ { once: true },
+ );
})
- .catch(error => {
+ .catch((error) => {
showValidationSpinner(false);
- document.getElementById("exportResponseMessage").textContent = "Validation error: " + error.message;
- document.getElementById("exportResponseModalLabel").textContent = "Validation Error";
- new bootstrap.Modal(document.getElementById("exportResponseModal"), { keyboard: false }).show();
+ document.getElementById("exportResponseMessage").textContent =
+ "Validation error: " + error.message;
+ document.getElementById(
+ "exportResponseModalLabel",
+ ).textContent = "Validation Error";
+ new bootstrap.Modal(
+ document.getElementById("exportResponseModal"),
+ { keyboard: false },
+ ).show();
});
}
- $(document).on('click', '.export-all-lims-btn', function (e) {
+ $(document).on("click", ".export-all-lims-btn", function (e) {
e.preventDefault();
if (batchRunning) return;
if (hasUnsavedChanges()) {
- const unsavedModal = new bootstrap.Modal(document.getElementById("exportBatchUnsavedModal"), { keyboard: false });
+ const unsavedModal = new bootstrap.Modal(
+ document.getElementById("exportBatchUnsavedModal"),
+ { keyboard: false },
+ );
unsavedModal.show();
- document.getElementById("batchSaveAndExportBtn")?.addEventListener("click", () => {
- unsavedModal.hide();
- // Trigger save all first — listen for completion
- alert("Please Save All first, then Export All.");
- }, { once: true });
+ document.getElementById("batchSaveAndExportBtn")?.addEventListener(
+ "click",
+ () => {
+ unsavedModal.hide();
+ // Trigger save all first — listen for completion
+ alert("Please Save All first, then Export All.");
+ },
+ { once: true },
+ );
return;
}
const eligibleRows = collectEligibleRows();
if (eligibleRows.length === 0) {
- document.getElementById("exportResponseMessage").textContent = "All rows already exported to LIMS.";
- document.getElementById("exportResponseModalLabel").textContent = "Export All";
- new bootstrap.Modal(document.getElementById("exportResponseModal"), { keyboard: false }).show();
+ document.getElementById("exportResponseMessage").textContent =
+ "All rows already exported to LIMS.";
+ document.getElementById("exportResponseModalLabel").textContent =
+ "Export All";
+ new bootstrap.Modal(
+ document.getElementById("exportResponseModal"),
+ { keyboard: false },
+ ).show();
return;
}
showBatchConfirm(eligibleRows);
@@ -468,7 +630,9 @@
batchRunning = true;
const batchUuid = crypto.randomUUID();
const total = eligibleRows.length;
- let processed = 0, succeeded = 0, failed = 0;
+ let processed = 0,
+ succeeded = 0,
+ failed = 0;
disableAllRowButtons();
@@ -479,18 +643,25 @@
if (cancelBtn) cancelBtn.disabled = false;
if (statusEl) statusEl.textContent = `Exporting 0 / ${total}...`;
- cancelBtn?.addEventListener("click", () => {
- batchCancelled = true;
- if (statusEl) statusEl.textContent = "Cancelling... (waiting for current row)";
- if (cancelBtn) cancelBtn.disabled = true;
- }, { once: true });
+ cancelBtn?.addEventListener(
+ "click",
+ () => {
+ batchCancelled = true;
+ if (statusEl)
+ statusEl.textContent =
+ "Cancelling... (waiting for current row)";
+ if (cancelBtn) cancelBtn.disabled = true;
+ },
+ { once: true },
+ );
(async () => {
for (let i = 0; i < eligibleRows.length; i++) {
if (batchCancelled) break;
const { iddatadb, row } = eligibleRows[i];
- if (statusEl) statusEl.textContent = `Exporting ${processed + 1} / ${total} (id: ${iddatadb})...`;
+ if (statusEl)
+ statusEl.textContent = `Exporting ${processed + 1} / ${total} (id: ${iddatadb})...`;
const gridRow = row || getGridRow(iddatadb);
if (gridRow) setRowExporting(gridRow, true);
@@ -503,18 +674,29 @@
} else {
failed++;
const errIdx = getRowIndexByIddatadb(iddatadb);
- if (errIdx >= 0) window.gridData[errIdx]._exportError = data.message || "Unknown error";
- if (gridRow) showRowError(gridRow, iddatadb, data.message || "Unknown error");
+ if (errIdx >= 0)
+ window.gridData[errIdx]._exportError =
+ data.message || "Unknown error";
+ if (gridRow)
+ showRowError(
+ gridRow,
+ iddatadb,
+ data.message || "Unknown error",
+ );
}
} catch (error) {
processed++;
failed++;
const errIdx = getRowIndexByIddatadb(iddatadb);
- if (errIdx >= 0) window.gridData[errIdx]._exportError = error.message;
+ if (errIdx >= 0)
+ window.gridData[errIdx]._exportError = error.message;
if (gridRow) showRowError(gridRow, iddatadb, error.message);
}
- if (gridRow) { setRowExporting(gridRow, false); gridRow.classList.remove("batch-disabled"); }
+ if (gridRow) {
+ setRowExporting(gridRow, false);
+ gridRow.classList.remove("batch-disabled");
+ }
}
batchRunning = false;
@@ -529,7 +711,8 @@
(window.gridData || []).forEach((row, idx) => {
if (row._exportError) {
const gridRow = getGridRow(row.iddatadb);
- if (gridRow) showRowError(gridRow, row.iddatadb, row._exportError);
+ if (gridRow)
+ showRowError(gridRow, row.iddatadb, row._exportError);
}
});
@@ -549,7 +732,9 @@
const modalEl = document.getElementById("exportResponseModal");
new bootstrap.Modal(modalEl, { keyboard: false }).show();
- modalEl.addEventListener("hidden.bs.modal", cleanupBackdrop, { once: true });
+ modalEl.addEventListener("hidden.bs.modal", cleanupBackdrop, {
+ once: true,
+ });
})();
}
})();
diff --git a/public/userarea/modal_partsTable.php b/public/userarea/modal_partsTable.php
index 75d945c..0157a2c 100644
--- a/public/userarea/modal_partsTable.php
+++ b/public/userarea/modal_partsTable.php
@@ -214,6 +214,12 @@
Duplica anche le analisi collegate
+