HTTP 控制器

2018-12-17 10:41 更新

簡(jiǎn)介

除了在單一的 routes.php 文件中定義所有的請(qǐng)求處理邏輯之外,你可能希望使用控制器類來組織此行為。控制器可將相關(guān)的 HTTP 請(qǐng)求處理邏輯組成一個(gè)類??刂破魍ǔ4娣旁?app/Http/Controllers 此目錄中。

           

基礎(chǔ)控制器

這里是一個(gè)基礎(chǔ)控制器類的例子:

<?php namespace App\Http\Controllers;use App\Http\Controllers\Controller;class UserController extends Controller {

    /**
     * 顯示所給定的用戶個(gè)人數(shù)據(jù)。
     *
     * @param  int  $id
     * @return Response
     */
    public function showProfile($id)
    {
        return view('user.profile', ['user' => User::findOrFail($id)]);
    }}

           

我們可以通過如下方式引導(dǎo)路由至對(duì)應(yīng)的控制器動(dòng)作:

Route::get('user/{id}', 'UserController@showProfile');

           

注意: 所有的控制器都應(yīng)該擴(kuò)展基礎(chǔ)控制器類。

控制器和命名空間

有一點(diǎn)非常重要,那就是我們無需指明完整的控制器命名空間,在類名稱中 App\Http\Controllers 之后的部分即可用于表示「根」命名空間。 RouteServiceProvider 默認(rèn)會(huì)在包含根控制器命名空間的路由群組中,加載 routes.php 此文件。

若你要在 App\Http\Controllers 此目錄深層使用 PHP 命名空間以嵌套化或組織你的控制器,只要使用相對(duì)于 App\Http\Controllers 根命名空間的特定類名稱即可。因此,若你的控制器類全名為 App\Http\Controllers\Photos\AdminController,你可以像這樣注冊(cè)一個(gè)路由:

Route::get('foo', 'Photos\AdminController@method');

           

命名控制器路由

和閉包路由一樣,你也可以指定控制器路由的名稱。

Route::get('foo', ['uses' => 'FooController@method', 'as' => 'name']);

           

指向控制器行為的 URL

要產(chǎn)生一個(gè)指向控制器行為的 URL,可使用 action 輔助方法。

$url = action('App\Http\Controllers\FooController@method');

           

若你想僅使用相對(duì)于控制器命名空間的類名稱中的一部分,來產(chǎn)生指向控制器行為的 URL,可用 URL 產(chǎn)生器注冊(cè)控制器的根命名空間。

URL::setRootControllerNamespace('App\Http\Controllers');$url = action('FooController@method');

           

你可以使用 currentRouteAction 方法來獲取正在執(zhí)行的控制器行為名稱:

$action = Route::currentRouteAction();

           

           

控制器中間件

中間件 可在控制器路由中指定,例如:

Route::get('profile', [
    'middleware' => 'auth',
    'uses' => 'UserController@showProfile']);

           

此外,你也可以在控制器構(gòu)造器中指定中間件 :

class UserController extends Controller {

    /**
     * 建立一個(gè)新的 UserController 實(shí)例。
     */
    public function __construct()
    {
        $this->middleware('auth');

        $this->middleware('log', ['only' => ['fooAction', 'barAction']]);

        $this->middleware('subscribed', ['except' => ['fooAction', 'barAction']]);
    }}

           

           

隱式控制器

Laravel 讓你能輕易地定義單一路由來處理控制器中的每一項(xiàng)行為。首先,用 Route::controller 方法定義一個(gè)路由:

Route::controller('users', 'UserController');

           

Controller 方法接受兩個(gè)參數(shù)。第一個(gè)參數(shù)是控制器欲處理的 base URI,第二個(gè)是控制器的類名稱。接著只要在你的控制器中加入方法,并在名稱前加上它們所對(duì)應(yīng)的 HTTP 請(qǐng)求。

class UserController extends Controller {

