Skip to content

Commit 9e2e6f9

Browse files
committed
Add more input validation in ServerController.
1 parent bbbd6be commit 9e2e6f9

File tree

2 files changed

+78
-2
lines changed

2 files changed

+78
-2
lines changed

solid/lib/Controller/ServerController.php

Lines changed: 16 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -156,6 +156,10 @@ public function authorize() {
156156
// return $result->addHeader('Access-Control-Allow-Origin', '*');
157157
}
158158

159+
if (! isset($_GET['client_id'])) {
160+
return new JSONResponse('Bad request, missing client_id', 400);
161+
}
162+
159163
if (isset($_GET['request'])) {
160164
$jwtConfig = Configuration::forSymmetricSigner(new Sha256(), InMemory::plainText($this->config->getPrivateKey()));
161165
try {
@@ -323,6 +327,11 @@ public function session() {
323327
*/
324328
public function token() {
325329
$request = \Laminas\Diactoros\ServerRequestFactory::fromGlobals($_SERVER, $_GET, $_POST, $_COOKIE, $_FILES);
330+
331+
if (!isset($request->getParsedBody()['grant_type'])) {
332+
return new JSONResponse('Bad request, grant_type is missing', 400);
333+
}
334+
326335
$grantType = $request->getParsedBody()['grant_type'];
327336
switch ($grantType) {
328337
case "authorization_code":
@@ -389,8 +398,13 @@ public function logout() {
389398
* @NoCSRFRequired
390399
*/
391400
public function register() {
392-
$clientData = file_get_contents('php://input');
393-
$clientData = json_decode($clientData, true);
401+
$postData = file_get_contents('php://input');
402+
$clientData = json_decode($postData, true);
403+
404+
if (! isset($clientData)) {
405+
return new JSONResponse("Missing client data", Http::STATUS_BAD_REQUEST);
406+
}
407+
394408
if (! isset($clientData['redirect_uris'])) {
395409
return new JSONResponse("Missing redirect URIs", Http::STATUS_BAD_REQUEST);
396410
}

solid/tests/Unit/Controller/ServerControllerTest.php

Lines changed: 62 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -119,13 +119,33 @@ public function testAuthorizeWithoutUser()
119119
$this->assertEquals($expected, $actual);
120120
}
121121

122+
/**
123+
* @testdox ServerController should return a 400 when asked to authorize with a user but without client_id
124+
*
125+
* @covers ::authorize
126+
*/
127+
public function testAuthorizeWithoutClientId()
128+
{
129+
$parameters = $this->createMockConstructorParameters();
130+
131+
$this->mockUserManager->method('userExists')->willReturn(true);
132+
133+
$controller = new ServerController(...array_values($parameters));
134+
135+
$actual = $controller->authorize();
136+
$expected = new JSONResponse('Bad request, missing client_id', Http::STATUS_BAD_REQUEST);
137+
138+
$this->assertEquals($expected, $actual);
139+
}
140+
122141
/**
123142
* @testdox ServerController should return a 400 when asked to authorize with a user but without valid token
124143
*
125144
* @covers ::authorize
126145
*/
127146
public function testAuthorizeWithoutValidToken()
128147
{
148+
$_GET['client_id'] = self::MOCK_CLIENT_ID;
129149
$_GET['response_type'] = 'mock-response-type';
130150

131151
$parameters = $this->createMockConstructorParameters();
@@ -277,12 +297,33 @@ public function testAuthorize()
277297
*
278298
* @covers ::register
279299
*/
300+
public function testRegisterWithoutClientData()
301+
{
302+
$parameters = $this->createMockConstructorParameters();
303+
304+
$controller = new ServerController(...array_values($parameters));
305+
306+
$actual = $controller->register();
307+
308+
$this->assertEquals(
309+
new JSONResponse('Missing client data', Http::STATUS_BAD_REQUEST),
310+
$actual
311+
);
312+
}
313+
314+
/**
315+
* @testdox ServerController should return a 400 when asked to register without redirect URIs
316+
*
317+
* @covers ::register
318+
*/
280319
public function testRegisterWithoutRedirectUris()
281320
{
282321
$parameters = $this->createMockConstructorParameters();
283322

284323
$controller = new ServerController(...$parameters);
285324

325+
self::$clientData = json_encode([]);
326+
286327
$actual = $controller->register();
287328

288329
$this->assertEquals(
@@ -335,6 +376,26 @@ public function testRegisterWithRedirectUris()
335376
$this->assertEquals($expected, $actual);
336377
}
337378

379+
public function testTokenWithoutGrantType()
380+
{
381+
$parameters = $this->createMockConstructorParameters();
382+
383+
$controller = new ServerController(...$parameters);
384+
385+
$tokenResponse = $controller->token();
386+
387+
$expected = $this->createExpectedResponse(Http::STATUS_BAD_REQUEST, 'Bad request, grant_type is missing');
388+
389+
$actual = [
390+
'data' => $tokenResponse->getData(),
391+
'headers' => $tokenResponse->getHeaders(),
392+
'status' => $tokenResponse->getStatus(),
393+
];
394+
unset($actual['headers']['X-Request-Id']);
395+
396+
$this->assertEquals($expected, $actual);
397+
}
398+
338399
/**
339400
* @testdox ServerController should consume Post, Server, and Session variables when generating a token
340401
*
@@ -344,6 +405,7 @@ public function testToken()
344405
{
345406
$_POST['client_id'] = self::MOCK_CLIENT_ID;
346407
$_POST['code'] = '';
408+
$_POST['grant_type'] = 'authorization_code';
347409
$_SERVER['HTTP_DPOP'] = 'mock dpop';
348410
$_SESSION['nonce'] = 'mock nonce';
349411

0 commit comments

Comments
 (0)