Подтвердить что ты не робот

Какая разница между командами и событиями в контексте Laravel 5?

Итак, вчера был выпущен Laravel 5 с окончательной реализацией командной шины, но я блуждал, какова реальная разница в использовании командной шины над механизмами событий, которые у нас есть в предыдущих выпусках?

Хорошо, я вижу причину, по которой он может быть использован для создания команд из объектов Request, которые очень полезны, но помимо этого он, похоже, ведет себя аналогичным образом вплоть до всей функциональности очередей для событий сейчас?

Можете ли вы привести примеры случаев использования и где есть плюсы и минусы?

4b9b3361

Ответ 1

  • Команды должны произойти прямо сейчас. т.е. "CreateUser"
  • События - это вещи, которые только что произошли прямо сейчас, то есть "UserSuccessfullyCreated"

Различия выглядят незначительными - но имеют некоторые ключевые отличия.

  • Команды должны быть специально вызваны/отправлены. То есть если ты хочешь do CommandX - вы должны вызвать CommandX где-то.
  • События отвечают на событие, запускаемое в любом месте приложения. Самое замечательное, что несколько классов обработки событий могут реагировать на одно и то же событие.

Давайте сделаем пример, чтобы лучше проиллюстрировать его. Допустим, мы создаем пользователя, и мы хотим отправить им приветственное письмо, а также обновить список рассылок.

В командном сценарии было бы

AdminController {

    function create() {
            Bus::dispatch(new CreateUser(Auth::user());
    }
}

то в нашем CommandClass мы будем делать

public function handle(CreateUser $auth)
{
     // 1. Create the user here
     // 2. Send welcome email
     // 3. Update our newsletter
}

Но если мы используем события - мы бы сделали что-то подобное в нашем CommandClass

public function handle(CreateUser $auth)
    {
         // 1. Create the user here
         Event::fire(new UserWasCreated($user));
    }

тогда мы можем создать столько событий, сколько хотим прослушать это событие, и сделать что-то:

EventClassA

Event::listen('UserWasCreated', function($event)
{
    // 2. Send welcome email
});

EventClassB

Event::listen('UserWasCreated', function($event)
{
    // 3. Update our newsletter
});

Самое замечательное - разделение проблем. Теперь команде "createuser" не нужно беспокоиться о том, что происходит после создания пользователя. Это просто нужно CreateUser.

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

EventClassC

Event::listen('UserWasCreated', function($event)
{
    // 4. Register them in lotto
});

Обратите внимание, что нам не нужно было вообще прикасаться к коду кода CreateUser команды? Это обеспечивает истинную проблему разделения классов в стиле ООП.

Ответ 2

Я просто хочу поделиться своим пониманием этой концепции над правильным ответом:

Основное отличие состоит в том, что команды могут изменять состояние модели, а события просто реагируют на изменение состояния.

КОМАНДЫ:

Команды в Laravel представляют реализацию шаблона Command.

Основные преимущества команд:

  • Доступ к ним можно получить где угодно
  • Их очень легко прочитать любой другой разработчик

Чтобы создать команду в Laravel 5:

Вам нужно сгенерировать команду DTO (которая может реализовать интерфейс SelfHandling). Используя php artisan make:command {command-name}

Пример: php artisan make:command Course/PostCourseCommand

Соглашение об именах для команд: говорить на бизнес-языке и добавлять к нему постфиксную команду

Чтобы вызвать (отправить) команду с вашего контроллера, вы можете использовать:

$this->dispatch(new PostCourseCommand())

или

Bus::dispatch(new PostCourseCommand());

Боковое примечание: Функция "Отправка из запроса" - отличный способ пропустить передачу переменных в конструктор команд один за другим, вместо этого он разрешит это для вас:

Пример:

$test_request = Request::create('/test', 'GET', [
   'name' => 'Mahmoud',
   'nickname' => 'Mega'
]);

$result = Bus::dispatchFrom(
   CreateCourse::class, $test_request
);

Наконец:

Вы можете отделить функцию обработчика и его логику от команды DTO до каталога Handlers, чтобы сделать это:

  • Сгенерировать обработчик команд с помощью мастера

art handler:command --command="Course/PoatCourseCommand"

  1. удалите интерфейс SelfHandling из класса Command, чтобы он искал обработчик для его обработки.

СОБЫТИЯ:

События в Laravel представляют реализацию шаблона Observer.

Чтобы создать событие в Laravel 5:

  • use artisan: art make:event {event-name}

Пример: art make:event LogSomething

  1. сгенерировать обработчик события для этого события

art handler:event LogSomething --event="LogSomething"

  1. зарегистрировать событие и его обработчик в службе событийных служб (app/Providers/EventServiceProvider.php)

Пример:

protected $listen = [    
   \Zzz\Events\LogSomething::class => [ // event.name
      \Zzz\Handlers\Events\LogSomething::class, //EventListener
   ],
],    

Чтобы вызвать (запустить) событие:

использование:

Event::fire(New LogSomething());

или вы можете использовать помощник события

event(New LogSomething());

Боковое примечание: в качестве альтернативы вы можете сгенерировать событие, просто зарегистрировав событие у поставщика услуг, затем выполните эту команду.

php artisan event:generate < это автоматически добавит вам два класса.

Также вы можете прослушивать событие без создания обработчика событий или регистрации листера в массиве слушателей, просто перейдя к службе проверки событий и внутри функции загрузки, записывая ваше событие и его действие (НЕ РЕКОМЕНДУЕТСЯ). Пример:

Event::listen('XXX\Events\DoSomethingElse', function($event)
{
    dd('handle me :)');
});

Наконец: вы можете поставить в очередь событие или даже подписаться на несколько событий из самого класса.