服務 ―― 包開發(fā)

2018-02-24 15:38 更新

服務 —— 包開發(fā)

1、簡介

包是添加功能到Laravel的主要方式。包可以提供任何功能,小到處理日期如Carbon,大到整個BDD測試框架如Behat。

當然,有很多不同類型的包。有些包是獨立的,意味著可以在任何框架中使用,而不僅是Laravel。比如Carbon和Behat都是獨立的包。所有這些包都可以通過在composer.json文件中請求以便被Laravel使用。

另一方面,其它包只能特定和Laravel一起使用,這些包可能有路由用于加強Laravel應用的功能,本章主要討論只能在Laravel中使用的包。

2、服務提供者

服務提供者是包和Laravel之間的連接點。服務提供者負責綁定對象到Laravel的服務容器并告知Laravel從哪里加載包資源如視圖、配置和本地化文件。

服務提供者繼承自Illuminate\Support\ServiceProvider類并包含兩個方法:registerboot。ServiceProvider基類位于Composer包illuminate/support。

要了解更多關于服務提供者的內容,查看其文檔。

3、路由

要定義包的路由,只需要在包服務提供者中的boot方法中引入路由文件。在路由文件中,可以使用Route門面注冊路由,和Laravel應用中注冊路由一樣:

/**
 * Perform post-registration booting of services.
 *
 * @return void
 */
public function boot(){
    if (! $this->app->routesAreCached()) {
        require __DIR__.'/../../routes.php';
    }
}

4、資源

4.1 視圖

要在Laravel中注冊包視圖,需要告訴Laravel視圖在哪,可以使用服務提供者的loadViewsFrom方法來實現。loadViewsFrom方法接收兩個參數:視圖模板的路徑和包名稱。例如,如果你的包名稱是“courier”,添加如下代碼到服務提供者的boot方法:

/**
 * Perform post-registration booting of services.
 *
 * @return void
 */
public function boot(){
    $this->loadViewsFrom(__DIR__.'/path/to/views', 'courier');
}

包視圖通過使用類似的package::view語法來引用。所以,你可以通過如下方式加載courier包上的admin視圖:

Route::get('admin', function () {
    return view('courier::admin');
});

4.1.1 覆蓋包視圖

當你使用loadViewsFrom方法的時候,Laravel實際上為視圖注冊了兩個存放位置:一個是resources/views/vendor目錄,另一個是你指定的目錄。所以,以courier為例:當請求一個包視圖時,Laravel首先檢查開發(fā)者是否在resources/views/vendor/courier提供了自定義版本的視圖,如果該視圖不存在,Laravel才會搜索你調用loadViewsFrom方法時指定的目錄。這種機制使得終端用戶可以輕松地自定義/覆蓋包視圖。

4.1.2?發(fā)布視圖

如果你想要視圖能夠發(fā)布到應用的resources/views/vendor目錄,可以使用服務提供者的publishes方法。該方法接收包視圖路徑及其相應的發(fā)布路徑數組作為參數:

/**
 * Perform post-registration booting of services.
 *
 * @return void
 */
public function boot(){
    $this->loadViewsFrom(__DIR__.'/path/to/views', 'courier');

    $this->publishes([
        __DIR__.'/path/to/views' => base_path('resources/views/vendor/courier'),
    ]);
}

現在,當包用戶執(zhí)行Laravel的Artisan命令vendor:publish時,你的視圖包將會被拷貝到指定路徑。

4.2?翻譯

如果你的包包含翻譯文件,你可以使用loadTranslationsFrom方法告訴Laravel如何加載它們,例如,如果你的包命名為“courier”,你應該添加如下代碼到服務提供者的boot方法:

/**
 * Perform post-registration booting of services.
 *
 * @return void
 */
public function boot(){
    $this->loadTranslationsFrom(__DIR__.'/path/to/translations', 'courier');
}

包翻譯使用形如package::file.line的語法進行引用。所以,你可以使用如下方式從messages文件中加載courier包的welcome行:

echo trans('courier::messages.welcome');

4.3 配置

通常,你想要發(fā)布包配置文件到應用根目錄下的config目錄,這將允許包用戶輕松覆蓋默認配置選項,要發(fā)布一個配置文件,只需在服務提供者的boot方法中使用publishes方法即可:

/**
 * Perform post-registration booting of services.
 *
 * @return void
 */
public function boot(){
    $this->publishes([
        __DIR__.'/path/to/config/courier.php' => config_path('courier.php'),
    ]);
}

現在,當包用戶執(zhí)行Laravel的Artisan命令vendor:publish時,你的文件將會被拷貝到指定位置,當然,配置被發(fā)布后,可以通過和其它配置選項一樣的方式進行訪問:

$value = config('courier.option');

4.3.1 默認包配置

你還可以選擇將自己的包配置文件合并到應用的拷貝版本,這允許用戶只引入他們在應用配置文件中實際想要覆蓋的配置選項。要合并兩個配置,在服務提供者的register方法中使用mergeConfigFrom方法即可:

/**
 * Register bindings in the container.
 *
 * @return void
 */
public function register(){
    $this->mergeConfigFrom(
        __DIR__.'/path/to/config/courier.php', 'courier'
    );
}

5、公共前端資源

你的包可能包含JavaScript、CSS和圖片,要發(fā)布這些前端資源到應用根目錄下的public目錄,使用服務提供者的publishes方法。在本例中,我們添加一個前端資源組標簽public,用于發(fā)布相關的前端資源組:

/**
 * Perform post-registration booting of services.
 *
 * @return void
 */
public function boot(){
    $this->publishes([
        __DIR__.'/path/to/assets' => public_path('vendor/courier'),
    ], 'public');
}

現在,當包用戶執(zhí)行vendor:publish命令時,前端資源將會被拷貝到指定位置,由于你需要在每次包更新時重寫前端資源,可以使用--force標識:

php artisan vendor:publish --tag=public --force

如果你想要確保前端資源已經更新到最新版本,可添加該命令到composer.json文件的post-update-cmd列表。

6、發(fā)布文件組

你可能想要分開發(fā)布包前端資源組和資源,例如,你可能想要用戶發(fā)布包配置的同時不發(fā)布包前端資源,可以通過在調用時給它們打上“標簽”來實現分離。下面我們在包服務提供者的boot方法中定義兩個公共組:

/**
 * Perform post-registration booting of services.
 *
 * @return void
 */
public function boot(){
    $this->publishes([
        __DIR__.'/../config/package.php' => config_path('package.php')
    ], 'config');

    $this->publishes([
        __DIR__.'/../database/migrations/' => database_path('migrations')
    ], 'migrations');
}

現在用戶可以在使用Artisan命令vendor:publish時通過引用標簽名來分開發(fā)布這兩個組:

php artisan vendor:publish --provider="Vendor\Providers\PackageServiceProvider" --tag="config"

擴展閱讀:實例教程 —— 如何在Laravel 5.1中進行自定義包開發(fā)

以上內容是否對您有幫助:
在線筆記
App下載
App下載

掃描二維碼

下載編程獅App

公眾號
微信公眾號

編程獅公眾號