使用 Laravel 5.5+ 更好的來實現 404 響應

譯文首發於 使用 Laravel 5.5+ 更好的來實現 404 響應,轉載請註明出處!

Laravel 5.5.10 封裝了兩個有用的路由器方法,能夠幫助咱們爲用戶提供更好的 404 頁面。如今,當拋出 404 異常時,Laravel 會顯示一個漂亮的 404.blade.php 視圖文件,你能夠自定義顯示給用戶 UI,但在該視圖中,你無權訪問 sessioncookie,身份驗證(auth)等...php

在 laravel 5.5.10 中,咱們有一個新的 Route::fallback() 方法,用於定義當沒有其餘路由與請求匹配時 Laravel 回退的路由。laravel

Route::fallback(function () {
    return 'Sorry' . auth()->user()->name . '! This page does not exist.';
});

因此,如今咱們能夠使用具備正常頁面和頁腳的應用佈局,來替代簡單的 404 視圖,同時還能給用戶顯示一條友好的提示信息。web

Route::fallback(function() {
    return response()->view('notFound', [], 404);
});
@extends('layout.app')

@section('content')
    <h3>Sorry! this page doesn't exist.</h3>
@stop

當 Laravel 渲染這個回退(fallback)路由時,會運行全部的中間件,所以當你在 web.php 路由文件中定義了回退路由時,全部處在 web 中間件組的中間件都會被執行,這樣咱們就能夠獲取 session 數據了。json

API 接口說明

如今當你點擊 /non-existing-page 時,你會看到在回退路由中定義的視圖,甚至當你點擊 /api/non-existing-endpoint 時,若是你也不想提供這個接口,你能夠到 api 回退路由中定義 JSON 響應,讓咱們到 api.php 路由文件中定義另一個回退路由:api

Route::fallback(function() {
    return response()->json(['message' => 'Not Found!]);
});

因爲 api 中間件組帶有 /api 前綴,全部帶有 /api 前綴的未定義的路由,都會進入到 api.php 路由文件中的回退路由,而不是 web.php 路由文件中所定義的那個。cookie

使用 abort(404) 和 ModelNotFound 異常

當使用 abort(404) 時會拋出一個 NotFoundHttpException,此時處理器會爲咱們渲染出 404.blade.php 視圖文件,一樣的 ModelNotFoundException 異常也會作一樣的處理,那麼咱們應該如何如何處理才能在更好的渲染出回退路由的視圖,而不是一個普通的視圖呢?session

class Handler extends ExceptionHandler
{
    public function render($request, Exception $exception)
    {
        if ($exception instanceof NotFoundHttpException) {
            return Route::responseWithRoute('fallback');
        }

        if ($exception instanceof ModelNotFoundException) {
            return Route::responseWithRoute('fallback');
        }

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

Route::respondWithRoute('fallback') 回去跑名爲 fallback 的路由,咱們能夠像下面這樣爲回退路由命名:app

Route::fallback(function() {
    return response()->view('notFound', [], 404);
})->name('fallback');

甚至,你還能夠爲特定的資源指定回退路由:佈局

if ($exception instanceof ModelNotFoundException) {
    return $exception->getModel() == Server::class
                ? Route::respondWithRoute('serverFallback') 
                : Route::respondWithRoute('fallback');
}

如今咱們須要在路由文件中定義這個回退路由:this

Route::fallback(function(){
    return 'We could not find this server, there are other '. auth()->user()->servers()->count() . ' under your account ......';
})->name('serverFallback');

原文

Better 404 responses using Laravel 5.5+

相關文章
相關標籤/搜索