Обработка событий

webman/event предоставляет изящный механизм событий, позволяя выполнять некоторую бизнес-логику без внедрения в код, достигая декомпозиции между бизнес-модулями. Типичный сценарий, например, при успешной регистрации нового пользователя достаточно опубликовать событие, например, user.register, и все модули смогут получить это событие и выполнить соответствующую бизнес-логику.

Установка

composer require webman/event

Подписка на события

Подписка на события настраивается через файл config/event.php

<?php
return [
    'user.register' => [
        [app\event\User::class, 'register'],
        // ...другие функции обработки событий...
    ],
    'user.logout' => [
        [app\event\User::class, 'logout'],
        // ...другие функции обработки событий...
    ]
];

Примечание:

  • user.register, user.logout и т. д. являются названиями событий, строкового типа, рекомендуется использовать строчные слова и разделять их точками (.)
  • Одно событие может соответствовать нескольким функциям обработки событий, порядок вызова соответствует порядку в конфигурации

Функции обработки событий

Функции обработки событий могут быть любыми методами класса, функциями, замыканиями и т. д.
Например, создайте класс обработки событий app/event/User.php (если директория не существует, создайте ее)

<?php
namespace app\event;
class User
{
    function register($user)
    {
        var_export($user);
    }

    function logout($user)
    {
        var_export($user);
    }
}

Публикация событий

Используйте Event::dispatch($event_name, $data); или Event::emit($event_name, $data); для публикации события, например

<?php
namespace app\controller;
use support\Request;
use Webman\Event\Event;
class User
{
    public function register(Request $request)
    {
        $user = [
            'name' => 'webman',
            'age' => 2
        ];
        Event::dispatch('user.register', $user);
    }
}

Существует два метода для публикации событий: Event::dispatch($event_name, $data); и Event::emit($event_name, $data);. Оба принимают одинаковые параметры.
Разница в том, что emit автоматически перехватывает исключения, это значит, что если одно событие имеет несколько функций обработки, и одна из функций вызывает исключение, это не повлияет на выполнение других функций обработки.
А dispatch не перехватывает исключения, любое исключение в текущей функции обработки события остановит выполнение следующей функции и выбросит исключение вверх.

Подсказка
Параметр $data может быть любыми данными, например, массивами, экземплярами класса, строками и т. д.

Прослушивание событий с помощью подстановочных знаков

Регистрация прослушивателей с подстановочными знаками позволяет вам обрабатывать несколько событий в одном слушателе. Например, в config/event.php можно настроить

<?php
return [
    'user.*' => [
        [app\event\User::class, 'deal']
    ],
];

Мы можем получить конкретное название события через второй параметр функции обработки $event_data

<?php
namespace app\event;
class User
{
    function deal($user, $event_name)
    {
        echo $event_name; // конкретное название события, например user.register, user.logout и т. д.
        var_export($user);
    }
}

Остановка вещания события

Когда мы возвращаем false в функции обработки события, это событие прекращает свое вещание.

Замыкания для обработки событий

Функции обработки событий могут быть как методами класса, так и замыканиями, например

<?php
return [
    'user.login' => [
        function($user){
            var_dump($user);
        }
    ]
];

Просмотр событий и слушателей

Используйте команду php webman event:list, чтобы увидеть все события и слушателей, настроенные в проекте.

Поддерживаемые диапазоны

Помимо основных плагинов проекта базовых плагинов и плагинов приложений, также поддерживается конфигурация event.php.
Конфигурационный файл базового плагина config/plugin/поставщик_плагина/имя_плагина/event.php
Конфигурационный файл плагина приложения plugin/имя_плагина/config/event.php

Обратите внимание

Обработка событий event не является асинхронной, event не подходит для обработки медленной бизнес-логики, медленная логика должна обрабатываться с помощью очередей сообщений, например, webman/redis-queue