您好,登錄后才能下訂單哦!
這篇文章主要講解了“l(fā)aravel中異常問題怎么解決”,文中的講解內(nèi)容簡(jiǎn)單清晰,易于學(xué)習(xí)與理解,下面請(qǐng)大家跟著小編的思路慢慢深入,一起來(lái)研究和學(xué)習(xí)“l(fā)aravel中異常問題怎么解決”吧!
laravel中的異常有:1、“E_ERROR”致命運(yùn)行時(shí)錯(cuò)誤,不可恢復(fù),會(huì)導(dǎo)致腳本終止不再繼續(xù)運(yùn)行;2、“E_WARNING”運(yùn)行時(shí)警告“非致命錯(cuò)誤”;3、“E_PARSE”編譯時(shí)語(yǔ)法解析錯(cuò)誤;4、“E_CORE_ERROR”初始化啟動(dòng)過程中發(fā)生的致命錯(cuò)誤;5、“E_COMPILE_ERROR”致命編譯時(shí)錯(cuò)誤;6、“E_RECOVERABLE_ERROR”可被捕捉的致命錯(cuò)誤。
本教程操作環(huán)境:windows7系統(tǒng)、Laravel9版,DELL G3電腦。
laravel中的異常級(jí)別
常量 | 說(shuō)明 |
---|---|
E_ERROR | 致命的運(yùn)行時(shí)錯(cuò)誤。這類錯(cuò)誤一般是不可恢復(fù)的情況,例如內(nèi)存分配導(dǎo)致的問題。后果是導(dǎo)致腳本終止不再繼續(xù)運(yùn)行。 |
E_WARNING | 運(yùn)行時(shí)警告 (非致命錯(cuò)誤)。僅給出提示信息,但是腳本不會(huì)終止運(yùn)行。 |
E_PARSE | 編譯時(shí)語(yǔ)法解析錯(cuò)誤。解析錯(cuò)誤僅僅由分析器產(chǎn)生。 |
E_NOTICE | 運(yùn)行時(shí)通知。表示腳本遇到可能會(huì)表現(xiàn)為錯(cuò)誤的情況,但是在可以正常運(yùn)行的腳本里面也可能會(huì)有類似的通知。 |
E_CORE_ERROR | 在 PHP 初始化啟動(dòng)過程中發(fā)生的致命錯(cuò)誤。該錯(cuò)誤類似 E_ERROR,但是是由 PHP 引擎核心產(chǎn)生的。 |
E_CORE_WARNING | PHP 初始化啟動(dòng)過程中發(fā)生的警告 (非致命錯(cuò)誤) 。類似 E_WARNING,但是是由 PHP 引擎核心產(chǎn)生的。 |
E_COMPILE_ERROR | 致命編譯時(shí)錯(cuò)誤。類似 E_ERROR, 但是是由 Zend 腳本引擎產(chǎn)生的。 |
E_COMPILE_WARNING | 編譯時(shí)警告 (非致命錯(cuò)誤)。類似 E_WARNING,但是是由 Zend 腳本引擎產(chǎn)生的。 |
E_USER_ERROR | 用戶產(chǎn)生的錯(cuò)誤信息。類似 E_ERROR, 但是是由用戶自己在代碼中使用 PHP 函數(shù) trigger_error () 來(lái)產(chǎn)生的。 |
E_USER_WARNING | 用戶產(chǎn)生的警告信息。類似 E_WARNING, 但是是由用戶自己在代碼中使用 PHP 函數(shù) trigger_error () 來(lái)產(chǎn)生的。 |
E_USER_NOTICE | 用戶產(chǎn)生的通知信息。類似 E_NOTICE, 但是是由用戶自己在代碼中使用 PHP 函數(shù) trigger_error () 來(lái)產(chǎn)生的。 |
E_STRICT | 啟用 PHP 對(duì)代碼的修改建議,以確保代碼具有最佳的互操作性和向前兼容性。 |
E_RECOVERABLE_ERROR | 可被捕捉的致命錯(cuò)誤。 它表示發(fā)生了一個(gè)可能非常危險(xiǎn)的錯(cuò)誤,但是還沒有導(dǎo)致 PHP 引擎處于不穩(wěn)定的狀態(tài)。 如果該錯(cuò)誤沒有被用戶自定義句柄捕獲 (參見 set_error_handler ()),將成為一個(gè) E_ERROR 從而腳本會(huì)終止運(yùn)行。 |
E_DEPRECATED | 運(yùn)行時(shí)通知。啟用后將會(huì)對(duì)在未來(lái)版本中可能無(wú)法正常工作的代碼給出警告。 |
E_USER_DEPRECATED | 用戶產(chǎn)少的警告信息。 類似 E_DEPRECATED, 但是是由用戶自己在代碼中使用 PHP 函數(shù) trigger_error () 來(lái)產(chǎn)生的。 |
E_ALL | 用戶產(chǎn)少的警告信息。 類似 E_DEPRECATED, 但是是由用戶自己在代碼中使用 PHP 函數(shù) trigger_error () 來(lái)產(chǎn)生的。 |
Laravel 異常處理
laravel 的異常處理由類 \Illuminate\Foundation\Bootstrap\HandleExceptions::class 完成:
class HandleExceptions { public function bootstrap(Application $app) { $this->app = $app; error_reporting(-1); set_error_handler([$this, 'handleError']); set_exception_handler([$this, 'handleException']); register_shutdown_function([$this, 'handleShutdown']); if (! $app->environment('testing')) { ini_set('display_errors', 'Off'); } } }
異常轉(zhuǎn)化
laravel 的異常處理均由函數(shù) handleException 負(fù)責(zé)。
PHP7 實(shí)現(xiàn)了一個(gè)全局的 throwable 接口,原來(lái)的 Exception 和部分 Error 都實(shí)現(xiàn)了這個(gè)接口, 以接口的方式定義了異常的繼承結(jié)構(gòu)。于是,PHP7 中更多的 Error 變?yōu)榭刹东@的 Exception 返回給開發(fā)者,如果不進(jìn)行捕獲則為 Error ,如果捕獲就變?yōu)橐粋€(gè)可在程序內(nèi)處理的 Exception。這些可被捕獲的 Error 通常都是不會(huì)對(duì)程序造成致命傷害的 Error,例如函數(shù)不存在。
PHP7 中,基于 /Error exception,派生了 5 個(gè)新的 engine exception:ArithmeticError / AssertionError / DivisionByZeroError / ParseError / TypeError。在 PHP7 里,無(wú)論是老的 /Exception 還是新的 /Error ,它們都實(shí)現(xiàn)了一個(gè)共同的 interface: /Throwable。
因此,遇到非 Exception 類型的異常,首先就要將其轉(zhuǎn)化為 FatalThrowableError 類型:
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); } }
FatalThrowableError 是 Symfony 繼承 \ErrorException 的錯(cuò)誤異常類:
class FatalThrowableError extends FatalErrorException { public function __construct(\Throwable $e) { if ($e instanceof \ParseError) { $message = 'Parse error: '.$e->getMessage(); $severity = E_PARSE; } elseif ($e instanceof \TypeError) { $message = 'Type error: '.$e->getMessage(); $severity = E_RECOVERABLE_ERROR; } else { $message = $e->getMessage(); $severity = E_ERROR; } \ErrorException::__construct( $message, $e->getCode(), $severity, $e->getFile(), $e->getLine() ); $this->setTrace($e->getTrace()); } }
異常 Log
當(dāng)遇到異常情況的時(shí)候,laravel 首要做的事情就是記錄 log,這個(gè)就是 report 函數(shù)的作用。
protected function getExceptionHandler() { return $this->app->make(ExceptionHandler::class); }
laravel 在 Ioc 容器中默認(rèn)的異常處理類是 Illuminate\Foundation\Exceptions\Handler:
class Handler implements ExceptionHandlerContract { public function report(Exception $e) { if ($this->shouldntReport($e)) { return; } try { $logger = $this->container->make(LoggerInterface::class); } catch (Exception $ex) { throw $e; // throw the original exception } $logger->error($e); } protected function shouldntReport(Exception $e) { $dontReport = array_merge($this->dontReport, [HttpResponseException::class]); return ! is_null(collect($dontReport)->first(function ($type) use ($e) { return $e instanceof $type; })); } }
異常頁(yè)面展示
記錄 log 后,就要將異常轉(zhuǎn)化為頁(yè)面向開發(fā)者展示異常的信息,以便查看問題的來(lái)源:
protected function renderHttpResponse(Exception $e) { $this->getExceptionHandler()->render($this->app['request'], $e)->send(); } class Handler implements ExceptionHandlerContract { public function render($request, Exception $e) { $e = $this->prepareException($e); 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 $this->prepareResponse($request, $e); } }
對(duì)于不同的異常,laravel 有不同的處理,大致有 HttpException、HttpResponseException、AuthorizationException、ModelNotFoundException、AuthenticationException、ValidationException。由于特定的不同異常帶有自身的不同需求,本文不會(huì)特別介紹。本文繼續(xù)介紹最普通的異常 HttpException 的處理:
protected function prepareResponse($request, Exception $e) { if ($this->isHttpException($e)) { return $this->toIlluminateResponse($this->renderHttpException($e), $e); } else { return $this->toIlluminateResponse($this->convertExceptionToResponse($e), $e); } } protected function renderHttpException(HttpException $e) { $status = $e->getStatusCode(); view()->replaceNamespace('errors', [ resource_path('views/errors'), __DIR__.'/views', ]); if (view()->exists("errors::{$status}")) { return response()->view("errors::{$status}", ['exception' => $e], $status, $e->getHeaders()); } else { return $this->convertExceptionToResponse($e); } }
對(duì)于 HttpException 來(lái)說(shuō),會(huì)根據(jù)其錯(cuò)誤的狀態(tài)碼,選取不同的錯(cuò)誤頁(yè)面模板,若不存在相關(guān)的模板,則會(huì)通過 SymfonyResponse 來(lái)構(gòu)造異常展示頁(yè)面:
protected function convertExceptionToResponse(Exception $e) { $e = FlattenException::create($e); $handler = new SymfonyExceptionHandler(config('app.debug')); return SymfonyResponse::create($handler->getHtml($e), $e->getStatusCode(), $e->getHeaders()); } protected function toIlluminateResponse($response, Exception $e) { if ($response instanceof SymfonyRedirectResponse) { $response = new RedirectResponse($response->getTargetUrl(), $response->getStatusCode(), $response->headers->all()); } else { $response = new Response($response->getContent(), $response->getStatusCode(), $response->headers->all()); } return $response->withException($e); }
感謝各位的閱讀,以上就是“l(fā)aravel中異常問題怎么解決”的內(nèi)容了,經(jīng)過本文的學(xué)習(xí)后,相信大家對(duì)laravel中異常問題怎么解決這一問題有了更深刻的體會(huì),具體使用情況還需要大家實(shí)踐驗(yàn)證。這里是億速云,小編將為大家推送更多相關(guān)知識(shí)點(diǎn)的文章,歡迎關(guān)注!
免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長(zhǎng)郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。