139 lines
4.9 KiB
PHP
139 lines
4.9 KiB
PHP
<?php
|
||
|
||
namespace App\Jobs;
|
||
|
||
use Illuminate\Bus\Queueable;
|
||
use Illuminate\Contracts\Queue\ShouldQueue;
|
||
use Illuminate\Foundation\Bus\Dispatchable;
|
||
use Illuminate\Queue\InteractsWithQueue;
|
||
use Illuminate\Queue\SerializesModels;
|
||
use Illuminate\Support\Facades\DB;
|
||
use Illuminate\Support\Facades\Log;
|
||
|
||
class UpdateHandoverDatesJob implements ShouldQueue
|
||
{
|
||
use Dispatchable, InteractsWithQueue, Queueable, SerializesModels;
|
||
|
||
protected $folderDates;
|
||
protected $registerColumnPath;
|
||
|
||
/**
|
||
* Create a new job instance.
|
||
*
|
||
* @param array $folderDates
|
||
* @param string $registerColumnPath
|
||
*/
|
||
public function __construct(array $folderDates, string $registerColumnPath)
|
||
{
|
||
$this->folderDates = $folderDates;
|
||
$this->registerColumnPath = $registerColumnPath;
|
||
}
|
||
|
||
/**
|
||
* Execute the job.
|
||
*
|
||
* @return void
|
||
*/
|
||
public function handle()
|
||
{
|
||
try {
|
||
Log::info('UpdateHandoverDatesJob started', [
|
||
'folder_count' => count($this->folderDates),
|
||
'register_column_path' => $this->registerColumnPath
|
||
]);
|
||
|
||
$startTime = microtime(true);
|
||
$updatedCount = 0;
|
||
|
||
// Batch size için küçük gruplar halinde işle
|
||
$batchSize = 100;
|
||
$folderBatches = array_chunk($this->folderDates, $batchSize, true);
|
||
|
||
foreach ($folderBatches as $batch) {
|
||
$cases = [];
|
||
$revisionCases = [];
|
||
$projectNames = [];
|
||
|
||
foreach ($batch as $projectName => $folderDate) {
|
||
$folderDateFormatted = date('Y-m-d', strtotime($folderDate));
|
||
|
||
// Tarih formatını doğrula
|
||
if (!$folderDateFormatted || $folderDateFormatted === '1970-01-01') {
|
||
Log::warning("Invalid date format for project: {$projectName}, date: {$folderDate}");
|
||
continue;
|
||
}
|
||
|
||
// SQL injection'ı önlemek için project name'i escape et
|
||
$escapedProjectName = addslashes($projectName);
|
||
$projectNames[] = $escapedProjectName;
|
||
|
||
// CASE statements için hazırla
|
||
$cases[] = "WHEN project = '{$escapedProjectName}' THEN '{$folderDateFormatted}'";
|
||
$revisionCases[] = "WHEN project = '{$escapedProjectName}' AND revision_date IS NULL THEN '{$folderDateFormatted}'";
|
||
}
|
||
|
||
if (!empty($projectNames)) {
|
||
// Tek sorguda birden fazla project'i güncelle
|
||
$caseStatement = implode(' ', $cases);
|
||
$revisionCaseStatement = implode(' ', $revisionCases);
|
||
|
||
$projectList = "'" . implode("','", $projectNames) . "'";
|
||
|
||
$affected = DB::update("
|
||
UPDATE handovers
|
||
SET
|
||
created_date = CASE {$caseStatement} ELSE created_date END,
|
||
revision_date = CASE
|
||
{$revisionCaseStatement}
|
||
ELSE revision_date
|
||
END,
|
||
updated_at = NOW()
|
||
WHERE project IN ({$projectList})
|
||
");
|
||
|
||
$updatedCount += $affected;
|
||
|
||
Log::info("Processed batch", [
|
||
'projects_in_batch' => count($projectNames),
|
||
'affected_rows' => $affected
|
||
]);
|
||
}
|
||
|
||
// Her batch'ten sonra kısa bir mola (memory ve CPU için)
|
||
usleep(10000); // 10ms mola
|
||
}
|
||
|
||
$endTime = microtime(true);
|
||
$executionTime = round($endTime - $startTime, 2);
|
||
|
||
Log::info('UpdateHandoverDatesJob completed successfully', [
|
||
'total_updated_records' => $updatedCount,
|
||
'execution_time_seconds' => $executionTime,
|
||
'average_time_per_record' => $updatedCount > 0 ? round($executionTime / $updatedCount, 4) : 0
|
||
]);
|
||
|
||
} catch (\Exception $e) {
|
||
Log::error('UpdateHandoverDatesJob failed', [
|
||
'error' => $e->getMessage(),
|
||
'trace' => $e->getTraceAsString()
|
||
]);
|
||
|
||
// Job'ı tekrar queue'ya atmak için exception'ı yeniden fırlat
|
||
throw $e;
|
||
}
|
||
}
|
||
|
||
/**
|
||
* Handle a job failure.
|
||
*
|
||
* @param \Throwable $exception
|
||
* @return void
|
||
*/
|
||
public function failed(\Throwable $exception)
|
||
{
|
||
Log::error('UpdateHandoverDatesJob permanently failed', [
|
||
'error' => $exception->getMessage(),
|
||
'folder_dates_count' => count($this->folderDates)
|
||
]);
|
||
}
|
||
}
|