fixed naslove

This commit is contained in:
Simon Pocrnjič 2025-12-17 21:12:53 +01:00
parent b8c9b51f29
commit 6c45063e47

View File

@ -28,12 +28,14 @@
use Illuminate\Database\QueryException; use Illuminate\Database\QueryException;
use Illuminate\Support\Carbon; use Illuminate\Support\Carbon;
use Illuminate\Support\Facades\DB; use Illuminate\Support\Facades\DB;
use Illuminate\Support\Facades\Log;
use Illuminate\Support\Facades\Storage; use Illuminate\Support\Facades\Storage;
class ImportProcessor class ImportProcessor
{ {
/** /**
* Track contracts that already existed and were matched during history imports. * Track contracts that already existed and were matched during history imports.
*
* @var array<int,bool> * @var array<int,bool>
*/ */
private array $historyFoundContractIds = []; private array $historyFoundContractIds = [];
@ -220,6 +222,11 @@ public function process(Import $import, ?Authenticatable $user = null): array
try { try {
DB::statement('SAVEPOINT import_row_'.$rowNum); DB::statement('SAVEPOINT import_row_'.$rowNum);
} catch (\Throwable $se) { } catch (\Throwable $se) {
Log::error('Import savepoint_failed', [
'import_id' => $import->id,
'row_number' => $rowNum,
'exception' => $this->exceptionContext($se),
]);
ImportEvent::create([ ImportEvent::create([
'import_id' => $import->id, 'import_id' => $import->id,
'user_id' => $user?->getAuthIdentifier(), 'user_id' => $user?->getAuthIdentifier(),
@ -1096,6 +1103,11 @@ public function process(Import $import, ?Authenticatable $user = null): array
} }
} }
if ($rollbackFailed) { if ($rollbackFailed) {
Log::error('Import row_rollback_failed', [
'import_id' => $import->id,
'row_number' => $rowNum,
'exception' => $this->exceptionContext($rollbackError ?? $e),
]);
// Abort the whole import if we cannot rollback to the row savepoint (transaction is poisoned) // Abort the whole import if we cannot rollback to the row savepoint (transaction is poisoned)
ImportEvent::create([ ImportEvent::create([
'import_id' => $import->id, 'import_id' => $import->id,
@ -1137,6 +1149,12 @@ public function process(Import $import, ?Authenticatable $user = null): array
} }
$failedRows[] = $rowNum; $failedRows[] = $rowNum;
$invalid++; $invalid++;
Log::error('Import row_exception', [
'import_id' => $import->id,
'row_number' => $rowNum,
'exception' => $this->exceptionContext($e),
'raw_preview' => isset($rawAssoc) ? $this->buildRawDataPreview($rawAssoc) : [],
]);
try { try {
ImportEvent::create([ ImportEvent::create([
'import_id' => $import->id, 'import_id' => $import->id,
@ -1154,6 +1172,12 @@ public function process(Import $import, ?Authenticatable $user = null): array
], ],
]); ]);
} catch (\Throwable $evtErr) { } catch (\Throwable $evtErr) {
Log::error('Import row_exception_event_failed', [
'import_id' => $import->id,
'row_number' => $rowNum,
'exception' => $this->exceptionContext($evtErr),
'original_exception' => $this->exceptionContext($e),
]);
// Swallow secondary failure to ensure loop continues // Swallow secondary failure to ensure loop continues
} }
@ -1226,6 +1250,10 @@ public function process(Import $import, ?Authenticatable $user = null): array
// Mark failed and log after rollback (so no partial writes persist) // Mark failed and log after rollback (so no partial writes persist)
$import->refresh(); $import->refresh();
$import->update(['status' => 'failed', 'failed_at' => now()]); $import->update(['status' => 'failed', 'failed_at' => now()]);
Log::error('Import processing_failed', [
'import_id' => $import->id,
'exception' => $this->exceptionContext($e),
]);
ImportEvent::create([ ImportEvent::create([
'import_id' => $import->id, 'import_id' => $import->id,
'user_id' => $user?->getAuthIdentifier(), 'user_id' => $user?->getAuthIdentifier(),
@ -2047,7 +2075,7 @@ private function upsertActivity(Import $import, array $mapped, $mappings, ?array
} }
$data = array_filter($applyInsert, fn ($v) => ! is_null($v)); $data = array_filter($applyInsert, fn ($v) => ! is_null($v));
$activityModel = new Activity(); $activityModel = new Activity;
$activityModel->forceFill($data); $activityModel->forceFill($data);
if (array_key_exists('created_at', $data)) { if (array_key_exists('created_at', $data)) {
// Preserve provided timestamps by disabling automatic timestamps for this save // Preserve provided timestamps by disabling automatic timestamps for this save
@ -2271,6 +2299,7 @@ private function upsertContractChain(Import $import, array $mapped, $mappings, b
if ($existing) { if ($existing) {
if ($historyImport) { if ($historyImport) {
$this->historyFoundContractIds[$existing->id] = true; $this->historyFoundContractIds[$existing->id] = true;
return ['action' => 'skipped_history', 'contract' => $existing, 'message' => 'Existing contract left unchanged (history import)']; return ['action' => 'skipped_history', 'contract' => $existing, 'message' => 'Existing contract left unchanged (history import)'];
} }
// 1) Prepare contract field changes (non-null) // 1) Prepare contract field changes (non-null)
@ -3090,8 +3119,8 @@ private function upsertAddress(int $personId, array $addrData, $mappings): array
if (mb_strlen($addressLine) < 3) { if (mb_strlen($addressLine) < 3) {
return ['action' => 'skipped', 'message' => 'Invalid address value']; return ['action' => 'skipped', 'message' => 'Invalid address value'];
} }
// Allow only basic address characters to avoid noisy special chars // Allow letters (incl. diacritics), numbers, and common separators
if (! preg_match('/^[A-Za-z0-9\\s\\.,\\-\\/\\#\\\'"\\(\\)&]+$/', $addressLine)) { if (! preg_match('/^[\\p{L}0-9\\s\\.,\\-\\/\\#\\\'"\\(\\)&]+$/u', $addressLine)) {
return ['action' => 'skipped', 'message' => 'Invalid address value']; return ['action' => 'skipped', 'message' => 'Invalid address value'];
} }
// Default country SLO if not provided // Default country SLO if not provided
@ -3343,3 +3372,6 @@ protected function attemptContractReactivation(Contract $contract, ?Authenticata
} }
} }
} }