Skip to content

Instantly share code, notes, and snippets.

@stefnats

stefnats/0.md Secret

Forked from adamwathan/0.md
Last active November 18, 2020 10:29
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save stefnats/5c68a77aa17c50903af29dfcafde1b0a to your computer and use it in GitHub Desktop.
Save stefnats/5c68a77aa17c50903af29dfcafde1b0a to your computer and use it in GitHub Desktop.
Disable exception handling in Laravel acceptance tests

Just a quick helper method you can add to your base TestCase to make it easy to toggle exception handling on the fly. Improved a little bit from the sloppier version I used in the screencast :)

Update 2016-11-09:

At some point since I originally shared this snippet and the accompanying screencast, Laravel started binding App\Exceptions\Handler under the Illuminate\Contracts\Debug\ExceptionHandler interface instead of the concrete class, so I've updated the files below to account for that.

Update 2020-11-18

@stefnats made some further improvements to disable throwing exception handling on

  • ModelNotFoundException / NotFoundHttpException -> return HTTP 404 instead
  • UnauthorizedHttpException -> return HTTP 401 instead
  • AuthenticationException -> return HTTP 401 instead
  • ValidationException -> return default response with HTTP 422 instead

This prevents common test cases from failing or being marked as E in the php testsuite, for example when you want to test for not existent resources

<?php
use App\Exceptions\Handler;
use Illuminate\Contracts\Debug\ExceptionHandler;
class TestCase extends Illuminate\Foundation\Testing\TestCase
{
// Framework-supplied test case methods snipped for brevity
// Use this version if you're on PHP 7
protected function disableExceptionHandling()
{
$this->app->instance(ExceptionHandler::class, new class extends Handler {
public function __construct() {}
public function report(Exception $e)
{
// no-op
}
public function render($request, Exception $e) {
if ($e instanceof ModelNotFoundException || $e instanceof NotFoundHttpException) {
return new Response(null, Response::HTTP_NOT_FOUND);
}
if ($e instanceof UnauthorizedHttpException) {
return new Response(null, Response::HTTP_UNAUTHORIZED);
}
if ($e instanceof AuthenticationException) {
return new Response(null, Response::HTTP_UNAUTHORIZED);
}
if ($e instanceof ValidationException) {
return parent::render($request, $e);
}
throw $e;
}
});
}
}
<?php
use App\Exceptions\Handler;
use Illuminate\Contracts\Debug\ExceptionHandler;
class TestCase extends Illuminate\Foundation\Testing\TestCase
{
// Framework-supplied test case methods snipped for brevity
// Use this version if you're on PHP 5
protected function disableExceptionHandling()
{
app()->instance(ExceptionHandler::class, new PassThroughHandler);
}
}
class PassThroughHandler extends Handler
{
public function __construct() {}
public function report(Exception $e)
{
// no-op
}
public function render($request, Exception $e)
{
if ($e instanceof ModelNotFoundException || $e instanceof NotFoundHttpException) {
return new Response(null, Response::HTTP_NOT_FOUND);
}
if ($e instanceof UnauthorizedHttpException) {
return new Response(null, Response::HTTP_UNAUTHORIZED);
}
if ($e instanceof AuthenticationException) {
return new Response(null, Response::HTTP_UNAUTHORIZED);
}
if ($e instanceof ValidationException) {
return parent::render($request, $e);
}
throw $e;
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment