Иногда бывает необходимо добавить свои данные к текущему запросу в Laravel. Например, вы помещаете в мидлвар проверку, разрешен ли пользователю доступ к этой странице, и, затем, передаете эту «проверку» дополнительным параметром текущего запроса.
Таким образом, вы предотвращаете дублирование кода, не размещая один и тот же код (или запрос) в мидлваре и контроллере. Например, возьмем следующую ситуацию: я хочу дать доступ только пользователям, у которых is_active
установлен в «1
», соответственно, мне нужно дважды сделать следующий запрос.
SomeUserMiddleware.php
public function handle($request, Closure $next) { // получаем ID пользователя $userId = $request->route('id'); // находим пользователя $user = User::where('is_active', 1)->where('id', $userId)->first(); // проверяем, существует ли залогиненный пользователь if (!$user->exists()) { // редиректим, если не существует return redirect()->route('redirectRoute'); } return $next($request); }
UserController.php
public function view($id) { $user = User::where('is_active', 1)->where('id', $userId)->first(); return view('users.view', ['page' => $user]); }
Как вы видите, запрос на получение пользователя сделан дважды. Пустая трата ресурсов, не так ли?
Метод merge
Можно отрефакторить приведенный выше код, вызвав метод merge
в запросе и передав $user
из мидлвара следующим образом.
SomeUserMiddleware.php
public function handle($request, Closure $next) { //получаем ID пользователя $userId = $request->route('id'); //находим пользователя $user = User::where('is_active', 1)->where('id', $userId)->first(); // проверяем, существует ли залогиненный пользователь if (!$user->exists()) { // редиректим, если не существует return redirect()->route('redirectRoute'); } // передаем атрибут в запрос $request->merge(['user' => $user]); return $next($request); }
И получаем в контроллере, например так:
UserController.php
public function view($id) { return view('users.view', ['user' => $request->user]); }
Преимущество вышеизложенного способа заключается в том, что теперь нам нужно выполнить только одно обращение к базе данных и передать его результат в запрос, который можно будет повторно использовать в другом месте (в нашем случае, в контроллере). И, как дополнительный бонус, мы делаем наши контроллеры «тонкими»!
Автор: Amit Merchant
Перевод: Алексей Широков
Наш Телеграм-канал — следите за новостями о Laravel.