    public function getIndex()
    {
        //    }

    public function postProfile()
    {
        //    }

    public function anyLogin()
    {
        //    }}

           

index 方法會(huì)響應(yīng)控制器處理的根 URI ,在這個(gè)例子中是 users

如果你的控制器行為包含多個(gè)字詞,你可以在 URI 中使用「破折號(hào)」語法來訪問此行為。例如,下面這個(gè)在 UserController 中的控制器動(dòng)作會(huì)響應(yīng) users/admin-profile 此一 URI :

public function getAdminProfile() {}

           

設(shè)定路由名字

如果你想“命名”一些控制器的路由,你可以給 controller 方法傳入第三個(gè)參數(shù):

Route::controller('users', 'UserController', [
    'anyLogin' => 'user.login',]);

           

           

RESTful 資源控制器

資源控制器可讓你無痛建立和資源相關(guān)的 RESTful 控制器。例如,你可能希望創(chuàng)建一個(gè)控制器,它可用來處理針對(duì)你的應(yīng)用程序所保存相片的 HTTP 請(qǐng)求。我們可以使用 make:controller Artisan 命令,快速創(chuàng)建這樣的控制器:

php artisan make:controller PhotoController

           

接著,我們注冊(cè)一個(gè)指向此控制器的資源路由:

Route::resource('photo', 'PhotoController');

           

此單一路由聲明創(chuàng)建了多個(gè)路由,用來處理各式各樣和相片資源相關(guān)的 RESTful 行為。同樣地,產(chǎn)生的控制器已有各種和這些行為綁定的方法,包含用來通知你它們處理了那些 URI 及動(dòng)詞。

由資源控制器處理的行為

動(dòng)詞路徑行為路由名稱
GET/photo索引photo.index
GET/photo/create創(chuàng)建photo.create
POST/photo保存photo.store
GET/photo/{photo}顯示photo.show
GET/photo/{photo}/edit編輯photo.edit
PUT/PATCH/photo/{photo}更新photo.update
DELETE/photo/{photo}刪除photo.destroy

自定義資源路由

除此之外,你也可以指定讓路由僅處理一部分的行為:

Route::resource('photo', 'PhotoController',
                ['only' => ['index', 'show']]);Route::resource('photo', 'PhotoController',
                ['except' => ['create', 'store', 'update', 'destroy']]);

           

所有的資源控制器行為默認(rèn)都有個(gè)路由名稱。然而你可在選項(xiàng)中傳遞一個(gè) names 數(shù)組來重載這些名稱:

Route::resource('photo', 'PhotoController',
                ['names' => ['create' => 'photo.build']]);

           

處理嵌套資源控制器

在你的路由聲明中使用「點(diǎn)」號(hào)來「嵌套化」資源控制器:

Route::resource('photos.comments', 'PhotoCommentController');

           

此路由會(huì)注冊(cè)一個(gè)「嵌套的」資源,可透過像 photos/{photos}/comments/{comments} 這樣的 URL 來訪問。

class PhotoCommentController extends Controller {

    /**
     * 顯示指定照片的評(píng)論。
     *
     * @param  int  $photoId
     * @param  int  $commentId
     * @return Response
     */
    public function show($photoId, $commentId)
    {
        //    }}

           

在資源控制器中加入其他的路由

除了默認(rèn)的資源路由外,若你還需要在資源控制器中加入其他路由,應(yīng)該在調(diào)用 Route::resource 之前先定義它們:

Route::get('photos/popular', 'PhotoController@method');Route::resource('photos', 'PhotoController');

           

           

依賴注入和控制器

構(gòu)造器注入

Laravel 服務(wù)容器 用于解析所有的 Laravel 控制器。因此,你可以在控制器所需要的構(gòu)造器中,對(duì)依賴作任何的類型限制。

<?php namespace App\Http\Controllers;use Illuminate\Routing\Controller;use App\Repositories\UserRepository;class UserController extends Controller {

    /**
     * 用戶保存庫實(shí)例。
     */
    protected $users;

    /**
     * 創(chuàng)建新的控制器實(shí)例。
     *
     * @param  UserRepository  $users
     * @return void
     */
    public function __construct(UserRepository $users)
    {
        $this->users = $users;
    }}

           

當(dāng)然了,你也可以對(duì)任何的 Laravel contract 作類型限制。只要容器能解析它,你就可以對(duì)它作類型限制。

方法注入

除了建構(gòu)器注入外,你也可以對(duì)控制器方法的依賴作類型限制。例如,讓我們對(duì)某個(gè)方法的 Request 實(shí)例作類型限制:

<?php namespace App\Http\Controllers;use Illuminate\Http\Request;use Illuminate\Routing\Controller;class UserController extends Controller {

    /**
     * 保存一個(gè)新的用戶。
     *
     * @param  Request  $request
     * @return Response
     */
    public function store(Request $request)
    {
        $name = $request->input('name');

        //    }}

           

如果你的控制器方法預(yù)期由路由參數(shù)取得輸入,只要在其他的依賴之后列出路由參數(shù)即可:

<?php namespace App\Http\Controllers;use Illuminate\Http\Request;use Illuminate\Routing\Controller;class UserController extends Controller {

    /**
     * 更新一個(gè)特定的用戶。
     *
     * @param  Request  $request
     * @param  int  $id
     * @return Response
     */
    public function update(Request $request, $id)
    {
        //    }}

           

注意: 方法注入和 模型綁定 是完全兼容的。容器可智能地判斷那些參數(shù)和模型相關(guān)以及那些參數(shù)應(yīng)該被注入。

           

路由緩存

若您的應(yīng)用只使用了控制器路由,你可利用 Laravel 的路由緩存。使用路由緩存,將大幅降低注冊(cè)應(yīng)用程序所有路由所需要的時(shí)間。某些情況下,路由注冊(cè)甚至可以快上 100 倍。要產(chǎn)生路由緩存,只要執(zhí)行 route:cache Artisan 命令:

php artisan route:cache

           

就是這樣!你的緩存路由文件將會(huì)被用來代替 app/Http/routes.php 此一文件。記住,若你增加了任何新的路由,你就 必須產(chǎn)生一個(gè)新的路由緩存。因此在應(yīng)用部署時(shí),你可能會(huì)希望只要執(zhí)行 route:cache 命令:

要移除路由緩存文件,但不希望產(chǎn)生新的緩存,可使用 route:clear 命令:

php artisan route:clear


以上內(nèi)容是否對(duì)您有幫助:
在線筆記
App下載
App下載

掃描二維碼

下載編程獅App

公眾號(hào)
微信公眾號(hào)

編程獅公眾號(hào)