1<?php
2
3// Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the GNU Affero General Public License v3.0.
4// See the LICENCE file in the repository root for full licence text.
5
6namespace Tests\Controllers\InterOp\Multiplayer;
7
8use App\Models\Beatmap;
9use App\Models\Chat\UserChannel;
10use App\Models\Multiplayer\Room;
11use App\Models\User;
12use Carbon\CarbonImmutable;
13use Tests\TestCase;
14
15class RoomsControllerTest extends TestCase
16{
17 private static function startRoomParams(): array
18 {
19 $beatmap = Beatmap::factory()->create();
20
21 return [
22 'ends_at' => CarbonImmutable::now()->addHours(1),
23 'name' => 'test room',
24 'type' => Room::REALTIME_DEFAULT_TYPE,
25 'playlist' => [[
26 'beatmap_id' => $beatmap->getKey(),
27 'ruleset_id' => $beatmap->playmode,
28 ]],
29 ];
30 }
31
32 public function testJoin(): void
33 {
34 $room = (new Room())->startGame(User::factory()->create(), static::startRoomParams());
35 $user = User::factory()->create();
36
37 $this->expectCountChange(fn () => UserChannel::count(), 1);
38
39 $this->withInterOpHeader(
40 route('interop.multiplayer.rooms.join', [
41 'room' => $room->getKey(),
42 'user' => $user->getKey(),
43 ]),
44 fn ($url) => $this->put($url),
45 )->assertSuccessful();
46 }
47
48 public function testJoinWithPassword(): void
49 {
50 $room = (new Room())->startGame(User::factory()->create(), [
51 ...static::startRoomParams(),
52 'password' => 'hunter2',
53 ]);
54 $user = User::factory()->create();
55
56 $this->expectCountChange(fn () => UserChannel::count(), 1);
57
58 $this->withInterOpHeader(
59 route('interop.multiplayer.rooms.join', [
60 'room' => $room->getKey(),
61 'user' => $user->getKey(),
62 ]),
63 fn ($url) => $this->put($url, ['password' => 'hunter2']),
64 )->assertSuccessful();
65 }
66
67 public function testJoinWithPasswordInvalid(): void
68 {
69 $room = (new Room())->startGame(User::factory()->create(), [
70 ...static::startRoomParams(),
71 'password' => 'hunter2',
72 ]);
73 $user = User::factory()->create();
74
75 $this->expectCountChange(fn () => UserChannel::count(), 0);
76
77 $this->withInterOpHeader(
78 route('interop.multiplayer.rooms.join', [
79 'room' => $room->getKey(),
80 'user' => $user->getKey(),
81 ]),
82 fn ($url) => $this->put($url, ['password' => '*******']),
83 )->assertStatus(403);
84 }
85
86 public function testStore(): void
87 {
88 $beatmap = Beatmap::factory()->create();
89 $params = [
90 ...static::startRoomParams(),
91 'user_id' => User::factory()->create()->getKey(),
92 ];
93
94 $this->expectCountChange(fn () => Room::count(), 1);
95
96 $this->withInterOpHeader(
97 route('interop.multiplayer.rooms.store'),
98 fn ($url) => $this->post($url, $params),
99 )->assertSuccessful();
100 }
101}