Почему команды и события представлены отдельно? - PullRequest
62 голосов
/ 11 февраля 2011

В чем разница между командами и событиями в архитектурах, которые подчеркивают события?Единственное различие, которое я вижу, состоит в том, что команды обычно создаются / вызываются субъектами вне системы, в то время как события, похоже, создаются обработчиками и другим кодом в системе.Однако во многих примерах приложений, которые я видел, они имеют разные (но функционально похожие) интерфейсы.

Ответы [ 7 ]

131 голосов
/ 11 февраля 2011

Команды могут быть отклонены.

События произошли.

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

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

Я вижу, что команды обычно получены / вызваны актерами вне система, тогда как события кажутся получены от обработчиков и другого кода в система

Это еще одна причина, по которой они представлены отдельно. Концептуальная ясность.

Команды и события являются сообщениями. Но на самом деле это отдельные понятия, и понятия должны быть смоделированы в явном виде.

5 голосов
/ 28 декабря 2016

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

Скажем, например, что после создания Customer вы также хотите инициализировать некоторые значения учетных записей и т. Д. После того, как ваш Customer AR добавит событие в EventDispatcher, и оно будет получено объектом CustomerCreatedEventHandler, этот обработчик может вызвать отправку команда, которая выполнит все, что вам нужно и т. д.

Кроме того, существуют DomainEvents и ApplicationEvents. Разница просто концептуальная. Сначала вы хотите отправить все события вашего домена (некоторые из них могут вызывать события приложения). Что я имею в виду под этим?

Инициализация учетной записи после события CustomerCreatedEvent является событием DOMAIN. Отправка клиенту уведомления по электронной почте является событием подачи заявки.

Причина, по которой вы не должны смешивать их, ясна. Если ваш SMTP-сервер временно не работает, это не означает, что это повлияет на вашу ОПЕРАЦИЮ ДОМЕНА. Вы по-прежнему хотите сохранить неиспорченное состояние своих агрегатов.

Обычно я добавляю события в мой Диспетчер на уровне совокупного корня. Это события DomainEvents или ApplicationEvents. Может быть и то, и другое. Как только мой обработчик команд завершен, и я вернулся в стек с кодом, который выполняет обработчик команд, я проверяю свой диспетчер и отправляю любое другое DomainEvent. Если все это успешно, то я закрываю транзакцию.

Если у меня есть какие-либо события приложений, самое время их отправить. Отправка электронного письма не обязательно требует открытого соединения с базой данных или открытой области транзакции.

Я немного отошел от первоначального вопроса, но вам также важно понять, как события могут также концептуально трактоваться по-разному.

Тогда у вас есть саги .... но это WAYYYY за рамками этого вопроса:)

Имеет ли это смысл?

4 голосов
/ 01 декабря 2014

Проработав несколько примеров и особенно презентацию Грега Янга (http://www.youtube.com/watch?v=JHGkaShoyNs)), я пришел к выводу, что команды являются избыточными. Это просто события от вашего пользователя, они нажимали эту кнопку. Вы должны сохранить они точно так же, как и другие события, потому что это данные, и вы не знаете, захотите ли вы использовать их в будущем. Ваш пользователь добавил, а затем удалил этот элемент из корзины или, по крайней мере, попытался. Позже вы можете захотеть использовать эту информацию, чтобы напомнить пользователю об этом позже.

2 голосов
/ 05 июля 2016

В дополнение к упомянутым выше концептуальным различиям, я думаю, есть еще одно отличие, связанное с общими реализациями:

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

Команды, возможно, не должны обрабатываться таким образом. Создатель команды обычно имеет доступ к предполагаемому исполнителю команды. Это может быть, например, в форме очереди сообщений для исполнителя. Таким образом, команда предназначена для одного объекта .

2 голосов
/ 11 февраля 2011

Они представлены отдельно, потому что они представляют очень разные вещи. Как сказал @qstarin, команды - это сообщения, которые могут быть отклонены, и в случае успеха произойдет событие. Команды и события - это Dtos, они являются сообщениями, и они имеют тенденцию выглядеть очень похожими при создании и создании сущности, однако с тех пор не обязательно.

Если вы беспокоитесь о повторном использовании, то вы можете использовать команды и события в качестве конвертов для вашей (Messge) полезной нагрузки

class CreateSomethingCommand
{
    public int CommandId {get; set;}

    public SomethingEnvelope {get; set;}
 }

однако, я хотел бы знать, почему вы спрашиваете: D у вас слишком много команд / событий?

1 голос
/ 24 марта 2019

Событие - это факт из прошлого.

Команда является только запросом и, следовательно, может быть отклонена.

Важной характеристикой команды является то, что она должна обрабатываться только один разодин приемник.Это потому, что команда - это отдельное действие или транзакция, которую вы хотите выполнить в приложении.Например, одна и та же команда создания заказа не должна обрабатываться более одного раза.Это важное различие между командами и событиями.События могут обрабатываться несколько раз, потому что многие системы или микросервисы могут быть заинтересованы в этом событии.'msdn'

1 голос
/ 28 декабря 2016

Я думаю, что кое-что добавить к ответу Квентина-Сантина состоит в том, что они:

Инкапсулирует запрос как объект, что позволяет вам параметризировать клиенты с разными запросами, очередями или журналами запросов и поддержкой отменяемые операции.

Источник .

...