tenant = Tenant::factory()->create(); $this->user = User::factory()->for($this->tenant)->create(); $this->actingAs($this->user); DB::statement('SET app.current_tenant_id = '.$this->tenant->id); $this->project = Project::factory()->for($this->tenant)->create(['name' => 'Окна Москва']); }); test('POST /api/deals/export требует auth', function () { auth()->logout(); $this->postJson('/api/deals/export', ['format' => 'csv'])->assertStatus(401); }); test('POST /api/deals/export csv возвращает сделки в диапазоне дат', function () { Deal::factory()->for($this->tenant)->for($this->project)->create([ 'phone' => '+7 999 111-11-11', 'received_at' => '2026-05-15 10:00:00', ]); Deal::factory()->for($this->tenant)->for($this->project)->create([ 'phone' => '+7 999 222-22-22', 'received_at' => '2026-05-25 10:00:00', ]); $r = $this->post('/api/deals/export', [ 'received_from' => '2026-05-14', 'received_to' => '2026-05-16', 'format' => 'csv', ]); $r->assertStatus(200); $r->assertHeader('content-type', 'text/csv; charset=utf-8'); $body = $r->streamedContent(); expect($body)->toContain('+7 999 111-11-11'); expect($body)->not->toContain('+7 999 222-22-22'); }); test('POST /api/deals/export xlsx отдаёт spreadsheet content-type', function () { Deal::factory()->for($this->tenant)->for($this->project)->create(['received_at' => '2026-05-15 10:00:00']); $r = $this->post('/api/deals/export', ['format' => 'xlsx']); $r->assertStatus(200); $r->assertHeader('content-type', 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet'); }); test('POST /api/deals/export не экспортирует чужой tenant (RLS)', function () { $other = Tenant::factory()->create(); DB::statement('SET app.current_tenant_id = '.$other->id); $foreignProject = Project::factory()->for($other)->create(); Deal::factory()->for($other)->for($foreignProject)->create(['phone' => '+7 900 000-00-00']); DB::statement('SET app.current_tenant_id = '.$this->tenant->id); $r = $this->post('/api/deals/export', ['format' => 'csv']); expect($r->streamedContent())->not->toContain('+7 900 000-00-00'); }); test('POST /api/deals/export 422 на неизвестный format', function () { $this->postJson('/api/deals/export', ['format' => 'pdf'])->assertStatus(422); }); test('POST /api/deals/export без format по умолчанию отдаёт CSV', function () { Deal::factory()->for($this->tenant)->for($this->project)->create(['received_at' => '2026-05-15 10:00:00']); $r = $this->post('/api/deals/export', []); $r->assertStatus(200); $r->assertHeader('content-type', 'text/csv; charset=utf-8'); });