<?php

declare(strict_types=1);

namespace App\Console\Commands;

use App\Support\RussianRegions;
use Illuminate\Console\Command;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Facades\Log;

/**
 * Одноразовый бэкфилл: проставляет deals.city (имя субъекта) у уже существующих сделок,
 * у которых city ещё пуст, по resolved_subject_code связанного лида
 * (deals → supplier_lead_deliveries → supplier_leads). Идемпотентно (только city IS NULL).
 *
 * Запускается через .github/workflows/artisan-run.yml (mutating-whitelist, confirm_apply).
 * Парная правка для RouteSupplierLeadJob, который заполняет city у новых сделок.
 */
final class DealsBackfillRegionCityCommand extends Command
{
    protected $signature = 'deals:backfill-region-city {--dry-run : Только посчитать, ничего не записывать}';

    protected $description = 'Дозаполнить deals.city именем региона по resolved_subject_code лида (одноразовый бэкфилл)';

    public function handle(): int
    {
        $dryRun = (bool) $this->option('dry-run');
        // BYPASSRLS-роль: бэкфилл идёт по всем тенантам без SET app.current_tenant_id.
        $conn = DB::connection('pgsql_supplier');
        $map = RussianRegions::CODE_TO_NAME;

        $rows = $conn->table('deals')
            ->join('supplier_lead_deliveries as dlv', 'dlv.deal_id', '=', 'deals.id')
            ->join('supplier_leads as sl', 'sl.id', '=', 'dlv.supplier_lead_id')
            ->whereNull('deals.city')
            ->whereNotNull('sl.resolved_subject_code')
            ->select('deals.id', 'deals.received_at', 'sl.resolved_subject_code')
            ->get();

        $seen = [];
        $updated = 0;
        foreach ($rows as $r) {
            $dealId = (int) $r->id;
            if (isset($seen[$dealId])) {
                continue; // у сделки несколько доставок — обрабатываем один раз
            }
            $seen[$dealId] = true;

            $name = $map[(int) $r->resolved_subject_code] ?? null;
            if ($name === null) {
                continue; // код вне справочника 1..89 — пропускаем
            }

            if (! $dryRun) {
                $conn->table('deals')
                    ->where('id', $dealId)
                    ->where('received_at', $r->received_at) // partition key
                    ->whereNull('city') // идемпотентный страж
                    ->update(['city' => $name]);
            }
            $updated++;
        }

        $prefix = $dryRun ? '[dry-run] ' : '';
        $this->info("{$prefix}deals.city backfill: {$updated} обновлено из ".count($seen).' кандидатов.');
        Log::info('deals.backfill_region_city', [
            'updated' => $updated,
            'candidates' => count($seen),
            'dry_run' => $dryRun,
        ]);

        return self::SUCCESS;
    }
}
