for($this->tenant) ->create([ 'tenant_id' => $this->tenant->id, 'name' => 'Package-less Event', 'slug' => 'package-less-event', ]); $response = $this->authenticatedRequest('GET', '/api/v1/tenant/events'); $response->assertOk(); $payload = $response->json('data'); $this->assertNotEmpty($payload, 'Expected at least one event in the response'); $matchingEvent = collect($payload)->firstWhere('id', $event->id); $this->assertNotNull($matchingEvent, 'Created event should be present in response payload'); $this->assertNull($matchingEvent['package'], 'Events without package should return null package data'); } public function test_index_includes_package_details_when_available(): void { $package = Package::factory()->create([ 'type' => 'endcustomer', 'name' => 'Classic', 'name_translations' => [ 'de' => 'Classic', 'en' => 'Classic', ], 'price' => 59, 'gallery_days' => 45, ]); $event = Event::factory() ->for($this->tenant) ->create([ 'tenant_id' => $this->tenant->id, 'name' => 'Packaged Event', 'slug' => 'packaged-event', ]); EventPackage::create([ 'event_id' => $event->id, 'package_id' => $package->id, 'purchased_price' => $package->price, 'purchased_at' => Carbon::now()->subDay(), 'gallery_expires_at' => Carbon::now()->addDays($package->gallery_days ?? 30), 'used_photos' => 0, 'used_guests' => 0, ]); $response = $this->authenticatedRequest('GET', '/api/v1/tenant/events'); $response->assertOk(); $payload = collect($response->json('data')); $matchingEvent = $payload->firstWhere('id', $event->id); $this->assertNotNull($matchingEvent, 'Packaged event should be present in response payload'); $this->assertIsArray($matchingEvent['package']); $this->assertSame($package->id, $matchingEvent['package']['id']); $this->assertSame('Classic', $matchingEvent['package']['name']); $this->assertSame('59.00', $matchingEvent['package']['price']); } public function test_index_scopes_events_to_authenticated_tenant(): void { $foreignTenant = Tenant::factory()->create(); Event::factory()->for($foreignTenant)->create([ 'name' => 'Foreign Event', 'slug' => 'foreign-event', ]); $ownEvent = Event::factory()->for($this->tenant)->create([ 'name' => 'Own Event', 'slug' => 'own-event', ]); $response = $this->authenticatedRequest('GET', '/api/v1/tenant/events'); $response->assertOk(); $payload = collect($response->json('data')); $this->assertTrue($payload->pluck('id')->contains($ownEvent->id), 'Authenticated tenant should see own event.'); $this->assertFalse($payload->pluck('slug')->contains('foreign-event'), 'Events from other tenants must be filtered out.'); } public function test_index_handles_event_package_without_package_model(): void { $event = Event::factory()->for($this->tenant)->create([ 'name' => 'Legacy Event', 'slug' => 'legacy-event', ]); $package = Package::factory()->create([ 'type' => 'endcustomer', 'price' => 49, ]); EventPackage::create([ 'event_id' => $event->id, 'package_id' => $package->id, 'purchased_price' => $package->price, 'purchased_at' => Carbon::now()->subDays(5), 'gallery_expires_at' => Carbon::now()->addDays(15), 'used_photos' => 10, 'used_guests' => 25, ]); $package->delete(); $response = $this->authenticatedRequest('GET', '/api/v1/tenant/events'); $response->assertOk(); $matchingEvent = collect($response->json('data'))->firstWhere('id', $event->id); $this->assertNotNull($matchingEvent, 'Event should still be returned even if package record is missing.'); $this->assertIsArray($matchingEvent['package'], 'Package payload should provide fallback data when relation is missing.'); $this->assertSame($package->id, $matchingEvent['package']['id']); $this->assertSame((string) $package->price, $matchingEvent['package']['price']); } }