Files
onboard/app/Console/Commands/AutofillDutyReports.php
brusnitsyn f163b95663 2026.06.8
2026-06-18 17:45:41 +09:00

100 lines
4.0 KiB
PHP
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<?php
namespace App\Console\Commands;
use App\Models\Department;
use App\Models\ReportDuty;
use App\Models\User;
use App\Services\DateRangeService;
use App\Services\DutyReportService;
use Illuminate\Console\Command;
use Illuminate\Support\Carbon;
use Illuminate\Support\Facades\Log;
use Symfony\Component\Console\Command\Command as CommandAlias;
use Throwable;
class AutofillDutyReports extends Command
{
protected $signature = 'duty:autofill
{--date= : Дата смены (YYYY-MM-DD). По умолчанию сегодня (смена вчера 09:00 → сегодня 09:00)}
{--user= : ID пользователя для аудита. По умолчанию DUTY_AUTOFILL_USER_ID или первый пользователь}
{--dry-run : Не писать в БД, только показать, для каких отделений нет отчёта}';
protected $description = 'Создаёт суточные отчёты для отделений, у которых нет отчёта за текущую смену';
public function __construct(
protected DutyReportService $reportService,
protected DateRangeService $dateRangeService
) {
parent::__construct();
}
public function handle(): int
{
$tz = config('app.timezone', 'Europe/Moscow');
$date = Carbon::parse($this->option('date') ?: now($tz)->format('Y-m-d'), $tz);
// Пользователь для аудита
$userId = $this->option('user') ?: env('DUTY_AUTOFILL_USER_ID');
$user = $userId ? User::find($userId) : User::orderBy('id')->first();
if (! $user) {
$this->error('Не найден пользователь для аудита (укажите --user или DUTY_AUTOFILL_USER_ID).');
return CommandAlias::FAILURE;
}
// Смена: вчера 09:00 → сегодня 09:00 (для date = сегодня)
$dateRange = $this->dateRangeService->createDateRangeForDate($date, $user);
$periodStart = $dateRange->startDateRaw;
$periodEnd = $dateRange->endDateRaw;
$departments = Department::orderBy('department_id')->get();
$this->info("Смена: {$periodStart}{$periodEnd} ({$tz})");
$this->info("Аудит: пользователь #{$user->id}");
if ($this->option('dry-run')) {
$this->warn('Режим DRY RUN — без записи');
}
$created = 0; $skipped = 0; $errors = 0;
foreach ($departments as $dept) {
$exists = ReportDuty::where('rf_department_id', $dept->department_id)
->where('period_start', $periodStart)
->where('period_end', $periodEnd)
->exists();
if ($exists) {
$skipped++;
continue;
}
if ($this->option('dry-run')) {
$this->line(" нет отчёта: #{$dept->department_id} ".($dept->name_short ?? ''));
$created++;
continue;
}
try {
$report = $this->reportService->saveReport($dateRange, $user->id, 0, $dept->department_id);
$stats = $this->reportService->saveSnapshot($dateRange, $report, $dept->rf_mis_department_id, $user->id);
$this->reportService->saveMetrics($stats, $report);
$created++;
} catch (Throwable $e) {
$errors++;
Log::error('DutyAutofill', [
'department_id' => $dept->department_id,
'period_start' => $periodStart,
'period_end' => $periodEnd,
'error' => $e->getMessage(),
]);
$this->error("[#{$dept->department_id}] {$e->getMessage()}");
}
}
$this->newLine();
$this->info("Готово. Создано: {$created} | Уже было: {$skipped} | Ошибок: {$errors}");
return $errors > 0 ? CommandAlias::FAILURE : CommandAlias::SUCCESS;
}
}