CQRS / ES - обработка ошибок проекции

Я работаю над системой CQRS + ES, в основном используя фреймворк аксонов, но на самом деле этот вопрос относится к любой реализации. Итак, у меня есть обработчик команд и 1 или несколько обработчиков событий, работающих на разных JVM, контейнерах и т. Д., И в какой-то момент один из этих обработчиков обнаруживает ошибку.

У нас есть два случая: «ожидаемая» бизнес-ошибка и «неожиданная» системная ошибка. Насколько я понимаю, сейчас мы находимся в асинхронном обработчике, и событие теперь является фактом, поэтому на самом деле мы не можем напрямую откатить команду ни в одном случае (поскольку это может повлечь за собой откат во многих других проекциях и нарушение CQRS).

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

В качестве примера предположим, что у нас есть команда, которая обновляет кредит клиента. Событие публикуется, одна проекция обновляет свою статистику «общего количества кредитов», другая публикует обновление для некоторого веб-сокета для пользовательского интерфейса и, наконец, еще одна проекция, которая поддерживает состояние кредита - и этот последний обработчик не работает. Должны ли мы отправить команду на откат бизнес-транзакции и снова вычесть кредит, снова обновить веб-узел и т. Д.? А в случае аксона есть ли способ, которым это фиксируется как транзакция?


person james-farrugia    schedule 29.05.2018    source источник


Ответы (1)


Я бы сказал, что принятие решения о том, является ли выполнение действия, таким образом, обработка команды, правильным, всегда должно приниматься Командной моделью / Агрегатом. Агрегат, находящийся в неправильном состоянии для обработки действия, обычно приводит к «бизнес-исключению / ошибке».

Однако, если вы будете принимать решения при сбое обработки событий, вы добавляете некоторую логику принятия решений в службу обработки событий, которая в большинстве случаев, вероятно, не заботится. Если такие службы обработки событий обновляют модели представлений / запросов, но не делают этого, я бы сказал, что это не веская причина для публикации «компенсирующей команды» в вашем агрегате для «отката / отмены события».

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

С точки зрения Axon Framework, вы можете заключить свой CreditStateEventHandler в TrackingEventProcessor и вызвать сброс этого процессора событий, вызвав функцию TrackingEventProcessor#resetTokens(). Это исходит из того, что исключение, из-за которого ваш CreditStateEventHandler, конечно же, вызвано ошибочным кодированием, в противном случае повторное воспроизведение привело бы к точно такому же исключению.

person Steven    schedule 30.05.2018