diff --git a/src/Illuminate/Foundation/Exceptions/Handler.php b/src/Illuminate/Foundation/Exceptions/Handler.php index 4a950cc7a43f..4fc71ec99d4b 100644 --- a/src/Illuminate/Foundation/Exceptions/Handler.php +++ b/src/Illuminate/Foundation/Exceptions/Handler.php @@ -323,35 +323,42 @@ public function render($request, Throwable $e) { if (method_exists($e, 'render') && $response = $e->render($request)) { return Router::toResponse($request, $response); - } elseif ($e instanceof Responsable) { + } + + if ($e instanceof Responsable) { return $e->toResponse($request); } $e = $this->prepareException($this->mapException($e)); - foreach ($this->renderCallbacks as $renderCallback) { - foreach ($this->firstClosureParameterTypes($renderCallback) as $type) { - if (is_a($e, $type)) { - $response = $renderCallback($e, $request); - - if (! is_null($response)) { - return $response; - } - } - } + if ($response = $this->renderViaCallbacks($request, $e)) { + return $response; } - if ($e instanceof HttpResponseException) { - return $e->getResponse(); - } elseif ($e instanceof AuthenticationException) { - return $this->unauthenticated($request, $e); - } elseif ($e instanceof ValidationException) { - return $this->convertValidationExceptionToResponse($e, $request); - } + return match (true) { + $e instanceof HttpResponseException => $e->getResponse(), + $e instanceof AuthenticationException => $this->unauthenticated($request, $e), + $e instanceof ValidationException => $this->convertValidationExceptionToResponse($e, $request), + default => $this->renderExceptionResponse($request, $e), + }; + } - return $this->shouldReturnJson($request, $e) - ? $this->prepareJsonResponse($request, $e) - : $this->prepareResponse($request, $e); + /** + * Prepare exception for rendering. + * + * @param \Throwable $e + * @return \Throwable + */ + protected function prepareException(Throwable $e) + { + return match (true) { + $e instanceof ModelNotFoundException => new NotFoundHttpException($e->getMessage(), $e), + $e instanceof AuthorizationException => new AccessDeniedHttpException($e->getMessage(), $e), + $e instanceof TokenMismatchException => new HttpException(419, $e->getMessage(), $e), + $e instanceof SuspiciousOperationException => new NotFoundHttpException('Bad hostname provided.', $e), + $e instanceof RecordsNotFoundException => new NotFoundHttpException('Not found.', $e), + default => $e, + }; } /** @@ -372,26 +379,41 @@ protected function mapException(Throwable $e) } /** - * Prepare exception for rendering. + * Try to render a response from request and exception via render callbacks. * + * @param \Illuminate\Http\Request $request * @param \Throwable $e - * @return \Throwable + * @return mixed + * + * @throws \ReflectionException */ - protected function prepareException(Throwable $e) + protected function renderViaCallbacks($request, Throwable $e) { - if ($e instanceof ModelNotFoundException) { - $e = new NotFoundHttpException($e->getMessage(), $e); - } elseif ($e instanceof AuthorizationException) { - $e = new AccessDeniedHttpException($e->getMessage(), $e); - } elseif ($e instanceof TokenMismatchException) { - $e = new HttpException(419, $e->getMessage(), $e); - } elseif ($e instanceof SuspiciousOperationException) { - $e = new NotFoundHttpException('Bad hostname provided.', $e); - } elseif ($e instanceof RecordsNotFoundException) { - $e = new NotFoundHttpException('Not found.', $e); + foreach ($this->renderCallbacks as $renderCallback) { + foreach ($this->firstClosureParameterTypes($renderCallback) as $type) { + if (is_a($e, $type)) { + $response = $renderCallback($e, $request); + + if (! is_null($response)) { + return $response; + } + } + } } + } - return $e; + /** + * Render a default exception response if any. + * + * @param \Illuminate\Http\Request $request + * @param \Throwable $e + * @return \Symfony\Component\HttpFoundation\Response + */ + protected function renderExceptionResponse($request, Throwable $e) + { + return $this->shouldReturnJson($request, $e) + ? $this->prepareJsonResponse($request, $e) + : $this->prepareResponse($request, $e); } /**