From ca47f0bd138e45c0b55d5b7852a275497239dfae Mon Sep 17 00:00:00 2001 From: Sjors Ottjes Date: Mon, 20 Sep 2021 10:30:37 +0200 Subject: [PATCH 1/2] add fallback 4xx/5xx error views --- .../Foundation/Exceptions/Handler.php | 18 +++++- .../FoundationExceptionsHandlerTest.php | 60 +++++++++++++++++++ 2 files changed, 75 insertions(+), 3 deletions(-) diff --git a/src/Illuminate/Foundation/Exceptions/Handler.php b/src/Illuminate/Foundation/Exceptions/Handler.php index 84ea798a973b..443560a8e639 100644 --- a/src/Illuminate/Foundation/Exceptions/Handler.php +++ b/src/Illuminate/Foundation/Exceptions/Handler.php @@ -544,7 +544,7 @@ protected function renderHttpException(HttpExceptionInterface $e) { $this->registerErrorViewPaths(); - if (view()->exists($view = $this->getHttpExceptionView($e))) { + if ($view = $this->getHttpExceptionView($e)) { return response()->view($view, [ 'errors' => new ViewErrorBag, 'exception' => $e, @@ -568,11 +568,23 @@ protected function registerErrorViewPaths() * Get the view used to render HTTP exceptions. * * @param \Symfony\Component\HttpKernel\Exception\HttpExceptionInterface $e - * @return string + * @return string|null */ protected function getHttpExceptionView(HttpExceptionInterface $e) { - return "errors::{$e->getStatusCode()}"; + $view = 'errors::'.$e->getStatusCode(); + + if (view()->exists($view)) { + return $view; + } + + $view = substr($view, 0, -2).'xx'; + + if (view()->exists($view)) { + return $view; + } + + return null; } /** diff --git a/tests/Foundation/FoundationExceptionsHandlerTest.php b/tests/Foundation/FoundationExceptionsHandlerTest.php index 90f701ece326..cc52ad29cb3d 100644 --- a/tests/Foundation/FoundationExceptionsHandlerTest.php +++ b/tests/Foundation/FoundationExceptionsHandlerTest.php @@ -8,6 +8,7 @@ use Illuminate\Contracts\Routing\ResponseFactory as ResponseFactoryContract; use Illuminate\Contracts\Support\Responsable; use Illuminate\Contracts\View\Factory; +use Illuminate\Contracts\View\Factory as ViewFactory; use Illuminate\Database\RecordsNotFoundException; use Illuminate\Foundation\Exceptions\Handler; use Illuminate\Http\RedirectResponse; @@ -285,6 +286,65 @@ public function testRecordsNotFoundReturns404WithoutReporting() $this->handler->report(new RecordsNotFoundException); } + + public function testItReturnsSpecificErrorViewIfExists() + { + $viewFactory = m::mock(stdClass::class); + $viewFactory->shouldReceive('exists')->with('errors::502')->andReturn(true); + + $this->container->singleton(ViewFactory::class, function () use ($viewFactory) { + return $viewFactory; + }); + + $handler = new class($this->container) extends Handler { + public function getErrorView($e) + { + return $this->getHttpExceptionView($e); + } + }; + + $this->assertSame('errors::502', $handler->getErrorView(new HttpException(502))); + } + + public function testItReturnsFallbackErrorViewIfExists() + { + $viewFactory = m::mock(stdClass::class); + $viewFactory->shouldReceive('exists')->once()->with('errors::502')->andReturn(false); + $viewFactory->shouldReceive('exists')->once()->with('errors::5xx')->andReturn(true); + + $this->container->singleton(ViewFactory::class, function () use ($viewFactory) { + return $viewFactory; + }); + + $handler = new class($this->container) extends Handler { + public function getErrorView($e) + { + return $this->getHttpExceptionView($e); + } + }; + + $this->assertSame('errors::5xx', $handler->getErrorView(new HttpException(502))); + } + + public function testItReturnsNullIfNoErrorViewExists() + { + $viewFactory = m::mock(stdClass::class); + $viewFactory->shouldReceive('exists')->once()->with('errors::404')->andReturn(false); + $viewFactory->shouldReceive('exists')->once()->with('errors::4xx')->andReturn(false); + + $this->container->singleton(ViewFactory::class, function () use ($viewFactory) { + return $viewFactory; + }); + + $handler = new class($this->container) extends Handler { + public function getErrorView($e) + { + return $this->getHttpExceptionView($e); + } + }; + + $this->assertNull($handler->getErrorView(new HttpException(404))); + } } class CustomException extends Exception From f19181c161c0cc51005be99dfcdc02fd2f70b200 Mon Sep 17 00:00:00 2001 From: Sjors Ottjes Date: Mon, 20 Sep 2021 11:25:29 +0200 Subject: [PATCH 2/2] cs --- tests/Foundation/FoundationExceptionsHandlerTest.php | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/tests/Foundation/FoundationExceptionsHandlerTest.php b/tests/Foundation/FoundationExceptionsHandlerTest.php index cc52ad29cb3d..4b2f6570b4d7 100644 --- a/tests/Foundation/FoundationExceptionsHandlerTest.php +++ b/tests/Foundation/FoundationExceptionsHandlerTest.php @@ -296,7 +296,8 @@ public function testItReturnsSpecificErrorViewIfExists() return $viewFactory; }); - $handler = new class($this->container) extends Handler { + $handler = new class($this->container) extends Handler + { public function getErrorView($e) { return $this->getHttpExceptionView($e); @@ -316,7 +317,8 @@ public function testItReturnsFallbackErrorViewIfExists() return $viewFactory; }); - $handler = new class($this->container) extends Handler { + $handler = new class($this->container) extends Handler + { public function getErrorView($e) { return $this->getHttpExceptionView($e); @@ -336,7 +338,8 @@ public function testItReturnsNullIfNoErrorViewExists() return $viewFactory; }); - $handler = new class($this->container) extends Handler { + $handler = new class($this->container) extends Handler + { public function getErrorView($e) { return $this->getHttpExceptionView($e);