create(['balance_rub' => '100000.00']); $project = Project::factory()->create([ 'tenant_id' => $tenant->id, 'signal_type' => 'site', 'signal_identifier' => 'backfill-city.ru', 'is_active' => true, ]); DB::statement("SET LOCAL app.current_tenant_id = '{$tenant->id}'"); $deal = Deal::create([ 'tenant_id' => $tenant->id, 'project_id' => $project->id, 'phone' => '79161234567', 'phones' => ['79161234567'], 'status' => 'new', 'received_at' => now(), 'subject_code' => $resolvedCode, 'city' => $city, ]); DB::statement("SELECT set_config('app.current_tenant_id', '0', true)"); $lead = SupplierLead::factory()->create([ 'platform' => 'B1', 'phone' => '79161234567', 'resolved_subject_code' => $resolvedCode, 'region_source' => $resolvedCode !== null ? 'dadata' : 'unknown', ]); DB::connection('pgsql_supplier')->table('supplier_lead_deliveries')->insert([ 'supplier_lead_id' => $lead->id, 'tenant_id' => $tenant->id, 'deal_id' => $deal->id, 'created_at' => now(), ]); return [$tenant->id, $deal->id]; } function dealCity(int $dealId): ?string { // BYPASSRLS чтение (как и сам бэкфилл) — без tenant-контекста. return DB::connection('pgsql_supplier')->table('deals')->where('id', $dealId)->value('city'); } it('backfills deal city from the lead resolved region code', function (): void { [, $dealId] = seedDealWithResolvedLead(29); // 29 → Красноярский край $this->artisan('deals:backfill-region-city')->assertSuccessful(); expect(dealCity($dealId))->toBe('Красноярский край'); }); it('does not touch deals that already have a city', function (): void { [, $dealId] = seedDealWithResolvedLead(29, city: 'Уже стоит'); $this->artisan('deals:backfill-region-city')->assertSuccessful(); expect(dealCity($dealId))->toBe('Уже стоит'); }); it('dry-run reports candidates without writing', function (): void { [, $dealId] = seedDealWithResolvedLead(29); $this->artisan('deals:backfill-region-city', ['--dry-run' => true])->assertSuccessful(); expect(dealCity($dealId))->toBeNull(); }); it('leaves city null when the lead has no resolved region', function (): void { [, $dealId] = seedDealWithResolvedLead(null); $this->artisan('deals:backfill-region-city')->assertSuccessful(); expect(dealCity($dealId))->toBeNull(); });