美文网首页
Laravel异常机制

Laravel异常机制

作者: 其实我很dou | 来源:发表于2017-12-14 14:16 被阅读0次

    容器绑定异常处理类

    $app = require_once __DIR__.'/../bootstrap/app.php';
    

    app.php中,

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

    启动过程中, 在Illuminate\Foundation\Http\Kernel类中, 会调用下面

    protected $bootstrappers = [
            'Illuminate\Foundation\Bootstrap\DetectEnvironment',
            'Illuminate\Foundation\Bootstrap\LoadConfiguration',
            'Illuminate\Foundation\Bootstrap\ConfigureLogging',
            'Illuminate\Foundation\Bootstrap\HandleExceptions',
            'Illuminate\Foundation\Bootstrap\RegisterFacades',
            'Illuminate\Foundation\Bootstrap\RegisterProviders',
            'Illuminate\Foundation\Bootstrap\BootProviders',
        ];
    

    每个类中的bootstrap方法, 'Illuminate\Foundation\Bootstrap\HandleExceptions'如下:

     public function bootstrap(Application $app)
        {
            $this->app = $app;
    
            error_reporting(-1);
    
            set_error_handler([$this, 'handleError']);
    
            //调用$this->handleException($e), 处理全局未处理的异常,
            // 将抛出的异常作为参数, 都传给改方法参数, 交由改方法处理
    
            set_exception_handler([$this, 'handleException']);
    
            register_shutdown_function([$this, 'handleShutdown']);
    
            if (! $app->environment('testing')) {
                ini_set('display_errors', 'Off');
            }
        }
    

    handleException如下:

    public function handleException($e)
        {
            if (! $e instanceof Exception) {
                $e = new FatalThrowableError($e);
            }
    
            // 记录日志
            $this->getExceptionHandler()->report($e);
    
            if ($this->app->runningInConsole()) {
                $this->renderForConsole($e);
            } else {
                // 生成响应
                $this->renderHttpResponse($e);
            }
        }
    
    protected function renderHttpResponse(Exception $e)
        {
            $this->getExceptionHandler()->render($this->app['request'], $e)->send();
        }
    
    protected function getExceptionHandler()
        {
            // 返回最开始绑定的异常处理类App\Exceptions\Handler::class
            return $this->app->make('Illuminate\Contracts\Debug\ExceptionHandler');
        }
    

    调用App\Exceptions\Handler::class的render()方法, 如下

    /**
         * Render an exception into an HTTP response.
         * 此方法写自己的异常处理类
         * 覆盖父类render方法
         * @param  \Illuminate\Http\Request  $request
         * @param  \Exception  $e
         * @return \Illuminate\Http\Response
         */
        public function render($request, Exception $e)
        {
            // 记录日志
            Log::error($e);
            if(app('request')->ajax() || app('request')->wantsJson()) {
                return $this->jsonErrWithException($e);
            } else {
                $data = ['code'=>config('errcode.sys_err'), 'msg'=>trans('error_info.sys_err')];
                if ($e instanceof AuthorizationException) {
                    // 暂时这样, 因为有异常没有初始化代码和mess
                    $data['code'] = $e->getCode();
                    $data['msg'] = $e->getMessage();
      
                } elseif($e instanceof MyException) {
                      // 我们自己定义的异常
    
                }
                // 自己定义的错误页面
                return response()->view('errors.503', $data, 503);
            }
        }
    

    启动最后一步 , 会调用kernel类的handle()方法, 如下

    Illuminate\Foundation\Http\Kernel;
    public function handle($request)
        {
            try {
                $request->enableHttpMethodParameterOverride();
    
                $response = $this->sendRequestThroughRouter($request);
            } catch (Exception $e) {
                // 日志记录异常
                $this->reportException($e);
                // 使用App\Exceptions\Handler::class处理异常
                $response = $this->renderException($request, $e);
            } catch (Throwable $e) {
                $this->reportException($e = new FatalThrowableError($e));
    
                $response = $this->renderException($request, $e);
            }
    
            $this->app['events']->fire('kernel.handled', [$request, $response]);
    
            return $response;
        }
    

    相关文章

      网友评论

          本文标题:Laravel异常机制

          本文链接:https://www.haomeiwen.com/subject/hetnixtx.html