
События в Laravel представлены реализацией паттерна Observer, что позволяет подписываться и прослушивать события приложения. Как правило, классы событий находятся в папке app/Events, а классы обработчиков событий — в app/Listeners.
Регистрация.
Вначале нужно зарегистрировать событие и слушателя в EventServiceProvider (файл app\Providers\EventServiceProvider.php) в свойстве $listen:protected $listen = [ 'App\Events\onAddPost' => [ 'App\Listeners\AddPostListener', ], ];
Ключом является класс события, а значением класс слушатель. Можно указать несколько классов слушателей.
Чтобы не создавать их вручную, нужно выполнить команду в консоли:
php artisan event:generateэто создаст два указанных класса в указанных папках (в каталоге App).
Событие и слушатели, которые уже существуют, будут оставлены нетронутыми.
Класс события (namespace App\Events).
В созданном классе события (папка app/Events) в методе конструктора можно установить получение аргументов, которые нужны для выполнения кода события. Например получить объект текущего поста:public function __construct(Post $post) { $this->postId = $post->id; }
Данный аргумент нужно будет передать в метод вызова события:
Event::fire(new onAddPost($post));
об этом далее.
Так же, в конструкторе можно указать нужные зависимости.
Метод broadcastOn() применяется в случае использования широковещательных событий.
Класс слушателя события.
Слушатели событий принимают экземпляр события в свой метод handle(). Таким образом можно получить доступ к свойствам события:public function handle(onAddPost $event) { dump($event->postId); }
В данном методе нужно прописать весь код, который должен выполниться при наступлении события.
Можно остановить распространение события для следующих слушателей, если из метода handle() вернуть false.
Конструктор класса слушателя стоит использовать для внедрения зависимостей (автоматического получения объектов указанных классов)
public function __construct(Mailer $mailer) { $this->mailer = $mailer; }
Запуск события.
Чтобы запустить пользовательское событие, нужно в нужном месте кода разместить Event::fire(). В данный метод передается объект созданного события, которому можно передать нужные аргументы для его конструктора.Event::fire(new onAddPost($post));
можно использовать функцию-помощник:
event(new onAddPost($post));
Не забывать предоставлять доступ для все указанных классов:
use Event; ...
Метод boot() EventServiceProvider.
Если слушателей событий не много и их код не сложный, можно не создавать отдельные классы для события и его слушателя, а использовать метод boot().
В данном методе вызывается метод listen класса Event, которому первым аргументом передается название события, а вторым анонимная функция которая и содержит нужный функционал:
Event::listen('onMyEvent', function ($post) { dump($post); });
Пример вызова события в данном случае:
Event::fire('onMyEvent',$post);
Подписчики событий.
Подписчики событий — это классы, которые могут подписаться на множество событий из самого класса. Это позволяет определить несколько обработчиков событий в одном классе. Удобно использовать, если есть ряд однотипных событий, например действия связанные с моделью Post (добавление, удаление и др.)
Размещать данные классы желательно в папке app\Listeners с указанием соответствующего пространства имен.
Подписчики должны определить метод subscribe(), в который будет передан экземпляр диспетчера события.
Пример класса подписчика (файл app\Listeners\PostEventListener.php):
<?php namespace App\Listeners; class PostEventListener { public function onPostAdd($post) { dd($post); } public function onPostUpdate($post) { dd($post); } public function subscribe($events) { $events->listen('PostAdd', 'App\Listeners\PostEventListener@onPostAdd'); $events->listen('PostUpdate', 'App\Listeners\PostEventListener@onPostUpdate'); } }
Данный класс подписан на два события (создавать их классы отдельно не нужно):
PostAdd и PostUpdate
которые передаются первым аргументом для метода listen(). В качестве второго аргумента передается класс и метод обрабатывающий каждый из этих событий. В данном случае, они содержатся в текущем классе.
Класс подписчик нужно зарегистрировать. Для этого есть 2 способа:
1. Указать в EventServiceProvider (файл app\Providers\EventServiceProvider.php) в свойстве $subscribe:
protected $subscribe = [ 'App\Listeners\PostEventListener', ];
2. Указать в коде до вызова события:
Event::subscribe(new \App\Listeners\PostEventListener());
Вызов события осуществляется как обычно, методом fire():
Event::fire('PostAdd',$post);