2017-05-30 112 views
1

我想确保从数据库连接问题抛出的异常是全局处理的。流明:异常处理程序 - 不捕捉QueryException或PDOException

我已经加入我的应用程序\例外以下\ Handler.php在render()方法,但是没有一个例外的是被抓:

<?php 

namespace App\Exceptions; 

use Exception; 
use Illuminate\Database\QueryException; 
use Illuminate\Validation\ValidationException; 
use Illuminate\Auth\Access\AuthorizationException; 
use Illuminate\Database\Eloquent\ModelNotFoundException; 
use Symfony\Component\HttpKernel\Exception\HttpException; 
use Laravel\Lumen\Exceptions\Handler as ExceptionHandler; 
use Symfony\Component\HttpKernel\Exception\MethodNotAllowedHttpException; 
use Symfony\Component\HttpKernel\Exception\NotFoundHttpException; 
use PDOException; 

class Handler extends ExceptionHandler 
{ 
    /** 
    * A list of the exception types that should not be reported. 
    * 
    * @var array 
    */ 
    protected $dontReport = [ 
     AuthorizationException::class, 
     HttpException::class, 
     ModelNotFoundException::class, 
     ValidationException::class, 
    ]; 

    /** 
    * Report or log an exception. 
    * 
    * This is a great spot to send exceptions to Sentry, Bugsnag, etc. 
    * 
    * @param \Exception $e 
    * @return void 
    */ 
    public function report(Exception $e) 
    { 
     parent::report($e); 
    } 

    /** 
    * Render an exception into an HTTP response. 
    * 
    * @param \Illuminate\Http\Request $request 
    * @param \Exception $e 
    * @return \Illuminate\Http\Response 
    */ 
    public function render($request, Exception $e) 
    { 
     if ($e instanceof AuthorizationException) { 
      return response()->json((['status' => 403, 'message' => 'Insufficient privileges to perform this action']), 403); 
     } 

     if ($e instanceof MethodNotAllowedHttpException) { 
      return response()->json((['status' => 405, 'message' => 'Method Not Allowed']), 405); 
     } 

     if ($e instanceof NotFoundHttpException) { 
      return response()->json((['status' => 404, 'message' => 'The requested resource was not found']), 404); 
     } 

     if ($e instanceof QueryException) { 
      return response()->json((['id' => 0, 'status_billing' => 'The requested resource was not found']), 500); 
     } 

     if ($e instanceof PDOException) { 
      return response()->json((['id' => 0, 'status_billing' => 'The requested resource was not found']), 500); 
     } 


     return parent::render($request, $e); 
    } 
} 

这也增添了我app.php :

$app->singleton(App\Exceptions\Handler::class); 

对于我的生活,我无法得到这个工作。

任何帮助/建议将不胜感激

感谢

回答

1

更改以下行从您的app.php

$app->singleton(App\Exceptions\Handler::class); 

到:

$app->singleton(
    Illuminate\Contracts\Debug\ExceptionHandler::class, 
    App\Exceptions\Handler::class 
); 

编辑

上述异常处理程序绑定中需要接口的原因是,当处理Route时引发异常时,会调用以下函数来处理该异常。

protected function handleException($passable, Exception $e) 
    { 
     if (! $this->container->bound(ExceptionHandler::class) || ! $passable instanceof Request) { 
      throw $e; 
     } 

     $handler = $this->container->make(ExceptionHandler::class); 

     $handler->report($e); 

     return $handler->render($passable, $e); 
    } 

的,如果容器条件检查是否具有针对的ExceptionHandler类的结合。如果存在绑定,那么异常将传递到该异常处理程序类以进一步处理。如果没有声明绑定,那么异常将被重新抛出。这里检查绑定是否为Illuminate\Contracts\Debug\ExceptionHandler。这就是为什么当你使用App\Exceptions\Handler::class直接绑定时,异常不会被你的异常处理程序捕获。

+0

感谢您的快速响应。 我在做这件事之前看到了它,它工作,但我不确定为什么,因为我从一开始就有它,它不工作。 就在几分钟前,我决定把它放回去,它开始工作。 另一件事是,我希望你可以验证,如果异常已经在方法中被捕获,那么渲染不会捕获它,对吗? 而且,如果可能的话,你能否给我简单的总结一下为什么'Illuminate \ Contracts \ Debug \ ExceptionHandler :: class'是必需的? 欣赏它 – thorbon

+1

是的,如果在方法中已经捕获异常,那么渲染方法不会捕获它。我已经更新了我的答案以包含详细的解释。 – ayip

+0

太棒了,非常感谢。 是否还有其他可用于以外的绑定?: Illuminate \ Contracts \ Debug \ ExceptionHandler – thorbon