Loading

Spring Boot:整合RabbitMQ

一.pom.xml

    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.3.0.RELEASE</version>
        <relativePath/> <!-- lookup parent from repository -->
    </parent>
    <groupId>com.wj</groupId>
    <artifactId>boot-rabbit</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <name>boot-rabbit</name>
    <description>Demo project for Spring Boot</description>

    <properties>
        <java.version>1.8</java.version>
    </properties>

    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-amqp</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
            <exclusions>
                <exclusion>
                    <groupId>org.junit.vintage</groupId>
                    <artifactId>junit-vintage-engine</artifactId>
                </exclusion>
            </exclusions>
        </dependency>
        <dependency>
            <groupId>org.springframework.amqp</groupId>
            <artifactId>spring-rabbit-test</artifactId>
            <scope>test</scope>
        </dependency>
    </dependencies>

二.application.yml

spring:
rabbitmq:
addresses: amqp://guest:guest@192.168.10.132:5672
virtual-host: /
connection-timeout: 10000
#生产端配置
publisher-confirm-type: CORRELATED #实现一个监听器用于监听Broker端给我们返回确认请求
publisher-returns: true #保证消息对Broker端是可达的
template:
mandatory: true #这个属性必须设置为true,才能保证监听有效
#消费端配置
listener:
simple:
#配置手工确认模式,用于ACK的手工处理
acknowledge-mode: manual
#配置消费端监听个数和最大个数用于控制消费端并发情况
concurrency: 5
max-concurrency: 10

三.配置类

@Configuration
public class MainConfig {

    @Bean
    public TopicExchange topicExchange(){
        return new TopicExchange("boot-exchange",true,false);
    }

    @Bean
    public Queue queue(){
        return new Queue("boot.queue",true) ;
    }

    @Bean
    public Binding binding(){
        return BindingBuilder.bind(this.queue()).to(topicExchange()).with("springboot.#");
    }
}

四.生产端代码

生产者类:

@Component
public class Producer {

    @Autowired
    private RabbitTemplate rabbitTemplate;

    RabbitTemplate.ConfirmCallback confirmCallback = (correlationData, ack, cause) -> {
        System.out.println(correlationData);
        System.out.println(ack);
        if(!ack){
            System.out.println("异常处理中。。");
        }
    };

    ReturnCallback returnCallback = (message, replyCode, replyText, exchange, routingKey) -> {
        System.out.println(exchange +":"+routingKey);
        System.out.println(replyCode+":"+replyText);
        System.out.println(new String(message.getBody()));
    };

    public void send(Object message, Map<String,Object> properties){
        MessageHeaders headers = new MessageHeaders(properties);
        Message msg = MessageBuilder.createMessage(message, headers);
        rabbitTemplate.setConfirmCallback(confirmCallback);
        rabbitTemplate.setReturnCallback(returnCallback);
        //消息的全局唯一id
        CorrelationData correlationData = new CorrelationData(UUID.randomUUID().toString());
        rabbitTemplate.convertAndSend("boot-exchange","springboot.rabbit",msg,correlationData);
    }
}

测试代码:

    @Autowired
    private Producer producer;

    @Test
    public void testSend(){
        Map<String, Object> map = new HashMap<>();
        map.put("name","wj");
        map.put("id","1234");
        producer.send("hello spring boot amqp",map);
    }

测试结果:

五.消费端代码

 消费端监听注解@RabbitListener

@Component
public class Consumer {
    @RabbitListener(
            bindings = @QueueBinding(
                value = @Queue(value = "boot.queue", durable = "true")
                , exchange = @Exchange(
                    value = "boot-exchange"
                    ,type = "topic"
                    ,ignoreDeclarationExceptions = "true"
                    )
                ,key = "springboot.#"
            )
    )
    @RabbitHandler
    public void onMessage(Message message, Channel channel){
        Long deliveryTag = (Long) message.getHeaders().get(AmqpHeaders.DELIVERY_TAG);
        System.out.println(message.getPayload());
    }
}

六.发送实体类消息

注意:实体类需要实现序列化接口,否则报错

生产端:

    public void sendUser(User user,Map<String,Object> properties){
        //消息的全局唯一id
        CorrelationData correlationData = new CorrelationData(UUID.randomUUID().toString());
        rabbitTemplate.convertAndSend("boot-exchange","springboot.rabbit",user,correlationData);
    }

消费端:

    @RabbitListener(
            bindings = @QueueBinding(
                    value = @Queue(value = "boot.queue", durable = "true")
                    , exchange = @Exchange(
                    value = "boot-exchange"
                    ,type = "topic"
                    ,ignoreDeclarationExceptions = "true"
            )
                    ,key = "springboot.#"
            )
    )
    @RabbitHandler
    public void onMessage(@Payload User user, Channel channel, @Headers Map<String,Object> properties){
        System.out.println(user);
        System.out.println(properties.get(AmqpHeaders.DELIVERY_TAG));
    }

测试:

    @Test
    public void sendUser(){
        User user = new User("张三", 12);
        producer.sendUser(user,null);
    }
posted @ 2020-06-03 14:31  秋风飒飒吹  阅读(233)  评论(0编辑  收藏  举报