Как настроить параллельный прослушиватель rabbitmq в Spring Boot?

#spring-boot #rabbitmq

#spring-boot #rabbitmq

Вопрос:

Я настроил минимальный проект Spring Boot с поддержкой RabbitMQ, и мой потребитель выглядит так:

 package app.mq.consumers;

import org.springframework.stereotype.Component;
import org.springframework.amqp.rabbit.annotation.RabbitListener;
import java.util.Date;

@Component
public final class StdoutConsumer {

  @RabbitListener(
    queues = {"stdout-q"},
    concurrency = "5",
    autoStartup = "true",
    exclusive = false
  )
  public void receiveMessage(Object message) throws Exception {
    Thread.sleep(1000);
    System.out.println(new Date());
  }
}
  

Он просто спит 1 секунду и выводит временную метку в стандартный вывод.

И вот application.yml :

 spring:
  rabbitmq:
    host: localhost
    port: 5672
    username: guest
    password: guest
  

Вот и все. Все остальное абсолютно нетронуто.

Я отправил 30 сообщений в RabbitMQ, затем запустил приложение Spring Boot, и я ожидал увидеть 5 временных меток, напечатанных примерно в одно и то же время (потому что я установил значение concurrency "5" ), а через 1 секунду следующие 5 временных меток и так далее и тому подобное. Однако я увидел, что временные метки печатаются одна за другой, причем интервал между любыми 2 временными метками составляет примерно 1 секунду. Если я изменю код на режим ожидания на 5 секунд, то интервал между каждыми 2 временными метками составит 5 секунд.

Предварительно заполненная очередь RabbitMQ

Напечатаны временные метки

Однако, когда я впервые запускаю приложение Spring Boot, а затем быстро отправляю сообщения в MQ, 5 потребителей работают одновременно.

Заполнять очередь на лету

Потребители работают одновременно

Я предполагаю, что проблема возникает на этапе инициализации потребителей, но почему Spring Framework инициализирует потребителей всех сразу? Как я могу заставить их запускаться сразу, а не по одному?

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

1. При проверке документации ( docs.spring.io/spring-amqp/reference/html/#listener-concurrency ), насколько я понимаю, контейнер ждет некоторое время, прежде чем добавлять потребителей. Можете ли вы попробовать с большим количеством сообщений (возможно, 20) и проверить, есть ли у вас в конечном итоге больше потребителей.

2. @SherifBehna Я действительно пробовал это, с 30 сообщениями в MQ, и на их печать ушло 30 секунд. Забавно, что если я сначала запускаю приложение spring boot, а затем быстро загружаю множество сообщений в MQ, потребители работают одновременно.