1f6fdd746SJonathan Jaubart<?php 2f6fdd746SJonathan Jaubart 3f6fdd746SJonathan Jaubart/** 4f6fdd746SJonathan Jaubart * webtrees: online genealogy 5d11be702SGreg Roach * Copyright (C) 2023 webtrees development team 6f6fdd746SJonathan Jaubart * This program is free software: you can redistribute it and/or modify 7f6fdd746SJonathan Jaubart * it under the terms of the GNU General Public License as published by 8f6fdd746SJonathan Jaubart * the Free Software Foundation, either version 3 of the License, or 9f6fdd746SJonathan Jaubart * (at your option) any later version. 10f6fdd746SJonathan Jaubart * This program is distributed in the hope that it will be useful, 11f6fdd746SJonathan Jaubart * but WITHOUT ANY WARRANTY; without even the implied warranty of 12f6fdd746SJonathan Jaubart * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13f6fdd746SJonathan Jaubart * GNU General Public License for more details. 14f6fdd746SJonathan Jaubart * You should have received a copy of the GNU General Public License 15f6fdd746SJonathan Jaubart * along with this program. If not, see <https://www.gnu.org/licenses/>. 16f6fdd746SJonathan Jaubart */ 17f6fdd746SJonathan Jaubart 18f6fdd746SJonathan Jaubartdeclare(strict_types=1); 19f6fdd746SJonathan Jaubart 20f6fdd746SJonathan Jaubartnamespace Fisharebest\Webtrees; 21f6fdd746SJonathan Jaubart 22a5f003cfSGreg Roachuse Aura\Router\Route; 23a5f003cfSGreg Roachuse Fisharebest\Webtrees\Contracts\UserInterface; 24f6fdd746SJonathan Jaubartuse Fisharebest\Webtrees\Http\Exceptions\HttpBadRequestException; 25202c018bSGreg Roachuse PHPUnit\Framework\Attributes\CoversClass; 26f507cef9SGreg Roachuse Psr\Http\Message\ServerRequestInterface; 27f6fdd746SJonathan Jaubart 28202c018bSGreg Roach#[CoversClass(Validator::class)] 29f6fdd746SJonathan Jaubartclass ValidatorTest extends TestCase 30f6fdd746SJonathan Jaubart{ 31a5f003cfSGreg Roach public function testAttributes(): void 32a5f003cfSGreg Roach { 3362ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 34a5f003cfSGreg Roach $request 35a5f003cfSGreg Roach ->method('getAttributes') 36a5f003cfSGreg Roach ->willReturn(['param' => 'test']); 37a5f003cfSGreg Roach 38a5f003cfSGreg Roach self::assertSame('test', Validator::attributes($request)->string('param')); 39a5f003cfSGreg Roach } 40a5f003cfSGreg Roach 41a5f003cfSGreg Roach public function testParsedBody(): void 42a5f003cfSGreg Roach { 4362ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 44a5f003cfSGreg Roach $request 45a5f003cfSGreg Roach ->method('getParsedBody') 46a5f003cfSGreg Roach ->willReturn(['param' => 'test']); 47a5f003cfSGreg Roach 48a5f003cfSGreg Roach self::assertSame('test', Validator::parsedBody($request)->string('param')); 49a5f003cfSGreg Roach } 50a5f003cfSGreg Roach 51a5f003cfSGreg Roach public function testQueryParams(): void 52a5f003cfSGreg Roach { 5362ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 54a5f003cfSGreg Roach $request 55a5f003cfSGreg Roach ->method('getQueryParams') 56a5f003cfSGreg Roach ->willReturn(['param' => 'test']); 57a5f003cfSGreg Roach 58a5f003cfSGreg Roach self::assertSame('test', Validator::queryParams($request)->string('param')); 59a5f003cfSGreg Roach } 60a5f003cfSGreg Roach 61a5f003cfSGreg Roach public function testServerParams(): void 62a5f003cfSGreg Roach { 6362ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 64a5f003cfSGreg Roach $request 65a5f003cfSGreg Roach ->method('getServerParams') 66a5f003cfSGreg Roach ->willReturn(['param' => 'test']); 67a5f003cfSGreg Roach 68a5f003cfSGreg Roach self::assertSame('test', Validator::serverParams($request)->string('param')); 69a5f003cfSGreg Roach } 70a5f003cfSGreg Roach 71a5f003cfSGreg Roach public function testNonUTF8QueryParameterName(): void 72a5f003cfSGreg Roach { 7362ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 74a5f003cfSGreg Roach $request 75a5f003cfSGreg Roach ->method('getQueryParams') 76a5f003cfSGreg Roach ->willReturn(["\xFF" => 'test']); 77a5f003cfSGreg Roach 78a5f003cfSGreg Roach $this->expectException(HttpBadRequestException::class); 79a5f003cfSGreg Roach 80a5f003cfSGreg Roach Validator::queryParams($request); 81a5f003cfSGreg Roach } 82a5f003cfSGreg Roach 83a5f003cfSGreg Roach public function testNonUTF8QueryParameterValue(): void 84a5f003cfSGreg Roach { 8562ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 86a5f003cfSGreg Roach $request 87a5f003cfSGreg Roach ->method('getQueryParams') 88a5f003cfSGreg Roach ->willReturn(['test' => "\xFF"]); 89a5f003cfSGreg Roach 90a5f003cfSGreg Roach $this->expectException(HttpBadRequestException::class); 91a5f003cfSGreg Roach 92a5f003cfSGreg Roach Validator::queryParams($request); 93a5f003cfSGreg Roach } 94a5f003cfSGreg Roach 95f6fdd746SJonathan Jaubart public function testRequiredArrayParameter(): void 96f6fdd746SJonathan Jaubart { 9762ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 98a5f003cfSGreg Roach $request 99a5f003cfSGreg Roach ->method('getQueryParams') 100a5f003cfSGreg Roach ->willReturn(['param' => ['test'], 'invalid' => 'not_array']); 101f6fdd746SJonathan Jaubart 102a5f003cfSGreg Roach self::assertSame(['test'], Validator::queryParams($request)->array('param')); 103f6fdd746SJonathan Jaubart 104f6fdd746SJonathan Jaubart $this->expectException(HttpBadRequestException::class); 105a5f003cfSGreg Roach 106a5f003cfSGreg Roach Validator::queryParams($request)->array('invalid'); 107a5f003cfSGreg Roach } 108a5f003cfSGreg Roach 109a5f003cfSGreg Roach public function testRequiredBooleanParameter(): void 110a5f003cfSGreg Roach { 11162ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 112a5f003cfSGreg Roach $request 113a5f003cfSGreg Roach ->method('getQueryParams') 114a5f003cfSGreg Roach ->willReturn([ 115a5f003cfSGreg Roach 'a' => '1', 116a5f003cfSGreg Roach 'b' => 'on', 117a5f003cfSGreg Roach 'c' => true, 118a5f003cfSGreg Roach 'd' => '0', 119a5f003cfSGreg Roach 'e' => '', 120a5f003cfSGreg Roach 'f' => false, 121a5f003cfSGreg Roach ]); 122a5f003cfSGreg Roach 123*a6d49169SGreg Roach self::assertTrue(Validator::queryParams($request)->boolean('a')); 124*a6d49169SGreg Roach self::assertTrue(Validator::queryParams($request)->boolean('b')); 125*a6d49169SGreg Roach self::assertTrue(Validator::queryParams($request)->boolean('c')); 126*a6d49169SGreg Roach self::assertFalse(Validator::queryParams($request)->boolean('d')); 127*a6d49169SGreg Roach self::assertFalse(Validator::queryParams($request)->boolean('e')); 128*a6d49169SGreg Roach self::assertFalse(Validator::queryParams($request)->boolean('f')); 129*a6d49169SGreg Roach self::assertFalse(Validator::queryParams($request)->boolean('g', false)); 130a5f003cfSGreg Roach 131a5f003cfSGreg Roach $this->expectException(HttpBadRequestException::class); 132a5f003cfSGreg Roach 133a5f003cfSGreg Roach Validator::queryParams($request)->boolean('h'); 134f6fdd746SJonathan Jaubart } 135f6fdd746SJonathan Jaubart 136f6fdd746SJonathan Jaubart public function testRequiredIntegerParameter(): void 137f6fdd746SJonathan Jaubart { 13862ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 139a5f003cfSGreg Roach $request 140a5f003cfSGreg Roach ->method('getQueryParams') 141a5f003cfSGreg Roach ->willReturn([ 14265625b93SGreg Roach 'int_type_positive' => 42, 14365625b93SGreg Roach 'int_type_negative' => -42, 14465625b93SGreg Roach 'string_type_positive' => '42', 14565625b93SGreg Roach 'string_type_negative' => '-42', 14665625b93SGreg Roach 'invalid' => 'not_int', 147a5f003cfSGreg Roach ]); 148f6fdd746SJonathan Jaubart 149a5f003cfSGreg Roach self::assertSame(42, Validator::queryParams($request)->integer('int_type_positive')); 150a5f003cfSGreg Roach self::assertSame(-42, Validator::queryParams($request)->integer('int_type_negative')); 151a5f003cfSGreg Roach self::assertSame(42, Validator::queryParams($request)->integer('string_type_positive')); 152a5f003cfSGreg Roach self::assertSame(-42, Validator::queryParams($request)->integer('string_type_negative')); 153f6fdd746SJonathan Jaubart 154f6fdd746SJonathan Jaubart $this->expectException(HttpBadRequestException::class); 155a5f003cfSGreg Roach 156a5f003cfSGreg Roach Validator::queryParams($request)->integer('invalid'); 157a5f003cfSGreg Roach } 158a5f003cfSGreg Roach 159a5f003cfSGreg Roach public function testRequiredRouteParameter(): void 160a5f003cfSGreg Roach { 16162ff2f18SGreg Roach $route = $this->createMock(Route::class); 162a5f003cfSGreg Roach 16362ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 164a5f003cfSGreg Roach $request 165a5f003cfSGreg Roach ->method('getQueryParams') 166a5f003cfSGreg Roach ->willReturn([ 167a5f003cfSGreg Roach 'valid-route' => $route, 168a5f003cfSGreg Roach 'not-route' => '', 169a5f003cfSGreg Roach ]); 170a5f003cfSGreg Roach 171a5f003cfSGreg Roach self::assertSame($route, Validator::queryParams($request)->route('valid-route')); 172a5f003cfSGreg Roach 173a5f003cfSGreg Roach $this->expectException(HttpBadRequestException::class); 174a5f003cfSGreg Roach 175a5f003cfSGreg Roach Validator::queryParams($request)->route('not-route'); 176f6fdd746SJonathan Jaubart } 177f6fdd746SJonathan Jaubart 178f6fdd746SJonathan Jaubart public function testRequiredStringParameter(): void 179f6fdd746SJonathan Jaubart { 18062ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 181a5f003cfSGreg Roach $request 182a5f003cfSGreg Roach ->method('getQueryParams') 183a5f003cfSGreg Roach ->willReturn(['param' => 'test', 'invalid' => ['not_string']]); 184f6fdd746SJonathan Jaubart 185a5f003cfSGreg Roach self::assertSame('test', Validator::queryParams($request)->string('param')); 186f6fdd746SJonathan Jaubart 187f6fdd746SJonathan Jaubart $this->expectException(HttpBadRequestException::class); 188a5f003cfSGreg Roach 189a5f003cfSGreg Roach Validator::queryParams($request)->string('invalid'); 190a5f003cfSGreg Roach } 191a5f003cfSGreg Roach 192a5f003cfSGreg Roach public function testRequiredTreeParameter(): void 193a5f003cfSGreg Roach { 19462ff2f18SGreg Roach $tree = $this->createMock(Tree::class); 195a5f003cfSGreg Roach 19662ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 197a5f003cfSGreg Roach $request 198a5f003cfSGreg Roach ->method('getQueryParams') 199a5f003cfSGreg Roach ->willReturn([ 200a5f003cfSGreg Roach 'valid-tree' => $tree, 201a5f003cfSGreg Roach 'not-tree' => '', 202a5f003cfSGreg Roach ]); 203a5f003cfSGreg Roach 204a5f003cfSGreg Roach self::assertSame($tree, Validator::queryParams($request)->tree('valid-tree')); 205a5f003cfSGreg Roach 206a5f003cfSGreg Roach $this->expectException(HttpBadRequestException::class); 207a5f003cfSGreg Roach 208a5f003cfSGreg Roach Validator::queryParams($request)->tree('no-tree'); 209a5f003cfSGreg Roach } 210a5f003cfSGreg Roach 211a5f003cfSGreg Roach public function testOptionalTreeParameter(): void 212a5f003cfSGreg Roach { 21362ff2f18SGreg Roach $tree = $this->createMock(Tree::class); 214a5f003cfSGreg Roach 21562ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 216a5f003cfSGreg Roach $request 217a5f003cfSGreg Roach ->method('getQueryParams') 218a5f003cfSGreg Roach ->willReturn([ 219a5f003cfSGreg Roach 'valid-tree' => $tree, 220a5f003cfSGreg Roach 'not-tree' => '', 221a5f003cfSGreg Roach ]); 222a5f003cfSGreg Roach 223a5f003cfSGreg Roach self::assertSame($tree, Validator::queryParams($request)->treeOptional('valid-tree')); 224*a6d49169SGreg Roach self::assertNull(Validator::queryParams($request)->treeOptional('missing-tree')); 225a5f003cfSGreg Roach 226a5f003cfSGreg Roach $this->expectException(HttpBadRequestException::class); 227a5f003cfSGreg Roach 228a5f003cfSGreg Roach Validator::queryParams($request)->treeOptional('not-tree'); 229a5f003cfSGreg Roach } 230a5f003cfSGreg Roach 231a5f003cfSGreg Roach public function testRequiredUserParameter(): void 232a5f003cfSGreg Roach { 23362ff2f18SGreg Roach $user = $this->createMock(UserInterface::class); 234a5f003cfSGreg Roach 23562ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 236a5f003cfSGreg Roach $request 237a5f003cfSGreg Roach ->method('getQueryParams') 238a5f003cfSGreg Roach ->willReturn([ 239a5f003cfSGreg Roach 'valid-user' => $user, 240a5f003cfSGreg Roach 'not-user' => '', 241a5f003cfSGreg Roach ]); 242a5f003cfSGreg Roach 243a5f003cfSGreg Roach self::assertSame($user, Validator::queryParams($request)->user('valid-user')); 244a5f003cfSGreg Roach 245a5f003cfSGreg Roach $this->expectException(HttpBadRequestException::class); 246a5f003cfSGreg Roach 247a5f003cfSGreg Roach Validator::queryParams($request)->user('not-user'); 248f6fdd746SJonathan Jaubart } 249f6fdd746SJonathan Jaubart 250f6fdd746SJonathan Jaubart public function testIsBetweenParameter(): void 251f6fdd746SJonathan Jaubart { 25262ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 253a5f003cfSGreg Roach $request 254a5f003cfSGreg Roach ->method('getQueryParams') 255a5f003cfSGreg Roach ->willReturn(['param' => '42', 'invalid' => '10', 'wrongtype' => 'not_integer']); 256f6fdd746SJonathan Jaubart 257a5f003cfSGreg Roach self::assertSame(42, Validator::queryParams($request)->isBetween(40, 45)->integer('param')); 258a5f003cfSGreg Roach self::assertSame(42, Validator::queryParams($request)->isBetween(40, 45)->integer('invalid', 42)); 259a5f003cfSGreg Roach self::assertSame(42, Validator::queryParams($request)->isBetween(40, 45)->integer('wrongtype', 42)); 260a5f003cfSGreg Roach } 261a5f003cfSGreg Roach 262a5f003cfSGreg Roach public function testIsInArray(): void 263a5f003cfSGreg Roach { 26462ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 265a5f003cfSGreg Roach $request 266a5f003cfSGreg Roach ->method('getQueryParams') 267a5f003cfSGreg Roach ->willReturn(['param' => 'foo']); 268a5f003cfSGreg Roach 269a5f003cfSGreg Roach self::assertSame('foo', Validator::queryParams($request)->isInArray(['foo', 'bar'])->string('param')); 270a5f003cfSGreg Roach 271a5f003cfSGreg Roach $this->expectException(HttpBadRequestException::class); 272a5f003cfSGreg Roach 273a5f003cfSGreg Roach Validator::queryParams($request)->isInArray(['baz'])->string('param'); 274a5f003cfSGreg Roach } 275a5f003cfSGreg Roach 276a5f003cfSGreg Roach public function testIsInArrayKeys(): void 277a5f003cfSGreg Roach { 27862ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 279a5f003cfSGreg Roach $request 280a5f003cfSGreg Roach ->method('getQueryParams') 281a5f003cfSGreg Roach ->willReturn(['param' => 'foo']); 282a5f003cfSGreg Roach 283a5f003cfSGreg Roach self::assertSame('foo', Validator::queryParams($request)->isInArrayKeys(['foo' => 1, 'bar' => 2])->string('param')); 284a5f003cfSGreg Roach 285a5f003cfSGreg Roach $this->expectException(HttpBadRequestException::class); 286a5f003cfSGreg Roach 287a5f003cfSGreg Roach Validator::queryParams($request)->isInArrayKeys(['baz' => 3])->string('param'); 288a5f003cfSGreg Roach } 289a5f003cfSGreg Roach 290a5f003cfSGreg Roach public function testIsNotEmpty(): void 291a5f003cfSGreg Roach { 29262ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 293a5f003cfSGreg Roach $request 294a5f003cfSGreg Roach ->method('getQueryParams') 295a5f003cfSGreg Roach ->willReturn(['empty' => '', 'not-empty' => 'foo']); 296a5f003cfSGreg Roach 297a5f003cfSGreg Roach self::assertSame('foo', Validator::queryParams($request)->isNotEmpty()->string('not-empty')); 298a5f003cfSGreg Roach 299a5f003cfSGreg Roach $this->expectException(HttpBadRequestException::class); 300a5f003cfSGreg Roach 301a5f003cfSGreg Roach Validator::queryParams($request)->isNotEmpty()->string('empty'); 302a5f003cfSGreg Roach } 303a5f003cfSGreg Roach 304a5f003cfSGreg Roach public function testIsTagParameter(): void 305a5f003cfSGreg Roach { 30662ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 307a5f003cfSGreg Roach $request 308a5f003cfSGreg Roach ->method('getQueryParams') 309a5f003cfSGreg Roach ->willReturn(['valid' => 'BIRT', 'invalid' => '@X1@']); 310a5f003cfSGreg Roach 311a5f003cfSGreg Roach self::assertSame('BIRT', Validator::queryParams($request)->isTag()->string('valid')); 312a5f003cfSGreg Roach 313a5f003cfSGreg Roach $this->expectException(HttpBadRequestException::class); 314a5f003cfSGreg Roach 315a5f003cfSGreg Roach Validator::queryParams($request)->isTag()->string('invalid'); 316f6fdd746SJonathan Jaubart } 317f6fdd746SJonathan Jaubart 318f6fdd746SJonathan Jaubart public function testIsXrefParameter(): void 319f6fdd746SJonathan Jaubart { 32062ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 321a5f003cfSGreg Roach $request 322a5f003cfSGreg Roach ->method('getQueryParams') 323a5f003cfSGreg Roach ->willReturn(['valid' => 'X1', 'invalid' => '@X1@', 'valid-array' => ['X1'], 'invalid-array' => ['@X1@']]); 324f6fdd746SJonathan Jaubart 325a5f003cfSGreg Roach self::assertSame('X1', Validator::queryParams($request)->isXref()->string('valid')); 326a5f003cfSGreg Roach self::assertSame(['X1'], Validator::queryParams($request)->isXref()->array('valid-array')); 327a5f003cfSGreg Roach self::assertSame([], Validator::queryParams($request)->isXref()->array('invalid-array')); 3281e60ebf4SGreg Roach 3291e60ebf4SGreg Roach $this->expectException(HttpBadRequestException::class); 330a5f003cfSGreg Roach 331a5f003cfSGreg Roach Validator::queryParams($request)->isXref()->string('invalid'); 332f6fdd746SJonathan Jaubart } 333f6fdd746SJonathan Jaubart 334f6fdd746SJonathan Jaubart public function testIsLocalUrlParameter(): void 335f6fdd746SJonathan Jaubart { 33662ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 337a5f003cfSGreg Roach $request 338a5f003cfSGreg Roach ->method('getAttribute') 339a5f003cfSGreg Roach ->with('base_url')->willReturn('http://example.local/wt'); 340a5f003cfSGreg Roach $request 341a5f003cfSGreg Roach ->method('getQueryParams') 342a5f003cfSGreg Roach ->willReturn(['param' => 'http://example.local/wt/page', 'noscheme' => '//example.local/wt/page']); 343f507cef9SGreg Roach 344a5f003cfSGreg Roach self::assertSame('http://example.local/wt/page', Validator::queryParams($request)->isLocalUrl()->string('param')); 345a5f003cfSGreg Roach self::assertSame('//example.local/wt/page', Validator::queryParams($request)->isLocalUrl()->string('noscheme')); 3461e60ebf4SGreg Roach } 3471e60ebf4SGreg Roach 3481e60ebf4SGreg Roach public function testIsLocalUrlParameterWrongScheme(): void 3491e60ebf4SGreg Roach { 35062ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 351a5f003cfSGreg Roach $request 352a5f003cfSGreg Roach ->method('getAttribute') 353a5f003cfSGreg Roach ->with('base_url') 354a5f003cfSGreg Roach ->willReturn('http://example.local/wt'); 355a5f003cfSGreg Roach $request 356a5f003cfSGreg Roach ->method('getQueryParams') 357a5f003cfSGreg Roach ->willReturn(['https' => 'https://example.local/wt/page']); 3581e60ebf4SGreg Roach 3591e60ebf4SGreg Roach $this->expectException(HttpBadRequestException::class); 360a5f003cfSGreg Roach 361a5f003cfSGreg Roach Validator::queryParams($request)->isLocalUrl()->string('https'); 3621e60ebf4SGreg Roach } 3631e60ebf4SGreg Roach 3641e60ebf4SGreg Roach public function testIsLocalUrlParameterWrongDomain(): void 3651e60ebf4SGreg Roach { 36662ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 367a5f003cfSGreg Roach $request 368a5f003cfSGreg Roach ->method('getAttribute') 369a5f003cfSGreg Roach ->with('base_url') 370a5f003cfSGreg Roach ->willReturn('http://example.local/wt'); 371a5f003cfSGreg Roach $request 372a5f003cfSGreg Roach ->method('getQueryParams') 373a5f003cfSGreg Roach ->willReturn(['invalid' => 'http://example.com/wt/page']); 3741e60ebf4SGreg Roach 3751e60ebf4SGreg Roach $this->expectException(HttpBadRequestException::class); 376a5f003cfSGreg Roach 377a5f003cfSGreg Roach Validator::queryParams($request)->isLocalUrl()->string('invalid'); 3781e60ebf4SGreg Roach } 3791e60ebf4SGreg Roach 3801e60ebf4SGreg Roach public function testIsLocalUrlParameterWrongType(): void 3811e60ebf4SGreg Roach { 38262ff2f18SGreg Roach $request = $this->createMock(ServerRequestInterface::class); 383a5f003cfSGreg Roach $request 384a5f003cfSGreg Roach ->method('getQueryParams') 385a5f003cfSGreg Roach ->willReturn(['wrongtype' => ['42']]); 386f6fdd746SJonathan Jaubart 3871e60ebf4SGreg Roach $this->expectException(HttpBadRequestException::class); 388f6fdd746SJonathan Jaubart 389a5f003cfSGreg Roach Validator::queryParams($request)->isLocalUrl()->isLocalUrl()->string('wrongtype'); 390f6fdd746SJonathan Jaubart } 391f6fdd746SJonathan Jaubart} 392