Skip to content

Commit

Permalink
Merge pull request #77 from bedita/feat/json-error
Browse files Browse the repository at this point in the history
Show JSON error response on `application/json` Accept
  • Loading branch information
batopa authored Oct 24, 2022
2 parents ca49abd + 37b5ae0 commit fccdf63
Show file tree
Hide file tree
Showing 2 changed files with 46 additions and 4 deletions.
18 changes: 16 additions & 2 deletions src/Error/ExceptionRenderer.php
Original file line number Diff line number Diff line change
Expand Up @@ -16,15 +16,16 @@
namespace BEdita\WebTools\Error;

use BEdita\SDK\BEditaClientException;
use Cake\Error\ExceptionRenderer as CakeExceptionRenderer;
use Cake\Controller\Controller;
use Cake\Error\Renderer\WebExceptionRenderer;
use Cake\Http\Response;
use Cake\Log\LogTrait;

/**
* Custom exception renderer class.
* Handle with templates 500 and 400 (for status code < 500).
*/
class ExceptionRenderer extends CakeExceptionRenderer
class ExceptionRenderer extends WebExceptionRenderer
{
use LogTrait;

Expand All @@ -41,6 +42,19 @@ protected function _template(\Throwable $exception, string $method, int $code):
return $this->template = $template;
}

/**
* @inheritDoc
*/
protected function _getController(): Controller
{
$controller = parent::_getController();
if ($this->request && $this->request->is('json')) {
$controller->viewBuilder()->setClassName('Json');
}

return $controller;
}

/**
* {@inheritDoc}
*
Expand Down
32 changes: 30 additions & 2 deletions tests/TestCase/Error/ExceptionRendererTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@
use Cake\Event\EventManager;
use Cake\Http\Exception\InternalErrorException;
use Cake\Http\Exception\NotFoundException;
use Cake\Http\ServerRequest;
use Cake\TestSuite\TestCase;
use Cake\View\View;
use TestApp\Controller\TestController;
Expand All @@ -35,11 +36,13 @@ class ExceptionRendererTest extends TestCase
/**
* Get Extension class with utility methods use in tests
*
* @param \Throwable $exception Exception.
* @param \Cake\Http\ServerRequest|null $request The request if this is set it will be used
* @return ExceptionRenderer
*/
protected function extensionClass(Throwable $error)
protected function extensionClass(Throwable $error, ?ServerRequest $request = null)
{
return new class ($error) extends ExceptionRenderer
return new class ($error, $request) extends ExceptionRenderer
{
public function getTemplate()
{
Expand Down Expand Up @@ -182,4 +185,29 @@ public function testOutputMessageSafeFallback()
$body = (string)$response->getBody();
static::assertStringContainsString($expected, $body);
}

/**
* Test `_getController` method with `application/json` Accept header
*
* @return void
* @covers ::_getController()
*/
public function testControllerJsonResponse(): void
{
$request = (new ServerRequest())->withHeader('Accept', 'application/json');
$renderer = $this->extensionClass(new NotFoundException(), $request);
$response = $renderer->render();

$body = (string)$response->getBody();
$error = json_decode($body, true);
$jsonErr = json_last_error();
static::assertEquals(JSON_ERROR_NONE, $jsonErr);
unset($error['file'], $error['line']);
$expected = [
'message' => 'Not Found',
'url' => '/',
'code' => 404,
];
static::assertEquals($expected, $error);
}
}

0 comments on commit fccdf63

Please sign in to comment.