]> BookStack Code Mirror - bookstack/blob - tests/Auth/UserInviteTest.php
Updated minimum php version from 7.3 to 7.4
[bookstack] / tests / Auth / UserInviteTest.php
1 <?php
2
3 namespace Tests\Auth;
4
5 use BookStack\Auth\Access\UserInviteService;
6 use BookStack\Auth\User;
7 use BookStack\Notifications\UserInvite;
8 use Carbon\Carbon;
9 use Illuminate\Notifications\Messages\MailMessage;
10 use Illuminate\Support\Facades\DB;
11 use Illuminate\Support\Facades\Notification;
12 use Illuminate\Support\Str;
13 use Tests\TestCase;
14
15 class UserInviteTest extends TestCase
16 {
17     public function test_user_creation_creates_invite()
18     {
19         Notification::fake();
20         $admin = $this->getAdmin();
21
22         $email = Str::random(16) . '@example.com';
23         $resp = $this->actingAs($admin)->post('/settings/users/create', [
24             'name'        => 'Barry',
25             'email'       => $email,
26             'send_invite' => 'true',
27         ]);
28         $resp->assertRedirect('/settings/users');
29
30         $newUser = User::query()->where('email', '=', $email)->orderBy('id', 'desc')->first();
31
32         Notification::assertSentTo($newUser, UserInvite::class);
33         $this->assertDatabaseHas('user_invites', [
34             'user_id' => $newUser->id,
35         ]);
36     }
37
38     public function test_user_invite_sent_in_selected_language()
39     {
40         Notification::fake();
41         $admin = $this->getAdmin();
42
43         $email = Str::random(16) . '@example.com';
44         $resp = $this->actingAs($admin)->post('/settings/users/create', [
45             'name'        => 'Barry',
46             'email'       => $email,
47             'send_invite' => 'true',
48             'setting'     => [
49                 'language' => 'de',
50             ],
51         ]);
52         $resp->assertRedirect('/settings/users');
53
54         $newUser = User::query()->where('email', '=', $email)->orderBy('id', 'desc')->first();
55         Notification::assertSentTo($newUser, UserInvite::class, function ($notification, $channels, $notifiable) {
56             /** @var MailMessage $mail */
57             $mail = $notification->toMail($notifiable);
58
59             return 'Du wurdest eingeladen BookStack beizutreten!' === $mail->subject &&
60                 'Ein Konto wurde für Sie auf BookStack erstellt.' === $mail->greeting;
61         });
62     }
63
64     public function test_invite_set_password()
65     {
66         Notification::fake();
67         $user = $this->getViewer();
68         $inviteService = app(UserInviteService::class);
69
70         $inviteService->sendInvitation($user);
71         $token = DB::table('user_invites')->where('user_id', '=', $user->id)->first()->token;
72
73         $setPasswordPageResp = $this->get('/register/invite/' . $token);
74         $setPasswordPageResp->assertSuccessful();
75         $setPasswordPageResp->assertSee('Welcome to BookStack!');
76         $setPasswordPageResp->assertSee('Password');
77         $setPasswordPageResp->assertSee('Confirm Password');
78
79         $setPasswordResp = $this->followingRedirects()->post('/register/invite/' . $token, [
80             'password' => 'my test password',
81         ]);
82         $setPasswordResp->assertSee('Password set, you should now be able to login using your set password to access BookStack!');
83         $newPasswordValid = auth()->validate([
84             'email'    => $user->email,
85             'password' => 'my test password',
86         ]);
87         $this->assertTrue($newPasswordValid);
88         $this->assertDatabaseMissing('user_invites', [
89             'user_id' => $user->id,
90         ]);
91     }
92
93     public function test_invite_set_has_password_validation()
94     {
95         Notification::fake();
96         $user = $this->getViewer();
97         $inviteService = app(UserInviteService::class);
98
99         $inviteService->sendInvitation($user);
100         $token = DB::table('user_invites')->where('user_id', '=', $user->id)->first()->token;
101
102         $this->get('/register/invite/' . $token);
103         $shortPassword = $this->followingRedirects()->post('/register/invite/' . $token, [
104             'password' => 'mypassw',
105         ]);
106         $shortPassword->assertSee('The password must be at least 8 characters.');
107
108         $this->get('/register/invite/' . $token);
109         $noPassword = $this->followingRedirects()->post('/register/invite/' . $token, [
110             'password' => '',
111         ]);
112         $noPassword->assertSee('The password field is required.');
113
114         $this->assertDatabaseHas('user_invites', [
115             'user_id' => $user->id,
116         ]);
117     }
118
119     public function test_non_existent_invite_token_redirects_to_home()
120     {
121         $setPasswordPageResp = $this->get('/register/invite/' . Str::random(12));
122         $setPasswordPageResp->assertRedirect('/');
123
124         $setPasswordResp = $this->post('/register/invite/' . Str::random(12), ['password' => 'Password Test']);
125         $setPasswordResp->assertRedirect('/');
126     }
127
128     public function test_token_expires_after_two_weeks()
129     {
130         Notification::fake();
131         $user = $this->getViewer();
132         $inviteService = app(UserInviteService::class);
133
134         $inviteService->sendInvitation($user);
135         $tokenEntry = DB::table('user_invites')->where('user_id', '=', $user->id)->first();
136         DB::table('user_invites')->update(['created_at' => Carbon::now()->subDays(14)->subHour(1)]);
137
138         $setPasswordPageResp = $this->get('/register/invite/' . $tokenEntry->token);
139         $setPasswordPageResp->assertRedirect('/password/email');
140         $setPasswordPageResp->assertSessionHas('error', 'This invitation link has expired. You can instead try to reset your account password.');
141     }
142 }