327 lines
13 KiB
PHP
327 lines
13 KiB
PHP
<?php
|
|
|
|
namespace App\Services\GesconImport\Traits;
|
|
|
|
/**
|
|
* Metodi di scansione/preview legacy estratti dal controller gigante per ridurre complessità.
|
|
* Non dipendono da stato esterno eccetto chiamate shell e filesystem.
|
|
*/
|
|
trait LegacyScanning
|
|
{
|
|
private function scanStabiliFromMasterIndex(string $indexMdbPath, string $legacyBasePath): array
|
|
{
|
|
$binTables = trim((string)@shell_exec('command -v mdb-tables')) ?: '/usr/bin/mdb-tables';
|
|
$binExport = trim((string)@shell_exec('command -v mdb-export')) ?: '/usr/bin/mdb-export';
|
|
if (!is_file($indexMdbPath) || !is_readable($indexMdbPath)) return [];
|
|
|
|
$tableGuess = null;
|
|
$tables = @shell_exec(sprintf('%s -1 %s 2>/dev/null', escapeshellarg($binTables), escapeshellarg($indexMdbPath))) ?: '';
|
|
if ($tables) {
|
|
foreach (preg_split('/\r?\n/', trim($tables)) as $t) {
|
|
if ($t === '') continue;
|
|
if (preg_match('/(cartelle|stabil|anni)/i', $t)) {
|
|
$tableGuess = trim($t);
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
if (!$tableGuess) {
|
|
$lines = array_filter(preg_split('/\r?\n/', trim($tables)));
|
|
$tableGuess = $lines ? trim(array_values($lines)[0]) : null;
|
|
}
|
|
if (!$tableGuess) return [];
|
|
|
|
$tmp = tempnam(sys_get_temp_dir(), 'mdbcsv_');
|
|
$cmd = sprintf(
|
|
'%s -D %s -d %s -q %s -R "\\n" %s %s > %s 2>/dev/null',
|
|
escapeshellarg($binExport),
|
|
escapeshellarg('%Y-%m-%d'),
|
|
escapeshellarg('|'),
|
|
escapeshellarg('"'),
|
|
escapeshellarg($indexMdbPath),
|
|
escapeshellarg($tableGuess),
|
|
escapeshellarg($tmp)
|
|
);
|
|
@shell_exec($cmd);
|
|
if (!is_file($tmp) || filesize($tmp) === 0) {
|
|
@unlink($tmp);
|
|
return [];
|
|
}
|
|
$fh = fopen($tmp, 'r');
|
|
if (!$fh) {
|
|
@unlink($tmp);
|
|
return [];
|
|
}
|
|
$headers = fgetcsv($fh, 0, '|');
|
|
if (!$headers) {
|
|
fclose($fh);
|
|
@unlink($tmp);
|
|
return [];
|
|
}
|
|
$headers = array_map(fn($h) => strtolower(trim((string)$h)), $headers);
|
|
$byCodeYears = [];
|
|
$byCodeName = [];
|
|
while (($cols = fgetcsv($fh, 0, '|')) !== false) {
|
|
if ($cols === [null]) continue;
|
|
$cols = array_map(fn($v) => is_string($v) ? trim($v) : $v, $cols);
|
|
if (count($cols) < count($headers)) $cols = array_pad($cols, count($headers), null);
|
|
if (count($cols) > count($headers)) $cols = array_slice($cols, 0, count($headers));
|
|
$row = @array_combine($headers, $cols) ?: [];
|
|
if (!$row) continue;
|
|
$code = $row['nome_directory'] ?? $row['cod_stabile'] ?? $row['internet_cod_stab'] ?? $row['codice'] ?? null;
|
|
$denom = $row['denominazione'] ?? $row['fe_denominazione'] ?? null;
|
|
$anno = $row['anno'] ?? $row['year'] ?? null;
|
|
if (!$code) continue;
|
|
$code = (string)$code;
|
|
if (!isset($byCodeYears[$code])) $byCodeYears[$code] = [];
|
|
if ($anno && preg_match('/^\d{4}$/', (string)$anno)) $byCodeYears[$code][(string)$anno] = true;
|
|
if ($denom) $byCodeName[$code] = (string)$denom;
|
|
}
|
|
fclose($fh);
|
|
@unlink($tmp);
|
|
$items = [];
|
|
foreach ($byCodeYears as $code => $yearsSet) {
|
|
$den = $byCodeName[$code] ?? null;
|
|
$years = array_keys($yearsSet);
|
|
sort($years, SORT_STRING);
|
|
$items[] = ['legacy_code' => $code, 'denominazione' => $den, 'years_count' => count($years), 'years' => $years];
|
|
}
|
|
if (empty($items)) {
|
|
$items = $this->scanLegacyCodesFromDir($legacyBasePath);
|
|
$items = $this->enrichLegacyWithArchives($items, $legacyBasePath);
|
|
}
|
|
usort($items, fn($a, $b) => strnatcasecmp((string)($a['legacy_code'] ?? ''), (string)($b['legacy_code'] ?? '')));
|
|
return $items;
|
|
}
|
|
|
|
private function scanStabiliFromMdb(string $mdbPath): array
|
|
{
|
|
$binTables = trim((string)@shell_exec('command -v mdb-tables')) ?: '/usr/bin/mdb-tables';
|
|
$binExport = trim((string)@shell_exec('command -v mdb-export')) ?: '/usr/bin/mdb-export';
|
|
$tableGuess = 'Stabili';
|
|
$tables = @shell_exec(sprintf('%s -1 %s 2>/dev/null', escapeshellarg($binTables), escapeshellarg($mdbPath))) ?: '';
|
|
if ($tables) {
|
|
foreach (preg_split('/\r?\n/', trim($tables)) as $t) {
|
|
if ($t === "") continue;
|
|
if (preg_match('/stabil/i', $t)) {
|
|
$tableGuess = trim($t);
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
$tmp = tempnam(sys_get_temp_dir(), 'mdbcsv_');
|
|
$cmd = sprintf(
|
|
'%s -D %s -d %s -q %s -R "\\n" %s %s > %s 2>/dev/null',
|
|
escapeshellarg($binExport),
|
|
escapeshellarg('%Y-%m-%d'),
|
|
escapeshellarg('|'),
|
|
escapeshellarg('"'),
|
|
escapeshellarg($mdbPath),
|
|
escapeshellarg($tableGuess),
|
|
escapeshellarg($tmp)
|
|
);
|
|
@shell_exec($cmd);
|
|
if (!is_file($tmp) || filesize($tmp) === 0) {
|
|
@unlink($tmp);
|
|
return [];
|
|
}
|
|
$fh = fopen($tmp, 'r');
|
|
if (!$fh) {
|
|
@unlink($tmp);
|
|
return [];
|
|
}
|
|
$headers = fgetcsv($fh, 0, '|');
|
|
if (!$headers) {
|
|
fclose($fh);
|
|
@unlink($tmp);
|
|
return [];
|
|
}
|
|
$headers = array_map(fn($h) => strtolower(trim((string)$h)), $headers);
|
|
$items = [];
|
|
while (($cols = fgetcsv($fh, 0, '|')) !== false) {
|
|
if ($cols === [null] || $cols === false) continue;
|
|
$cols = array_map(fn($v) => is_string($v) ? trim($v) : $v, $cols);
|
|
$countH = count($headers);
|
|
if (count($cols) < $countH) $cols = array_pad($cols, $countH, null);
|
|
if (count($cols) > $countH) $cols = array_slice($cols, 0, $countH);
|
|
$row = @array_combine($headers, $cols);
|
|
if (!$row) continue;
|
|
$legacyCode = $row['nome_directory'] ?? ($row['internet_cod_stab'] ?? ($row['cod_stabile'] ?? null));
|
|
$denom = $row['denominazione'] ?? ($row['fe_denominazione'] ?? null);
|
|
if ($legacyCode) {
|
|
$items[] = ['legacy_code' => trim((string)$legacyCode), 'denominazione' => $denom ? trim((string)$denom) : null];
|
|
}
|
|
}
|
|
fclose($fh);
|
|
@unlink($tmp);
|
|
$byCode = [];
|
|
foreach ($items as $it) {
|
|
if (!empty($it['legacy_code'])) $byCode[$it['legacy_code']] = $it;
|
|
}
|
|
ksort($byCode, SORT_NATURAL);
|
|
return array_values($byCode);
|
|
}
|
|
|
|
private function sampleStabileFromMdb(string $mdbPath, ?string $legacyCode, int $index = 0): array
|
|
{
|
|
$binTables = trim((string)@shell_exec('command -v mdb-tables')) ?: '/usr/bin/mdb-tables';
|
|
$binExport = trim((string)@shell_exec('command -v mdb-export')) ?: '/usr/bin/mdb-export';
|
|
$tableGuess = 'Stabili';
|
|
$tables = @shell_exec(sprintf('%s -1 %s 2>/dev/null', escapeshellarg($binTables), escapeshellarg($mdbPath))) ?: '';
|
|
if ($tables) {
|
|
foreach (preg_split('/\r?\n/', trim($tables)) as $t) {
|
|
if ($t === '') continue;
|
|
if (preg_match('/stabil/i', $t)) {
|
|
$tableGuess = trim($t);
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
$tmp = tempnam(sys_get_temp_dir(), 'mdbcsv_');
|
|
$cmd = sprintf(
|
|
'%s -D %s -d %s -q %s -R "\\n" %s %s > %s 2>/dev/null',
|
|
escapeshellarg($binExport),
|
|
escapeshellarg('%Y-%m-%d'),
|
|
escapeshellarg('|'),
|
|
escapeshellarg('"'),
|
|
escapeshellarg($mdbPath),
|
|
escapeshellarg($tableGuess),
|
|
escapeshellarg($tmp)
|
|
);
|
|
@shell_exec($cmd);
|
|
if (!is_file($tmp) || filesize($tmp) === 0) {
|
|
@unlink($tmp);
|
|
return [];
|
|
}
|
|
$fh = fopen($tmp, 'r');
|
|
if (!$fh) {
|
|
@unlink($tmp);
|
|
return [];
|
|
}
|
|
$headers = fgetcsv($fh, 0, '|');
|
|
if (!$headers) {
|
|
fclose($fh);
|
|
@unlink($tmp);
|
|
return [];
|
|
}
|
|
$headers = array_map(fn($h) => strtolower(trim((string)$h)), $headers);
|
|
$rowData = [];
|
|
$i = 0;
|
|
while (($cols = fgetcsv($fh, 0, '|')) !== false) {
|
|
if ($cols === [null]) continue;
|
|
$cols = array_map(fn($v) => is_string($v) ? trim($v) : $v, $cols);
|
|
$countH = count($headers);
|
|
if (count($cols) < $countH) $cols = array_pad($cols, $countH, null);
|
|
if (count($cols) > $countH) $cols = array_slice($cols, 0, $countH);
|
|
$row = @array_combine($headers, $cols) ?: [];
|
|
$legacyKey = $row['nome_directory'] ?? ($row['internet_cod_stab'] ?? ($row['cod_stabile'] ?? null));
|
|
if ($legacyCode) {
|
|
if ((string)$legacyKey === (string)$legacyCode) {
|
|
$rowData = $row;
|
|
break;
|
|
}
|
|
} else {
|
|
if ($i++ >= $index) {
|
|
$rowData = $row;
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
fclose($fh);
|
|
@unlink($tmp);
|
|
if (empty($rowData)) return [];
|
|
$rowData['legacy_key'] = (string)($rowData['nome_directory'] ?? ($rowData['internet_cod_stab'] ?? ($rowData['cod_stabile'] ?? '')));
|
|
return $rowData;
|
|
}
|
|
|
|
private function scanLegacyCodesFromDir(string $basePath): array
|
|
{
|
|
$items = [];
|
|
if (!is_dir($basePath)) return $items;
|
|
try {
|
|
$dh = opendir($basePath);
|
|
if ($dh) {
|
|
while (($file = readdir($dh)) !== false) {
|
|
if ($file === '.' || $file === '..') continue;
|
|
$full = rtrim($basePath, DIRECTORY_SEPARATOR) . DIRECTORY_SEPARATOR . $file;
|
|
if (!is_dir($full)) continue;
|
|
$code = null;
|
|
if (preg_match('/^(\d{2,5})/', $file, $m)) {
|
|
$code = $m[1];
|
|
} elseif (preg_match('/(\d{2,5})/', $file, $m)) {
|
|
$code = $m[1];
|
|
}
|
|
$hasGenerale = is_file($full . DIRECTORY_SEPARATOR . 'generale_stabile.mdb');
|
|
$hasYears = false;
|
|
if (is_dir($full)) {
|
|
try {
|
|
$sub = opendir($full);
|
|
if ($sub) {
|
|
while (($yf = readdir($sub)) !== false) {
|
|
if ($yf === '.' || $yf === '..') continue;
|
|
if (!preg_match('/^\d{4}$/', $yf)) continue;
|
|
$ya = $full . DIRECTORY_SEPARATOR . $yf . DIRECTORY_SEPARATOR . 'singolo_anno.mdb';
|
|
if (is_file($ya)) {
|
|
$hasYears = true;
|
|
break;
|
|
}
|
|
}
|
|
closedir($sub);
|
|
}
|
|
} catch (\Throwable $e) {
|
|
}
|
|
}
|
|
if ($code || $hasGenerale || $hasYears) {
|
|
$items[] = ['legacy_code' => $code ?: $file, 'denominazione' => null];
|
|
}
|
|
}
|
|
closedir($dh);
|
|
}
|
|
} catch (\Throwable $e) { /* ignore */
|
|
}
|
|
$byCode = [];
|
|
foreach ($items as $it) {
|
|
$c = (string)($it['legacy_code'] ?? '');
|
|
if ($c !== '') {
|
|
$byCode[$c] = $it;
|
|
}
|
|
}
|
|
uksort($byCode, 'strnatcasecmp');
|
|
return array_values($byCode);
|
|
}
|
|
|
|
private function enrichLegacyWithArchives(array $items, string $basePath): array
|
|
{
|
|
$enriched = [];
|
|
foreach ($items as $it) {
|
|
$code = trim((string)($it['legacy_code'] ?? ''));
|
|
if ($code === '') {
|
|
$enriched[] = $it;
|
|
continue;
|
|
}
|
|
$dir = rtrim($basePath, DIRECTORY_SEPARATOR) . DIRECTORY_SEPARATOR . $code;
|
|
$hasGenerale = is_file($dir . DIRECTORY_SEPARATOR . 'generale_stabile.mdb');
|
|
$yearsCount = 0;
|
|
if (is_dir($dir)) {
|
|
try {
|
|
$dh = opendir($dir);
|
|
if ($dh) {
|
|
while (($f = readdir($dh)) !== false) {
|
|
if ($f === '.' || $f === '..') continue;
|
|
if (!preg_match('/^\d{4}$/', $f)) continue;
|
|
$sub = $dir . DIRECTORY_SEPARATOR . $f . DIRECTORY_SEPARATOR . 'singolo_anno.mdb';
|
|
if (is_file($sub)) $yearsCount++;
|
|
}
|
|
closedir($dh);
|
|
}
|
|
} catch (\Throwable $e) {
|
|
}
|
|
}
|
|
$it['has_generale'] = $hasGenerale;
|
|
$it['years_count'] = $yearsCount;
|
|
$enriched[] = $it;
|
|
}
|
|
return $enriched;
|
|
}
|
|
}
|