xref: /webtrees/tests/app/Services/RateLimitServiceTest.php (revision 5a8afed46297e8105e3e5a33ce37e6a8e88bc79d)
1<?php
2
3/**
4 * webtrees: online genealogy
5 * Copyright (C) 2023 webtrees development team
6 * This program is free software: you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation, either version 3 of the License, or
9 * (at your option) any later version.
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 * You should have received a copy of the GNU General Public License
15 * along with this program. If not, see <https://www.gnu.org/licenses/>.
16 */
17
18declare(strict_types=1);
19
20namespace Fisharebest\Webtrees\Services;
21
22use Fisharebest\Webtrees\GuestUser;
23use Fisharebest\Webtrees\Http\Exceptions\HttpTooManyRequestsException;
24use Fisharebest\Webtrees\TestCase;
25use LogicException;
26
27use PHPUnit\Framework\Attributes\CoversClass;
28
29use function explode;
30use function implode;
31use function range;
32use function time;
33
34#[CoversClass(RateLimitService::class)]
35class RateLimitServiceTest extends TestCase
36{
37    public function testTooMuchHistory(): void
38    {
39        $rate_limit_service = new RateLimitService();
40
41        $user = new GuestUser();
42
43        $this->expectException(LogicException::class);
44
45        $rate_limit_service->limitRateForUser($user, 1000, 30, 'rate-limit');
46    }
47
48    public function testLimitNotReached(): void
49    {
50        $rate_limit_service = new RateLimitService();
51
52        $user = new GuestUser();
53
54        $rate_limit_service->limitRateForUser($user, 3, 30, 'rate-limit');
55        $history = $user->getPreference('rate-limit');
56        static::assertCount(1, explode(',', $history));
57
58        $rate_limit_service->limitRateForUser($user, 3, 30, 'rate-limit');
59        $history = $user->getPreference('rate-limit');
60        static::assertCount(2, explode(',', $history));
61
62        $rate_limit_service->limitRateForUser($user, 3, 30, 'rate-limit');
63        $history = $user->getPreference('rate-limit');
64        static::assertCount(3, explode(',', $history));
65    }
66
67    public function testOldEventsIgnored(): void
68    {
69        $rate_limit_service = new RateLimitService();
70
71        $user = new GuestUser();
72
73        $history = implode(',', range(time() - 35, time() - 31));
74        $user->setPreference('rate-limit', $history);
75
76        $rate_limit_service->limitRateForUser($user, 5, 30, 'rate-limit');
77        $history = $user->getPreference('rate-limit');
78        static::assertCount(6, explode(',', $history));
79    }
80
81    public function testLimitReached(): void
82    {
83        $rate_limit_service = new RateLimitService();
84
85        $user = new GuestUser();
86
87        $history = implode(',', range(time() - 5, time() - 1));
88        $user->setPreference('rate-limit', $history);
89
90        $this->expectException(HttpTooManyRequestsException::class);
91        $rate_limit_service->limitRateForUser($user, 5, 30, 'rate-limit');
92    }
93}
94