Spring Нужно ли мне использовать EventListener вместо Async?

#spring-boot #events #spring-transactions #spring-async

#spring-boot #Мероприятия #spring-транзакции #spring-асинхронный

Вопрос:

Я работаю с приложением, которое использует Spring ApplicationEventPublisher для публикации сообщений. У нас будут функции, которые выполняют некоторые сложные функции чтения / обновления в rdbms, а затем публикуют это сообщение для выполнения такой работы, как отправка электронной почты пользователям или даже публикация сообщений sqs для других микросервисов.

 ApplicationEventPublisher eventPublisher;
UpdateEvent event = UpdateEvent.builder().eventSource("SomeUpdate")
                    .scenarioId(scenarioId).build();
eventPublisher.publishEvent(event);
  

и прослушиватель:

 public interface LocalMessageHandlingAsyncService {

    @TransactionalEventListener
    void publishUpdateEvent(UpdateEvent mediaPlanUpdateEvent);

  

Поскольку некоторые события будут выполнять операции чтения из базы данных вокруг данных, с которыми мы только что работали, мы используем @TransactionalEventListener , чтобы убедиться, что мы работаем с последними зафиксированными данными. Когда я смотрю на этот тип шаблона, мне интересно, в чем преимущество этого по сравнению с простым вызовом отдельного асинхронного метода?

С помощью асинхронного метода нам не нужно беспокоиться о сериализации объектов в json или создании отдельных объектов событий для управления. Нам все еще приходится беспокоиться об открытых транзакциях, но, я полагаю, это решаемо с помощью TransactionSynchronizationManager.

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

Ответ №1:

Как вы упомянули, с одним потребителем этот шаблон проектирования мало что дает для таблицы.

Однако я предложу кое-что другое: Spring Integration

Используя Spring Integration, вы можете создавать конвейеры и фактически интегрировать такие задачи, как отправка электронной почты пользователям и публикация сообщения в SQS, в другие микросервисы изначально. Это позволяет вам:

  1. Преобразование и обработка сообщения в промежутках между служебными задачами в одном приложении
  2. В случае необходимости используйте посредник сообщений, такой как RabbitMQ, для обработки рассылки одного и того же сообщения в 1. в распределенную среду (т. Е. Служба в 3. может быть запущена на другом компьютере и т.д. Или вы можете отправить и забыть)
  3. И в одной из ваших служебных задач вы действительно можете отправлять электронные письма и т.д.

Комментарии:

1. Хм, это кажется еще более накладным и сложным, чем публикация события! Я думаю, что асинхронный метод здесь все еще предпочтительнее

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