Laravel

Laravel5のミドルウェアの使い方

More than 3 years have passed since last update.

Laravel5のミドルウェアについてちょっと調べてみました。

http://readouble.com/laravel/5/0/0/ja/middleware.html

例えば、職場の偉い人が「WEBサイトの訪問者に挨拶したい」とか言ってきたとします。

要件としては大体こんな感じです。


  • WEBサイト上のすべての画面で挨拶したい。

  • ちなみに時間帯によって挨拶の文言を変えたい。

ミドルウェアはこういう「常に何かやりたい」ってケースで使えば良さそうです。

それでは、上記要件を満たすミドルウェアを作ってみます。


ミドルウェアの作成

まず、artisanコマンドでミドルウェアを作成します。

$ php artisan make:middleware GreetingMiddleware

作成された app/Http/Middleware/GreetingMiddleware.php を適当に編集します。


app/Http/Middleware/GreetingMiddleware.php

<?php namespace App\Http\Middleware;

use Closure;
use Config;
use Illuminate\Contracts\View\Factory as ViewFactory;
use Carbon\Carbon;

class GreetingMiddleware {

/**
* Create a new instance.
*
* @param \Illuminate\Contracts\View\Factory $view
* @return void
*/

public function __construct(ViewFactory $view)
{
$this->view = $view;
}

/**
* Handle an incoming request.
*
* @param \Illuminate\Http\Request $request
* @param \Closure $next
* @return mixed
*/

public function handle($request, Closure $next)
{
$timestamp = $request->server('REQUEST_TIME');
$hour = Carbon::createFromTimeStamp($timestamp, Config::get('app.timezone'))->hour;

$message = 'こんばんは';
if (in_array($hour, range(5, 9)))
{
$message = 'おはよう';
}
else if (in_array($hour, range(10, 17)))
{
$message = 'こんにちは';
}
$this->view->share('greetingMessage', $message);

return $next($request);
}
}



ミドルウェアの登録

全てのリクエストで上記ミドルウェアを実行したいので、グローバルミドルウェアとして登録します。


app/Http/Kernel.php

protected $middleware = [

....

'App\Http\Middleware\GreetingMiddleware', // <= 追記する
];



テンプレートファイルの編集

続いて、挨拶を表示すべくテンプレートファイルを編集します。

今回は、resources/views/app.blade.phpのヘッダー付近に書いてみます。


resources/views/app.blade.php

<span>

{{ $greetingMessage }}
@if (Auth::guest())
ゲストさん
@else
{{ Auth::user()->name }}さん
@endif
</span>

これでWEBブラウザから確認すると、「こんにちは XXXさん」のように表示されるようになりました。


ミドルウェアのテスト

最後に、テストがないと同僚がプルリクエストを受け付けてくれないので、ユニットテストを書きます。


tests/Http/Middleware/GreetingMiddlewareTest.php

<?php

use App\Http\Middleware\GreetingMiddleware;
use Illuminate\Http\Request;
use Symfony\Component\HttpFoundation\ServerBag;

class GreetingMiddlewareTest extends TestCase {

public function setUp()
{
parent::setUp();
$this->view = app('view');
$this->middleware = new GreetingMiddleware($this->view);
$this->request = new Request();
}

public function handleDataProvider()
{
return [
['2015-03-27 05:00:00', 'おはよう'],
['2015-03-27 09:59:59', 'おはよう'],
['2015-03-27 10:00:00', 'こんにちは'],
['2015-03-27 17:59:59', 'こんにちは'],
['2015-03-27 18:00:00', 'こんばんは'],
['2015-03-28 04:59:59', 'こんばんは'],
];
}

/**
* @dataProvider handleDataProvider
*/

public function testHandle($datetime, $expected)
{
$this->request->server = new ServerBag(['REQUEST_TIME' => strtotime($datetime)]);
$this->middleware->handle($this->request, function($request){});
$this->assertEquals($expected, $this->view->shared('greetingMessage'));
}
}


ユニットテストを実行してグリーンになればOKです。

$ phpunit tests/Http/Middleware/GreetingMiddlewareTest.php