seed(CityWorldSeeder::class); $city = City::query()->where('slug', 'city10')->first(); $this->assertNotNull($city); $this->assertTrue($city->is_active); $this->assertSame(4, $city->jobs()->count()); $user = User::factory()->create(['status' => User::STATUS_ACTIVE, 'is_active' => true]); $this->seed(CityWorldSeeder::class); $this->assertNotNull(Character::query()->where('user_id', $user->id)->first()); } /** * Migration backfills legacy is_active flags onto status. */ public function test_status_backfill_matches_is_active(): void { $this->seed(CityWorldSeeder::class); $active = User::where('is_active', true)->where('status', '!=', User::STATUS_ACTIVE)->count(); $this->assertSame(0, $active); } /** * The performance-tuned city delivers exactly 72 blocks (9 × 8) with * the matching road grid and bounds in the world payload. */ public function test_layout_has_72_blocks_after_performance_resize(): void { $this->seed(CityWorldSeeder::class); $user = User::factory()->create(['status' => User::STATUS_ACTIVE, 'is_active' => true]); Character::ensureForUser($user); $this->actingAs($user); $payload = $this->getJson('/city/data')->assertOk()->json(); $this->assertCount(72, $payload['layout']['blocks']); $zRoads = count(array_filter($payload['layout']['roads'], fn (array $r): bool => $r['axis'] === 'z')); $xRoads = count(array_filter($payload['layout']['roads'], fn (array $r): bool => $r['axis'] === 'x')); // Server payload: 10 vertical + 9 horizontal grid roads (the bridge // and north extension are appended client-side at build time). $this->assertSame(10, $zRoads); $this->assertSame(9, $xRoads); $this->assertEquals(-120, $payload['city']['bounds']['min_x']); $this->assertEquals(160, $payload['city']['bounds']['max_x']); $this->assertEquals(-120, $payload['city']['bounds']['min_z']); $this->assertEquals(120, $payload['city']['bounds']['max_z']); // The sparse plaza pattern (~1 in 4 cells) scales with the city. $this->assertGreaterThanOrEqual(10, count($payload['plazas'])); } }