614 lines
28 KiB
PHP
614 lines
28 KiB
PHP
<?php include('include/headscript.php');
|
|
|
|
if (!isset($_GET['id']) || !is_numeric($_GET['id'])) {
|
|
die("Invalid template ID");
|
|
}
|
|
|
|
$id = intval($_GET['id']);
|
|
$db = DBHandlerSelect::getInstance();
|
|
$pdo = $db->getConnection();
|
|
$stmt = $pdo->prepare("SELECT name, header_row, start_column, target_table, sample_xlsx, idclient, clientname, idschema, schemaname, schemajson FROM excel_templates WHERE id = ?");
|
|
$stmt->execute([$id]);
|
|
$template = $stmt->fetch(PDO::FETCH_ASSOC);
|
|
|
|
if (!$template) {
|
|
die("Template not found");
|
|
}
|
|
|
|
// Opzionale: se clientname o schemaname non sono disponibili, potresti volerli recuperare dinamicamente
|
|
$clientName = $template['clientname'] ?: '';
|
|
$schemaName = $template['schemaname'] ?: '';
|
|
$schemajson = $template['schemajson'] ?: ''; // Recupera il valore di schemajson
|
|
$isSchemajsonEmpty = empty(trim($template['schemajson']));
|
|
|
|
?>
|
|
<!doctype html>
|
|
<html lang="en">
|
|
|
|
<head>
|
|
<!-- Required meta tags -->
|
|
<meta charset="utf-8">
|
|
<meta name="viewport" content="width=device-width, initial-scale=1">
|
|
<!--favicon-->
|
|
<link rel="icon" href="assets/images/favicon-32x32.png" type="image/png" />
|
|
<?php include('cssinclude.php'); ?>
|
|
<title>Mapping XLS Template <?= htmlspecialchars($titlewebsite, ENT_QUOTES, 'UTF-8'); ?></title>
|
|
<script src="https://cdnjs.cloudflare.com/ajax/libs/xlsx/0.18.5/xlsx.full.min.js"></script>
|
|
|
|
</head>
|
|
|
|
<body>
|
|
<!--wrapper-->
|
|
<div class="wrapper">
|
|
<!--sidebar wrapper -->
|
|
<?php include('include/navbar.php'); ?>
|
|
<!--end sidebar wrapper -->
|
|
<!--start header -->
|
|
<?php include('include/topbar.php'); ?>
|
|
<!--end header -->
|
|
<!--start page wrapper -->
|
|
<div class="page-wrapper">
|
|
<div class="page-content">
|
|
|
|
<?php include('top_stat_widget.php'); ?>
|
|
|
|
|
|
<div class="card radius-10">
|
|
<div class="card-header">
|
|
<div class="d-flex align-items-center">
|
|
<div>
|
|
<h6 class="mb-0">Associate Columns - Template: <span id="templateName"><?php echo htmlspecialchars($template['name']); ?></span></h6>
|
|
<p>
|
|
Client: <span id="clientName"><?php echo htmlspecialchars($clientName); ?></span> |
|
|
Schema: <span id="schemaName"><?php echo htmlspecialchars($schemaName); ?></span> |
|
|
Header Row: <span id="headerRow"><?php echo $template['header_row']; ?></span> |
|
|
Start Column: <span id="startColumn"><?php echo htmlspecialchars($template['start_column']); ?></span>
|
|
</p>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
<div class="card-body">
|
|
<!-- Upload Section -->
|
|
<div class="mb-4">
|
|
<label class="form-label">Upload XLS Example:</label>
|
|
<input type="file" id="xlsUpload" class="form-control">
|
|
<small id="uploadStatus" class="text-muted">
|
|
<?php if (!empty($template['sample_xlsx'])): ?>
|
|
✅ Current file: <a href="xlstemplates/<?php echo htmlspecialchars($template['sample_xlsx']); ?>" target="_blank">
|
|
<?php echo htmlspecialchars($template['sample_xlsx']); ?>
|
|
</a>
|
|
<?php else: ?>
|
|
No file uploaded yet.
|
|
<?php endif; ?>
|
|
</small>
|
|
</div>
|
|
|
|
<!-- Association Section -->
|
|
<div class="row">
|
|
<div class="col-md-5">
|
|
<h5>XLS Column</h5>
|
|
<ul id="xlsColumns" class="list-group border p-3" style="height: 300px; overflow-y: auto;"></ul>
|
|
</div>
|
|
<div class="col-md-2 text-center d-flex align-items-center justify-content-center">
|
|
<button class="btn btn-dark" id="addAssociation">➝ Add</button>
|
|
</div>
|
|
<div class="col-md-5">
|
|
<div class="d-flex align-items-center mb-2">
|
|
<h5>Schema Fields</h5>
|
|
<button id="loadSchemaButton" class="btn btn-primary ms-2" data-empty="<?php echo $isSchemajsonEmpty ? 'true' : 'false'; ?>">
|
|
<?php echo $isSchemajsonEmpty ? 'Load Schema Details' : 'Update Schema Details'; ?>
|
|
</button>
|
|
</div>
|
|
<table id="schemaFieldsTable" class="table table-striped">
|
|
<thead>
|
|
<tr>
|
|
<th>Title</th>
|
|
<th>ID</th>
|
|
<th>Type</th>
|
|
</tr>
|
|
</thead>
|
|
<tbody id="schemaFieldsBody">
|
|
<!-- I dettagli dello schema verranno caricati qui -->
|
|
</tbody>
|
|
</table>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- Associations List -->
|
|
<div class="mt-4">
|
|
<h5>Current Associations</h5>
|
|
<ul id="associationsList" class="list-group border p-3"></ul>
|
|
</div>
|
|
|
|
<!-- Save Button -->
|
|
<div class="mt-4 text-end">
|
|
<a href="templates_dashboard.php" class="btn btn-primary">⬅ Back to Template Dashboard</a>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
</div>
|
|
</div>
|
|
<!--end page wrapper -->
|
|
<!--start overlay-->
|
|
<div class="overlay toggle-icon"></div>
|
|
<!--end overlay-->
|
|
<!--Start Back To Top Button-->
|
|
<a href="javaScript:;" class="back-to-top"><i class='bx bxs-up-arrow-alt'></i></a>
|
|
<!--End Back To Top Button-->
|
|
<?php include('include/footer.php'); ?>
|
|
</div>
|
|
<!--end wrapper-->
|
|
|
|
|
|
<!-- search modal -->
|
|
<?php //include('include/searchmodal.php');
|
|
?>
|
|
<!-- end search modal -->
|
|
|
|
|
|
<!--start switcher-->
|
|
<?php //include('include/themeswitcher.php');
|
|
?>
|
|
<!--end switcher-->
|
|
<?php include('jsinclude.php'); ?>
|
|
<script>
|
|
document.getElementById('xlsUpload').addEventListener('change', function(event) {
|
|
let file = event.target.files[0];
|
|
if (!file) {
|
|
console.error("❌ No file selected");
|
|
return;
|
|
}
|
|
|
|
console.log("📂 File selected:", file.name);
|
|
|
|
let formData = new FormData();
|
|
formData.append("xls_file", file);
|
|
formData.append("template_id", <?php echo $id; ?>);
|
|
|
|
let statusText = document.getElementById('uploadStatus');
|
|
statusText.innerText = "Uploading...";
|
|
|
|
fetch('upload_xls_example.php', {
|
|
method: 'POST',
|
|
body: formData
|
|
})
|
|
.then(response => response.json())
|
|
.then(data => {
|
|
if (!data.success) {
|
|
console.error("❌ Error uploading file:", data.message);
|
|
statusText.innerText = "❌ Upload failed: " + data.message;
|
|
return;
|
|
}
|
|
|
|
console.log("✅ File uploaded successfully:", data.filepath);
|
|
statusText.innerHTML = `✅ File uploaded: <a href="xlstemplates/${data.filename}" target="_blank">${data.filename}</a>`;
|
|
|
|
processXLSX(file);
|
|
})
|
|
.catch(error => {
|
|
console.error("❌ Fetch error:", error);
|
|
statusText.innerText = "❌ Upload failed. Check console.";
|
|
});
|
|
});
|
|
|
|
function processXLSX(file) {
|
|
let reader = new FileReader();
|
|
reader.onload = function(e) {
|
|
let data = new Uint8Array(e.target.result);
|
|
let workbook = XLSX.read(data, {
|
|
type: 'array'
|
|
});
|
|
let sheet = workbook.Sheets[workbook.SheetNames[0]];
|
|
|
|
console.log("📄 Sheet found:", workbook.SheetNames[0]);
|
|
|
|
let rowIndex = parseInt(document.getElementById('headerRow').textContent) || 1;
|
|
let startColumn = parseInt(document.getElementById('startColumn').textContent) || 1;
|
|
|
|
console.log("📌 Using Header Row:", rowIndex, "Start Column:", startColumn);
|
|
|
|
let sheetData = XLSX.utils.sheet_to_json(sheet, {
|
|
header: 1,
|
|
defval: "",
|
|
raw: false,
|
|
range: 0
|
|
});
|
|
|
|
console.log("📊 Sheet Data:", sheetData);
|
|
|
|
if (!sheetData[rowIndex - 1]) {
|
|
console.warn("⚠️ No headers found in the specified row:", rowIndex);
|
|
document.getElementById('xlsColumns').innerHTML = "<li class='list-group-item text-danger'>No headers found</li>";
|
|
return;
|
|
}
|
|
|
|
let headers = sheetData[rowIndex - 1] || [];
|
|
|
|
console.log("🔎 Raw Headers:", headers);
|
|
|
|
if (!headers.length || headers.every(h => h.trim() === "")) {
|
|
console.warn("⚠️ Header row is empty at row:", rowIndex);
|
|
document.getElementById('xlsColumns').innerHTML = "<li class='list-group-item text-warning'>No headers found in the specified row</li>";
|
|
return;
|
|
}
|
|
|
|
let adjustedHeaders = headers.slice(startColumn - 1).filter(header => header !== undefined && header.trim() !== "");
|
|
|
|
console.log("✅ Extracted Headers:", adjustedHeaders);
|
|
|
|
let xlsColumns = document.getElementById('xlsColumns');
|
|
xlsColumns.innerHTML = '';
|
|
|
|
adjustedHeaders.forEach(header => {
|
|
let li = document.createElement('li');
|
|
li.className = 'list-group-item';
|
|
li.textContent = header;
|
|
xlsColumns.appendChild(li);
|
|
});
|
|
};
|
|
|
|
reader.readAsArrayBuffer(file);
|
|
}
|
|
|
|
document.addEventListener("DOMContentLoaded", function() {
|
|
let selectedXLSColumn = null;
|
|
let selectedSchemaField = null;
|
|
let templateId = <?php echo $id; ?>;
|
|
let schemaId = <?php echo json_encode($template['idschema'] ?? 0); ?>;
|
|
let clientId = <?php echo json_encode($template['idclient'] ?? 0); ?>;
|
|
let isSchemajsonEmpty = <?php echo json_encode($isSchemajsonEmpty); ?>;
|
|
|
|
async function loadClientAndSchemaNames() {
|
|
if (clientId && clientId > 0) {
|
|
try {
|
|
const response = await fetch(`get_clienti.php?id=${clientId}`, {
|
|
method: "GET",
|
|
headers: {
|
|
"Content-Type": "application/json"
|
|
}
|
|
});
|
|
const data = await response.json();
|
|
if (response.ok && data.value && data.value.length > 0) {
|
|
document.getElementById('clientName').textContent = data.value[0].Nominativo || 'N/A';
|
|
}
|
|
} catch (error) {
|
|
console.error("❌ Error loading client name:", error);
|
|
}
|
|
}
|
|
|
|
if (schemaId && schemaId > 0) {
|
|
try {
|
|
const response = await fetch(`get_schemi.php?id=${schemaId}`, {
|
|
method: "GET",
|
|
headers: {
|
|
"Content-Type": "application/json"
|
|
}
|
|
});
|
|
const data = await response.json();
|
|
if (response.ok && data.value && data.value.length > 0) {
|
|
document.getElementById('schemaName').textContent = data.value[0].Nome || 'N/A';
|
|
}
|
|
} catch (error) {
|
|
console.error("❌ Error loading schema name:", error);
|
|
}
|
|
}
|
|
}
|
|
|
|
loadClientAndSchemaNames();
|
|
|
|
async function loadOrUpdateSchemaDetails() {
|
|
if (!schemaId || schemaId === 0) {
|
|
console.warn("⚠️ No schema ID available for template:", templateId);
|
|
document.getElementById('schemaFieldsBody').innerHTML = '<tr><td colspan="3" class="text-warning">No schema associated with this template.</td></tr>';
|
|
return;
|
|
}
|
|
|
|
const loadSchemaButton = document.getElementById('loadSchemaButton');
|
|
loadSchemaButton.disabled = true;
|
|
loadSchemaButton.textContent = 'Loading...';
|
|
|
|
try {
|
|
// Chiamata a get_schema_details.php
|
|
const response = await fetch(`get_schema_details.php?id=${schemaId}`, {
|
|
method: "GET",
|
|
headers: {
|
|
"Content-Type": "application/json"
|
|
}
|
|
});
|
|
|
|
console.log("📡 HTTP Status (get_schema_details):", response.status);
|
|
if (!response.ok) {
|
|
throw new Error(`HTTP error! Status: ${response.status}`);
|
|
}
|
|
|
|
const rawResponse = await response.text();
|
|
console.log("📡 Raw Response (get_schema_details):", rawResponse);
|
|
|
|
let data;
|
|
try {
|
|
data = JSON.parse(rawResponse);
|
|
} catch (e) {
|
|
throw new Error('Invalid JSON response from get_schema_details: ' + e.message);
|
|
}
|
|
|
|
console.log("📡 Parsed Schema Details Response:", data);
|
|
|
|
if (!data || typeof data !== 'object') {
|
|
throw new Error('Invalid schema details response: Response is not an object');
|
|
}
|
|
|
|
if (!data.SchemiCustomFieldsDettagli) {
|
|
throw new Error('Invalid schema details response: Missing "SchemiCustomFieldsDettagli"');
|
|
}
|
|
|
|
const schemaJson = JSON.stringify(data);
|
|
|
|
// Salva il JSON
|
|
await saveSchemaJson(templateId, schemaJson);
|
|
|
|
// Rileggi i dati aggiornati
|
|
const updatedTemplateResponse = await fetch(`mapping_template_xls_scheme.php?id=${templateId}`, {
|
|
method: "GET",
|
|
headers: {
|
|
"Content-Type": "application/json"
|
|
}
|
|
});
|
|
|
|
console.log("📡 HTTP Status (updated_template):", updatedTemplateResponse.status);
|
|
const rawUpdatedResponse = await updatedTemplateResponse.text();
|
|
console.log("📡 Raw Response (updated_template):", rawUpdatedResponse);
|
|
|
|
let updatedTemplateData;
|
|
try {
|
|
updatedTemplateData = JSON.parse(rawUpdatedResponse);
|
|
} catch (e) {
|
|
throw new Error('Invalid JSON response from updated_template: ' + e.message);
|
|
}
|
|
|
|
const updatedSchemaJson = updatedTemplateData.schemajson;
|
|
const schemaDetails = JSON.parse(updatedSchemaJson);
|
|
|
|
if (schemaDetails && schemaDetails.SchemiCustomFieldsDettagli) {
|
|
const schemaFieldsBody = document.getElementById('schemaFieldsBody');
|
|
schemaFieldsBody.innerHTML = '';
|
|
|
|
schemaDetails.SchemiCustomFieldsDettagli.forEach(detail => {
|
|
const field = detail.CustomField;
|
|
const tr = document.createElement('tr');
|
|
tr.innerHTML = `
|
|
<td>${field.Titolo || 'N/A'}</td>
|
|
<td>${field.IdCustomField || 'N/A'}</td>
|
|
<td>${field.Tipo || 'N/A'}</td>
|
|
`;
|
|
tr.setAttribute('data-field', JSON.stringify({
|
|
id: field.IdCustomField,
|
|
title: field.Titolo,
|
|
type: field.Tipo
|
|
}));
|
|
tr.addEventListener('click', function() {
|
|
document.querySelectorAll('#schemaFieldsBody tr').forEach(el => el.classList.remove('table-active'));
|
|
tr.classList.add('table-active');
|
|
selectedSchemaField = JSON.parse(tr.getAttribute('data-field'));
|
|
console.log("📌 Selected Schema Field:", selectedSchemaField);
|
|
});
|
|
schemaFieldsBody.appendChild(tr);
|
|
});
|
|
} else {
|
|
throw new Error('No schema details available after update');
|
|
}
|
|
|
|
loadSchemaButton.textContent = 'Update Schema Details';
|
|
} catch (error) {
|
|
console.error("❌ Error details:", error);
|
|
document.getElementById('schemaFieldsBody').innerHTML = '<tr><td colspan="3" class="text-danger">Error: ' + error.message + '</td></tr>';
|
|
} finally {
|
|
loadSchemaButton.disabled = false; // Assicura che il pulsante torni attivo
|
|
loadSchemaButton.textContent = isSchemajsonEmpty ? 'Load Schema Details' : 'Update Schema Details';
|
|
}
|
|
}
|
|
|
|
async function saveSchemaJson(templateId, schemaJson) {
|
|
console.log("Saving Schema JSON - templateId:", templateId, "schemaJson:", schemaJson); // Debug
|
|
try {
|
|
const response = await fetch('update_schemajson.php', {
|
|
method: 'POST',
|
|
headers: {
|
|
'Content-Type': 'application/json'
|
|
},
|
|
body: JSON.stringify({
|
|
template_id: templateId,
|
|
schemajson: schemaJson
|
|
})
|
|
});
|
|
|
|
const data = await response.json();
|
|
console.log("Response from update_schemajson.php:", data); // Debug
|
|
if (!data.success) {
|
|
throw new Error(data.message || 'Failed to save schema JSON');
|
|
}
|
|
console.log("✅ Schema JSON saved:", data);
|
|
} catch (error) {
|
|
console.error("❌ Error saving schema JSON:", error);
|
|
throw error;
|
|
}
|
|
}
|
|
|
|
const loadSchemaButton = document.getElementById('loadSchemaButton');
|
|
if (isSchemajsonEmpty) {
|
|
loadSchemaButton.textContent = 'Load Schema Details';
|
|
} else {
|
|
const initialSchema = JSON.parse('<?php echo addslashes($schemajson); ?>');
|
|
if (initialSchema && initialSchema.SchemiCustomFieldsDettagli) {
|
|
const schemaFieldsBody = document.getElementById('schemaFieldsBody');
|
|
schemaFieldsBody.innerHTML = '';
|
|
|
|
initialSchema.SchemiCustomFieldsDettagli.forEach(detail => {
|
|
const field = detail.CustomField;
|
|
const tr = document.createElement('tr');
|
|
tr.innerHTML = `
|
|
<td>${field.Titolo || 'N/A'}</td>
|
|
<td>${field.IdCustomField || 'N/A'}</td>
|
|
<td>${field.Tipo || 'N/A'}</td>
|
|
`;
|
|
tr.setAttribute('data-field', JSON.stringify({
|
|
id: field.IdCustomField,
|
|
title: field.Titolo,
|
|
type: field.Tipo
|
|
}));
|
|
tr.addEventListener('click', function() {
|
|
document.querySelectorAll('#schemaFieldsBody tr').forEach(el => el.classList.remove('table-active'));
|
|
tr.classList.add('table-active');
|
|
selectedSchemaField = JSON.parse(tr.getAttribute('data-field'));
|
|
console.log("📌 Selected Schema Field:", selectedSchemaField);
|
|
});
|
|
schemaFieldsBody.appendChild(tr);
|
|
});
|
|
}
|
|
}
|
|
loadSchemaButton.addEventListener('click', loadOrUpdateSchemaDetails);
|
|
|
|
function loadMappings() {
|
|
fetch('load_existing_mappings.php?template_id=' + templateId)
|
|
.then(response => response.json())
|
|
.then(data => {
|
|
if (!data.success) {
|
|
console.error("❌ Error loading mappings:", data.message);
|
|
return;
|
|
}
|
|
|
|
let associationsList = document.getElementById('associationsList');
|
|
let xlsColumnsList = document.getElementById('xlsColumns');
|
|
|
|
|
|
data.mappings.forEach(mapping => {
|
|
let li = document.createElement('li');
|
|
li.className = 'list-group-item d-flex justify-content-between align-items-center';
|
|
li.innerHTML = `
|
|
${mapping.excel_column} ➝ ${mapping.schema_field_id || 'N/A'}
|
|
<button class="btn btn-danger btn-sm removeAssociation" data-excel="${mapping.excel_column}" data-mysql="${mapping.schema_field_id}">X</button>
|
|
`;
|
|
associationsList.appendChild(li);
|
|
});
|
|
|
|
if (Array.isArray(data.remaining_xls_columns)) {
|
|
data.remaining_xls_columns.forEach(header => {
|
|
let li = document.createElement('li');
|
|
li.className = 'list-group-item';
|
|
li.textContent = header;
|
|
xlsColumnsList.appendChild(li);
|
|
});
|
|
}
|
|
|
|
// ❌ RIMOSSA: non ricaricare i dati dello schema automaticamente!
|
|
// if (!isSchemajsonEmpty) {
|
|
// loadOrUpdateSchemaDetails();
|
|
// }
|
|
})
|
|
.catch(error => console.error("❌ Error fetching mappings:", error));
|
|
}
|
|
|
|
|
|
loadMappings();
|
|
|
|
document.getElementById('xlsColumns').addEventListener('click', function(event) {
|
|
if (event.target.tagName === 'LI') {
|
|
document.querySelectorAll('#xlsColumns li').forEach(el => el.classList.remove('active'));
|
|
event.target.classList.add('active');
|
|
selectedXLSColumn = event.target.textContent;
|
|
console.log("📌 Selected XLS Column:", selectedXLSColumn);
|
|
}
|
|
});
|
|
|
|
document.getElementById('schemaFieldsBody').addEventListener('click', function(event) {
|
|
if (event.target.tagName === 'TR') {
|
|
document.querySelectorAll('#schemaFieldsBody tr').forEach(el => el.classList.remove('table-active'));
|
|
event.target.classList.add('table-active');
|
|
selectedSchemaField = JSON.parse(event.target.getAttribute('data-field') || '{}');
|
|
console.log("📌 Selected Schema Field:", selectedSchemaField);
|
|
}
|
|
});
|
|
|
|
document.getElementById('addAssociation').addEventListener('click', function() {
|
|
if (!selectedXLSColumn || !selectedSchemaField) {
|
|
alert("Please select both an XLS column and a schema field.");
|
|
return;
|
|
}
|
|
|
|
saveAssociation(selectedXLSColumn, selectedSchemaField.id);
|
|
|
|
selectedXLSColumn = null;
|
|
selectedSchemaField = null;
|
|
});
|
|
|
|
function saveAssociation(excelColumn, schemaFieldId) {
|
|
let allHeaders = [...document.querySelectorAll('#xlsColumns li')].map(el => el.textContent).join(",");
|
|
|
|
fetch('save_column_mapping.php', {
|
|
method: 'POST',
|
|
headers: {
|
|
'Content-Type': 'application/json'
|
|
},
|
|
body: JSON.stringify({
|
|
template_id: templateId,
|
|
tablename: "<?php echo $template['target_table']; ?>",
|
|
excel_column: excelColumn,
|
|
schema_field_id: schemaFieldId,
|
|
data_type: "VARCHAR",
|
|
is_required: 0,
|
|
default_value: "",
|
|
headerexcel: allHeaders
|
|
})
|
|
})
|
|
.then(response => response.json())
|
|
.then(data => {
|
|
if (!data.success) {
|
|
console.error("❌ Error saving mapping:", data.message);
|
|
alert("Error saving mapping: " + data.message);
|
|
} else {
|
|
console.log("✅ Association saved:", data);
|
|
loadMappings();
|
|
}
|
|
})
|
|
.catch(error => console.error("❌ Fetch error:", error));
|
|
}
|
|
|
|
document.getElementById('associationsList').addEventListener('click', function(event) {
|
|
if (event.target.classList.contains('removeAssociation')) {
|
|
let excelColumn = event.target.getAttribute("data-excel");
|
|
let mysqlColumn = event.target.getAttribute("data-mysql");
|
|
|
|
removeAssociation(excelColumn, mysqlColumn);
|
|
}
|
|
});
|
|
|
|
function removeAssociation(excelColumn, mysqlColumn) {
|
|
fetch('remove_column_mapping.php', {
|
|
method: 'POST',
|
|
headers: {
|
|
'Content-Type': 'application/json'
|
|
},
|
|
body: JSON.stringify({
|
|
template_id: templateId,
|
|
excel_column: excelColumn,
|
|
mysql_column: mysqlColumn,
|
|
tablename: "<?php echo $template['target_table']; ?>"
|
|
})
|
|
})
|
|
.then(response => response.json())
|
|
.then(data => {
|
|
if (!data.success) {
|
|
console.error("❌ Error removing mapping:", data.message);
|
|
alert("Error removing mapping: " + data.message);
|
|
} else {
|
|
console.log("🗑️ Association removed:", data);
|
|
loadMappings();
|
|
}
|
|
})
|
|
.catch(error => console.error("❌ Fetch error:", error));
|
|
}
|
|
});
|
|
</script>
|
|
</body>
|
|
|
|
</html>
|