update historical trf and navbar

This commit is contained in:
Claudio 2025-08-27 12:13:11 +02:00
parent 22e4e652b5
commit 06dd7883c2
4 changed files with 744 additions and 488 deletions

View File

@ -0,0 +1,64 @@
<?php
// Enable errors for debugging
ini_set('display_errors', 1);
ini_set('display_startup_errors', 1);
error_reporting(E_ALL);
ini_set('log_errors', 1);
ini_set('error_log', __DIR__ . '/delete_record_debug.log');
// Log iniziale
error_log("Inizio cancellazione record alle " . date('Y-m-d H:i:s'));
// Includi il file di configurazione del database
include('include/headscript.php');
// Ricevi l'ID dalla richiesta POST
$input = json_decode(file_get_contents('php://input'), true);
$iddatadb = isset($input['id']) ? intval($input['id']) : 0;
if ($iddatadb <= 0) {
http_response_code(400);
echo json_encode(['success' => false, 'message' => 'ID non valido']);
exit;
}
// Connessione al database
try {
$db = DBHandlerSelect::getInstance();
$pdo = $db->getConnection();
} catch (Exception $e) {
http_response_code(500);
echo json_encode(['success' => false, 'message' => 'Errore di connessione al database: ' . $e->getMessage()]);
error_log("Errore di connessione al database: " . $e->getMessage());
exit;
}
// Inizia una transazione
$pdo->beginTransaction();
try {
// Elimina i dettagli associati dal tavolo import_data_details
$stmt = $pdo->prepare("DELETE FROM import_data_details WHERE id = ?");
$stmt->execute([$iddatadb]);
// Elimina il record principale dal tavolo datadb
$stmt = $pdo->prepare("DELETE FROM datadb WHERE iddatadb = ?");
$stmt->execute([$iddatadb]);
// Verifica se il record è stato eliminato
if ($stmt->rowCount() > 0) {
$pdo->commit();
echo json_encode(['success' => true, 'message' => 'Record eliminato con successo']);
error_log("Record con iddatadb=$iddatadb eliminato con successo");
} else {
$pdo->rollBack();
http_response_code(404);
echo json_encode(['success' => false, 'message' => 'Record non trovato']);
error_log("Record con iddatadb=$iddatadb non trovato");
}
} catch (Exception $e) {
$pdo->rollBack();
http_response_code(500);
echo json_encode(['success' => false, 'message' => 'Errore durante la cancellazione: ' . $e->getMessage()]);
error_log("Errore durante la cancellazione del record con iddatadb=$iddatadb: " . $e->getMessage());
}

View File

