首頁>技術>

引言

有時候為了不重寫程式碼,避免冗餘無用重複的程式碼在程式內到處都是。我們總是想方設法 把寫過的邏輯拿過來使用。

今天要說的就是在laravel中,能不能在命令列中呼叫控制器的方法, 怎麼去實現?

學習時間

為了快速測試控制器方法可不可行,我們有時候會想,能不能像這樣在命令列直接訪問某個控制器路由的方法。

php index.php --uri=controller/method/var1/var2

要知道國內號稱用途最廣的thinkphp都已經這樣用了,laravel可落後乎?當然不可。

於是我們想,既然laravel提供了artisan的命令列呼叫,何不先做一個命令,然後在命令內使用程式方法 呼叫控制器呢。說來就動手開寫。

首先建立一個命令類。

php artisan make:command CallRoute

系統都是按照模板生成的 CallRoute.php 檔案,我們只撿特殊的部分貼出來。 首先定義命令格式和傳入的引數。

protected $signature = 'route:call {uri}';

然後是用法的描述:

protected $description = 'php artsian route:call /route';

要訪問uri地址,我們肯定要構造一個請求體,傳入對應的引數,這樣控制器方法才能正確地接收。

$request = Request::create($this->argument('uri'), 'GET');

這裡構造的請求體非常靈活,你可以模擬任何有效的請求,地址,方法,引數,等等。 然後重點來了,我們使用laravel框架提供的 Container 容器構造一個呼叫:

app()->make(\\Illuminate\\Contracts\\Http\\Kernel::class)->handle($request);

就醬。

為了讓你的命令在laravel生命週期內可被註冊,還需要手動註冊一下。在檔案 app/Console/Kernel.php 內加這麼一行:

protected $commands = [ 'App\\Console\\Commands\\CallRoute'];

現在你就可以在命令列使用了:

php artisan route:call /path

當然了如果你使用的laravel版本比較高,其提供了 tinker 功能,會讓你眼前一亮,相見恨晚。 比如原始的請求路由地址是這樣的:

URL: http://xxx.test/calendar?filter[id]=1&anotherparam=2

那麼我們可以直接使用容器例項化一個控制器物件:

 $cc = app()->make('App\\Http\\Controllers\\CalendarController');

然後使用全域性容器盒子呼叫控制器物件的方法,並傳送引數:

app()->call([$cc, 'getCalendarV2'], ['filter[id]'=>1, 'anotherparam' => '2']);

是不是超級簡單,有沒有?可見,laravel容器盒子這種設計理念,幾乎可以跨任意區域呼叫, 提供的強大能力,非同尋常。

寫在最後

本文通過詳細地設計實現了命令列呼叫控制器方法的步驟,其中低版本的推薦第一種寫法, 通過寫入請求體到框架上下文進行通訊;高版本的可以隨便開掛,容器盒子威力無比!

Happy coding :-)

最新評論
  • BSA-TRITC(10mg/ml) TRITC-BSA 牛血清白蛋白改性標記羅丹明
  • 在Deno中構建一個命令列天氣預報程式