How to get Spring RabbitMQ to create a new Queue?

前端 未结 4 624
长发绾君心
长发绾君心 2020-12-06 09:46

In my (limited) experience with rabbit-mq, if you create a new listener for a queue that doesn\'t exist yet, the queue is automatically created. I\'m trying to use the Sprin

相关标签:
4条回答
  • 2020-12-06 10:12

    Can you add this after your connection tag, but before the listener:

    <rabbit:queue name="test" auto-delete="true" durable="false" passive="false" />
    

    Unfortunately, according to the XSD schema, the passive attribute (listed above) is not valid. However, in every queue_declare implementation I've seen, passive has been a valid queue_declare parameter. I'm curious to see whether that will work or whether they plan to support it in future.

    Here is the full list of options for a queue declaration: http://www.rabbitmq.com/amqp-0-9-1-reference.html#class.queue

    And here is the full XSD for the spring rabbit schema (with comments included): http://www.springframework.org/schema/rabbit/spring-rabbit-1.0.xsd

    0 讨论(0)
  • 2020-12-06 10:20

    As of Spring Boot 2.1.6 and Spring AMQP 2.1.7 you can create queues during startup if they don't exists with this:

    @Component
    public class QueueConfig {
    
        private AmqpAdmin amqpAdmin;
    
        public QueueConfig(AmqpAdmin amqpAdmin) {
            this.amqpAdmin = amqpAdmin;
        }
    
        @PostConstruct
        public void createQueues() {
            amqpAdmin.declareQueue(new Queue("queue_one", true));
            amqpAdmin.declareQueue(new Queue("queue_two", true));
        }
    }
    
    0 讨论(0)
  • 2020-12-06 10:24

    Older thread, but this still shows up pretty high on Google, so here's some newer information:

    2015-11-23

    Since Spring 4.2.x with Spring-Messaging and Spring-Amqp 1.4.5.RELEASE and Spring-Rabbit 1.4.5.RELEASE, declaring exchanges, queues and bindings has become very simple through an @Configuration class some annotations:

    @EnableRabbit
    @Configuration
    @PropertySources({
        @PropertySource("classpath:rabbitMq.properties")
    })
    public class RabbitMqConfig {    
        private static final Logger logger = LoggerFactory.getLogger(RabbitMqConfig.class);
    
        @Value("${rabbitmq.host}")
        private String host;
    
        @Value("${rabbitmq.port:5672}")
        private int port;
    
        @Value("${rabbitmq.username}")
        private String username;
    
        @Value("${rabbitmq.password}")
        private String password;
    
        @Bean
        public ConnectionFactory connectionFactory() {
            CachingConnectionFactory connectionFactory = new CachingConnectionFactory(host, port);
            connectionFactory.setUsername(username);
            connectionFactory.setPassword(password);
    
            logger.info("Creating connection factory with: " + username + "@" + host + ":" + port);
    
            return connectionFactory;
        }
    
        /**
         * Required for executing adminstration functions against an AMQP Broker
         */
        @Bean
        public AmqpAdmin amqpAdmin() {
            return new RabbitAdmin(connectionFactory());
        }
    
        /**
         * This queue will be declared. This means it will be created if it does not exist. Once declared, you can do something
         * like the following:
         * 
         * @RabbitListener(queues = "#{@myDurableQueue}")
         * @Transactional
         * public void handleMyDurableQueueMessage(CustomDurableDto myMessage) {
         *    // Anything you want! This can also return a non-void which will queue it back in to the queue attached to @RabbitListener
         * }
         */
        @Bean
        public Queue myDurableQueue() {
            // This queue has the following properties:
            // name: my_durable
            // durable: true
            // exclusive: false
            // auto_delete: false
            return new Queue("my_durable", true, false, false);
        }
    
        /**
         * The following is a complete declaration of an exchange, a queue and a exchange-queue binding
         */
        @Bean
        public TopicExchange emailExchange() {
            return new TopicExchange("email", true, false);
        }
    
        @Bean
        public Queue inboundEmailQueue() {
            return new Queue("email_inbound", true, false, false);
        }
    
        @Bean
        public Binding inboundEmailExchangeBinding() {
            // Important part is the routing key -- this is just an example
            return BindingBuilder.bind(inboundEmailQueue()).to(emailExchange()).with("from.*");
        }
    }
    

    Some sources and documentation to help:

    1. Spring annotations
    2. Declaring/configuration RabbitMQ for queue/binding support
    3. Direct exchange binding (for when routing key doesn't matter)

    Note: Looks like I missed a version -- starting with Spring AMQP 1.5, things get even easier as you can declare the full binding right at the listener!

    0 讨论(0)
  • 2020-12-06 10:34

    What seemed to resolve my issue was adding an admin. Here is my xml:

    <rabbit:listener-container connection-factory="rabbitConnectionFactory"  >
        <rabbit:listener ref="orderQueueListener" queues="test.order" />
    </rabbit:listener-container>
    
    <rabbit:queue name="test.order"></rabbit:queue>
    
    <rabbit:admin id="amqpAdmin" connection-factory="rabbitConnectionFactory"/>
    
    <bean id="orderQueueListener" class="com.levelsbeyond.rabbit.OrderQueueListener">   
    </bean>
    
    0 讨论(0)
提交回复
热议问题