Middleware (посредники, или промежуточное программое обеспечение) - это фильтры обработки HTTP-запроса. Основная задача middleware - предворительная обработка запроса, до того, как он попадает в маршутизатор, либо контроллер.
Так, например, в Laravel включены middlewares для проверки аутентификации пользователя. Если пользователь не залогинен, middleware перенаправляет его на страницу логина. Если же залогинен - middleware не вмешивается в прохождение запроса, передавая его дальше по цепочке middleware-посредников к собственно приложению.
В Laravel есть несколько дефолтных middleware, которые находятся в папке app/Http/Middleware. Это middlewares для реализации режима обслуживания сайта ("сайт временно не работает, зайдите позже"), проверки авторизации и CSRF-защита.
Для создания middleware можно воспользоваться командой make:middleware:
php artisan make:middleware Admin
В папке app/Http/Middleware будет создан файл с классом Admin и методом handle().
Cоздадим middlewareAdmin, который будет пропускать только админов, т.е. тех пользователей, у которых в таблице users в базе данных выставлен параметр isAdmin = 1.
if(Auth::user()->isAdmin != 1){ return redirect()->guest('auth/login'); }
Метод handle() класса middleware должен принять объект $request и с помощью функции-замыкания $next вернуть его дальше (незименным, либо обработанным).
public function handle($request, Closure $next, $guard = null) { if(Auth::user()->isAdmin != 1){ return redirect()->guest('auth/login'); } return $next($request); }
Далее необходимо добавить middleware в свойство routeMiddleware класса app/Http/Kernel.php, назначив ему некоторое имя, например, admin, которое будет ключем массива:
protected $routeMiddleware = [ 'auth' => 'App\Http\Middleware\Authenticate', 'admin' => 'App\Http\Middleware\Admin', 'guest' => 'App\Http\Middleware\RedirectIfAuthenticated', ];
Теперь мы можем использовать созданный middleware в своих контроллерах, и других классах фрэймворка. Для использования в контроллере, в нём необходимо создать конструктор, в котором осуществляется вызов middleware.
public function __construct() { parent::__construct(); $this->middleware('admin'); }
Также возможно использование middleware в маршрутизаторе (файл routes/web.php). Здесь мы можем один middleware связать с группой контроллеров.
Route::group(['middleware' => ['auth']], function () { Route::get('home', 'HomeController@index'); Route::get('home/edit', 'HomeController@edit'); });
Еще один из вариантов использования middleware - это через специальный метод класса Route, который так и называется middleware()
Route::get('home/edit', 'HomeController@edit')->middleware('admin');
Возможно смешивание различных вариантов использования. Рассмотрим группу маршрутов, закрытую от неавторизированного пользователя с помощью middleware auth, и один маршрут из группы дополнительно закроем с помощью middleware admin:
Route::group(['middleware' => ['auth']], function () { Route::get('home', 'HomeController@index'); Route::get('home/edit', 'HomeController@edit')->middleware('admin'); });
Далее рассмотрим, как передвать переменные из middleware в контроллеры. Для этого можно использовать объект $request:
public function handle($request, Closure $next, $guard = null) { $picture = 'pic.jpg'; $request->merge(compact('picture')); return $next($request); }
После чего в методах контроллера можно обращаться к тому же объекту $request, и извлекать свойства. Предворительно класс Request должен быть загружен.
public function getIndex(Illuminate\Http\Request $request) { echo $request->picture; }
При создании контроллеров с помощью artisan, класс контроллера поставляется с подключенным классом Request. Тогда входящим параметром в методе прописываем только имя класса.
namespace App\Http\Controllers; use Illuminate\Http\Request class MyController extends Controller{ public function getIndex(Request $request) { echo $request->picture; } }