@ -27,7 +27,11 @@ if (!in_array($status, ['i', 'P', 'l'])) {
$is_readonly = in_array($status, ['P', 'l']);
// Paginazione
// Gestione modalità: lista (default per status 'i') o edit
$mode = $_GET['mode'] ?? ($status === 'i' ? 'list' : 'edit');
$selected_ids = $_POST['selected_ids'] ?? [];
// Paginazione (solo per mode 'list')
$page = max(1, intval($_GET['page'] ?? 1));
$limit = 20;
$offset = ($page - 1) * $limit;
@ -36,14 +40,8 @@ $offset = ($page - 1) * $limit;
$db = DBHandlerSelect::getInstance();
$pdo = $db->getConnection();
// Conta il numero totale di record
$stmt = $pdo->prepare("SELECT COUNT(*) FROM datadb WHERE templateid = ? AND status = ?");
$stmt->execute([$template_id, $status]);
$total_records = $stmt->fetchColumn();
$total_pages = ceil($total_records / $limit);
// Retrieve all mappings
$stmt = $pdo->prepare("SELECT id, excel_column, data_type, is_required, manual_default, is_manual, field_label, field_id FROM template_mapping WHERE template_id = ?");
$stmt = $pdo->prepare("SELECT id, excel_column, data_type, is_required, manual_default, is_manual, field_label, field_id, main_field FROM template_mapping WHERE template_id = ?");
$stmt->execute([$template_id]);
$allMappings = $stmt->fetchAll(PDO::FETCH_ASSOC);
@ -52,7 +50,38 @@ if (empty($allMappings)) {
exit;
}
// Trova il main_field
$mainFieldMapping = null;
foreach ($allMappings as $mapping) {
if ($mapping['main_field'] == 1) {
$mainFieldMapping = $mapping;
break;
}
}
if (!$mainFieldMapping) {
$mainFieldMapping = reset(array_filter($allMappings, fn($m) => !$m['is_manual']));
}
// Retrieve data from datadb
if ($mode === 'edit' && !empty($selected_ids)) {
$placeholders = implode(',', array_fill(0, count($selected_ids), '?'));
$stmt = $pdo->prepare("
SELECT d.*, CONCAT(u.first_name, ' ', u.last_name) AS user_name
FROM datadb d
LEFT JOIN auth_users u ON d.user_id = u.id
WHERE d.templateid = ? AND d.status = ? AND d.iddatadb IN ($placeholders)
");
$params = array_merge([$template_id, $status], $selected_ids);
$stmt->execute($params);
$importedData = $stmt->fetchAll(PDO::FETCH_ASSOC);
$total_records = count($importedData);
$total_pages = 1;
} else {
$stmt = $pdo->prepare("SELECT COUNT(*) FROM datadb WHERE templateid = ? AND status = ?");
$stmt->execute([$template_id, $status]);
$total_records = $stmt->fetchColumn();
$total_pages = ceil($total_records / $limit);
$stmt = $pdo->prepare("
SELECT d.*, CONCAT(u.first_name, ' ', u.last_name) AS user_name
FROM datadb d
@ -62,6 +91,7 @@ $stmt = $pdo->prepare("
");
$stmt->execute([$template_id, $status, $limit, $offset]);
$importedData = $stmt->fetchAll(PDO::FETCH_ASSOC);
}
error_log("Record caricati: " . count($importedData));
@ -436,6 +466,39 @@ foreach ($stmt->fetchAll(PDO::FETCH_ASSOC) as $row) {
background-color: #d4edda;
transition: background-color 0.5s ease;
}
.list-table {
width: 100%;
border-collapse: collapse;
}
.list-table th,
.list-table td {
padding: 10px;
border: 1px solid #dee2e6;
text-align: left;
}
.list-table th {
background-color: #e9ecef;
}
.delete-btn {
background: #dc3545;
color: white;
border: none;
padding: 5px 10px;
border-radius: 4px;
cursor: pointer;
}
.delete-btn:hover {
background: #c82333;
}
.proceed-btn {
margin-top: 20px;
}
</style>
<title>Dati Storici - <?= htmlspecialchars($titlewebsite, ENT_QUOTES, 'UTF-8'); ?></title>
</head>
@ -454,7 +517,7 @@ foreach ($stmt->fetchAll(PDO::FETCH_ASSOC) as $row) {
</div>
<div>
<label for="status-filter">Filtra per Status:</label>
<select id="status-filter" onchange="window.location.href='historical_trf.php?id=<?= $template_id ?>&status=' + this.value">
<select id="status-filter">
<option value="i" <?= $status === 'i' ? 'selected' : '' ?>>Imported (i)</option>
<option value="P" <?= $status === 'P' ? 'selected' : '' ?>>Progress (P)</option>
<option value="l" <?= $status === 'l' ? 'selected' : '' ?>>LIMS (l)</option>
@ -467,12 +530,74 @@ foreach ($stmt->fetchAll(PDO::FETCH_ASSOC) as $row) {
<div class="alert alert-info text-center">
Nessun dato trovato per il template e lo status selezionato.
</div>
<?php else: ?>
<?php if ($mode === 'list'): ?>
<form id="selectForm" method="POST" action="historical_trf.php?id=<?= $template_id ?>&status=<?= $status ?>&mode=edit">
<div class="mb-3 d-flex align-items-center justify-content-between">
<div>
Visualizzazione di <?= min($offset + 1, $total_records) ?>-<?= min($offset + count($importedData), $total_records) ?> di <?= $total_records ?> record
</div>
<div>
<input type="text" id="searchInput" placeholder="Cerca in tutte le colonne..." class="form-control form-control-sm" style="width: 300px;">
<div id="noResults" class="text-danger" style="display:none;">Nessun risultato trovato</div>
</div>
</div>
<table class="list-table">
<thead>
<tr>
<th><input type="checkbox" id="selectAll"></th>
<th><?= htmlspecialchars($mainFieldMapping['field_label'] ?? 'Main Field') ?></th>
<th>File</th>
<th><?= htmlspecialchars($slugMapping['importdate'] ?? 'Import Date') ?></th>
<th>Azioni</th>
</tr>
</thead>
<tbody>
<?php foreach ($importedData as $row): ?>
<?php
$mainValue = '';
if ($mainFieldMapping) {
$stmt = $pdo->prepare("SELECT field_value FROM import_data_details WHERE id = ? AND mapping_id = ?");
$stmt->execute([$row['iddatadb'], $mainFieldMapping['id']]);
$mainValue = $stmt->fetchColumn() ?? '';
}
?>
<tr>
<td><input type="checkbox" name="selected_ids[]" value="<?= $row['iddatadb'] ?>"></td>
<td><?= htmlspecialchars($mainValue) ?></td>
<td><a href="imported_trf/<?= htmlspecialchars($row['filename_import']) ?>" target="_blank">File</a></td>
<td><?= htmlspecialchars($row['importdate']) ?></td>
<td>
<button type="button" class="delete-btn" data-id="<?= $row['iddatadb'] ?>"><i class="fas fa-trash"></i></button>
</td>
</tr>
<?php endforeach; ?>
</tbody>
</table>
<nav aria-label="Page navigation" class="mt-3">
<ul class="pagination justify-content-center">
<li class="page-item <?= $page <= 1 ? 'disabled' : '' ?>">
<a class="page-link" href="historical_trf.php?id=<?= $template_id ?>&status=<?= $status ?>&mode=list&page=<?= $page - 1 ?>">Precedente</a>
</li>
<?php for ($i = 1; $i <= $total_pages; $i++): ?>
<li class="page-item <?= $i === $page ? 'active' : '' ?>">
<a class="page-link" href="historical_trf.php?id=<?= $template_id ?>&status=<?= $status ?>&mode=list&page=<?= $i ?>"><?= $i ?></a>
</li>
<?php endfor; ?>
<li class="page-item <?= $page >= $total_pages ? 'disabled' : '' ?>">
<a class="page-link" href="historical_trf.php?id=<?= $template_id ?>&status=<?= $status ?>&mode=list&page=<?= $page + 1 ?>">Successivo</a>
</li>
</ul>
</nav>
<div class="text-center">
<button type="submit" class="btn btn-primary proceed-btn">Prosegui con Modifica Massiva</button>
</div>
</form>
<?php else: ?>
<div class="mb-3 d-flex align-items-center justify-content-between">
<div>
Visualizzazione di <?= min($offset + 1, $total_records) ?>-<?= min($offset + count($importedData), $total_records) ?> di <?= $total_records ?> record
</div>
<div class="d-flex align-items-center">
<input type="text" id="searchInput" placeholder="Cerca..." class="form-control form-control-sm me-2" style="width: 200px;">
<button type="button" class="btn btn-secondary btn-sm me-1 scroll-left">
@ -483,10 +608,7 @@ foreach ($stmt->fetchAll(PDO::FETCH_ASSOC) as $row) {
</button>
</div>
</div>
<div id="noResults" class="text-danger" style="display:none;">Nessun risultato trovato</div>
<div class="scrollbar-container"></div>
<form id="editForm">
<div class="grid-container">
@ -498,7 +620,6 @@ foreach ($stmt->fetchAll(PDO::FETCH_ASSOC) as $row) {
<div class="grid-cell" style="flex: 0 0 100px;"></div>
<div class="grid-cell" style="flex: 0 0 150px;"></div>
<?php
//$fixedColumns = ['filename_import', 'status', 'importdate'];
foreach ($fixedColumns as $col) {
echo "<div class='grid-cell' style='flex: 0 0 150px;'></div>";
}
@ -699,15 +820,15 @@ foreach ($stmt->fetchAll(PDO::FETCH_ASSOC) as $row) {
<nav aria-label="Page navigation" class="mt-3">
<ul class="pagination justify-content-center">
<li class="page-item <?= $page <= 1 ? 'disabled' : '' ?>">
<a class="page-link" href="historical_trf.php?id=<?= $template_id ?>&status=<?= $status ?>&page=<?= $page - 1 ?>">Precedente</a>
<a class="page-link" href="historical_trf.php?id=<?= $template_id ?>&status=<?= $status ?>&mode=edit&page=<?= $page - 1 ?>">Precedente</a>
</li>
<?php for ($i = 1; $i <= $total_pages; $i++): ?>
<li class="page-item <?= $i === $page ? 'active' : '' ?>">
<a class="page-link" href="historical_trf.php?id=<?= $template_id ?>&status=<?= $status ?>&page=<?= $i ?>"><?= $i ?></a>
<a class="page-link" href="historical_trf.php?id=<?= $template_id ?>&status=<?= $status ?>&mode=edit&page=<?= $i ?>"><?= $i ?></a>
</li>
<?php endfor; ?>
<li class="page-item <?= $page >= $total_pages ? 'disabled' : '' ?>">
<a class="page-link" href="historical_trf.php?id=<?= $template_id ?>&status=<?= $status ?>&page=<?= $page + 1 ?>">Successivo</a>
<a class="page-link" href="historical_trf.php?id=<?= $template_id ?>&status=<?= $status ?>&mode=edit&page=<?= $page + 1 ?>">Successivo</a>
</li>
</ul>
</nav>
@ -725,7 +846,7 @@ foreach ($stmt->fetchAll(PDO::FETCH_ASSOC) as $row) {
}
?>
<?php endif; ?>
</div>
<?php endif; ?>
</div>
</div>
</div>
@ -743,6 +864,77 @@ foreach ($stmt->fetchAll(PDO::FETCH_ASSOC) as $row) {
console.log("Righe caricate: <?= count($importedData) ?>");
console.log("Totale record: <?= $total_records ?>, Pagine: <?= $total_pages ?>");
// Gestione del dropdown status-filter
const statusFilter = document.getElementById('status-filter');
statusFilter.addEventListener('change', function() {
const status = this.value;
const mode = status === 'i' ? 'list' : 'edit';
window.location.href = `historical_trf.php?id=<?= $template_id ?>&status=${status}&mode=${mode}`;
});
<?php if ($mode === 'list'): ?>
// Gestione select all
const selectAll = document.getElementById('selectAll');
selectAll.addEventListener('change', function() {
document.querySelectorAll('input[name="selected_ids[]"]').forEach(cb => cb.checked = this.checked);
});
// Gestione filtro unico
const searchInput = document.querySelector('#searchInput');
const noResults = document.querySelector('#noResults');
searchInput.addEventListener('input', function() {
const filter = this.value.toLowerCase();
const rows = document.querySelectorAll('.list-table tbody tr');
let hasResults = false;
rows.forEach(row => {
const cells = row.querySelectorAll('td');
let match = false;
cells.forEach((cell, index) => {
if (index >= 1 && index <= 3) {
const text = cell.textContent.toLowerCase();
if (text.includes(filter)) {
match = true;
}
}
});
row.style.display = match ? '' : 'none';
if (match) hasResults = true;
});
noResults.style.display = hasResults ? 'none' : 'block';
});
// Gestione cancellazione
const deleteButtons = document.querySelectorAll('.delete-btn');
deleteButtons.forEach(btn => {
btn.addEventListener('click', function() {
const id = this.getAttribute('data-id');
if (confirm('Sicuro di voler cancellare questo record?')) {
fetch('delete_record.php', {
method: 'POST',
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify({
id: id
})
})
.then(response => response.json())
.then(data => {
if (data.success) {
this.closest('tr').remove();
const currentCount = document.querySelectorAll('.list-table tbody tr').length;
if (currentCount === 0) {
location.reload();
}
} else {
alert('Errore: ' + data.message);
}
})
.catch(error => alert('Errore durante la cancellazione: ' + error.message));
}
});
});
<?php else: ?>
// Gestione input e celle espandibili
const inputs = document.querySelectorAll('.cell-input');
inputs.forEach(input => {
@ -859,12 +1051,11 @@ foreach ($stmt->fetchAll(PDO::FETCH_ASSOC) as $row) {
}
});
// Gestione filtro di ricerca
// Gestione filtro di ricerca (per la griglia)
const searchInput = document.querySelector('#searchInput');
const noResults = document.querySelector('#noResults');
searchInput.addEventListener('input', function() {
const filter = this.value.toLowerCase();
// Esegui il filtro solo se ci sono almeno 3 caratteri
if (filter.length < 3) {
const rows = document.querySelectorAll('.grid-row');
rows.forEach(row => row.style.display = '');
@ -894,6 +1085,7 @@ foreach ($stmt->fetchAll(PDO::FETCH_ASSOC) as $row) {
});
noResults.style.display = hasResults ? 'none' : 'block';
});
// Gestione scorrimento orizzontale
const gridContainer = document.querySelector('.grid-container');
const scrollbarContainer = document.querySelector('.scrollbar-container');
@ -929,9 +1121,7 @@ foreach ($stmt->fetchAll(PDO::FETCH_ASSOC) as $row) {
// Gestione dropdown
const dropdownData = {};
async function populateDropdowns() {
// Esegui solo se non è in modalità readonly (status = 'i')
if (<?= json_encode($is_readonly) ?>) return;
const dropdowns = document.querySelectorAll('.dropdown-select');
if (dropdowns.length === 0) return;
const uniqueFieldIds = [...new Set(Array.from(dropdowns).map(d => d.getAttribute('data-field-id')))].filter(fieldId => fieldId);
@ -974,11 +1164,9 @@ foreach ($stmt->fetchAll(PDO::FETCH_ASSOC) as $row) {
}
});
});
<?php endif; ?>
});
</script>
</body>
</html>
<?php
// Fine del file PHP
?>

View File

@ -126,7 +126,11 @@ error_log("Loaded template: " . print_r($template, true));
<div class="page-wrapper">
<div class="page-content">
<?php include('top_stat_widget.php'); ?>
<div class="mb-3 text">
<a href="historical_trf.php?id=<?= $id ?>&status=i" class="btn btn-warning me-2">Imported (i)</a>
<a href="historical_trf.php?id=<?= $id ?>&status=P" class="btn btn-primary me-2">In Progress (P)</a>
<a href="historical_trf.php?id=<?= $id ?>&status=l" class="btn btn-success">To LIMS (l)</a>
</div>
<div class="card radius-10">
<div class="card-header">
<div class="d-flex align-items-center">
@ -136,6 +140,7 @@ error_log("Loaded template: " . print_r($template, true));
</div>
</div>
</div>
<div class="card-body">
<!-- Form per caricare il file -->
<form id="uploadForm" enctype="multipart/form-data" class="mb-4">

View File

@ -24,8 +24,7 @@
</li> -->
<li> <a href="import_dashboard.php"><i class='bx bx-radio-circle'></i>XLS Import</a>
</li>
<li> <a href="historical_trf.php"><i class='bx bx-radio-circle'></i>Historical TRF</a>
</li>
</ul>
</li>