springboot2.1.0、RabbitMQ确认机制

一)pom.xml文件和上一篇章保持不变

二)application.properties增加几个确认机制的配置

server.port=8080

spring.application.name=spring-boot-rabbitmq

spring.rabbitmq.host=localhost
spring.rabbitmq.port=5672
spring.rabbitmq.username=rabbitmq
spring.rabbitmq.password=rabbitmq

spring.rabbitmq.publisher-confirms=true
spring.rabbitmq.publisher-returns=true

# ACK
spring.rabbitmq.listener.direct.acknowledge-mode=manual
spring.rabbitmq.listener.simple.acknowledge-mode=manual

 

第三步:改造一下Fanout模式的代码

package com.oysept.springboot.fanout.config;

import org.springframework.amqp.core.Binding;
import org.springframework.amqp.core.BindingBuilder;
import org.springframework.amqp.core.FanoutExchange;
import org.springframework.amqp.core.Queue;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

/**
 * Fanout Exchange: 广播模式或者订阅模式,给Fanout交换机发送消息,绑定了这个交换机的所有队列都收到这个消息。
 * @author ouyangjun
 */
@Configuration
public class FanoutRabbitMQConfig {

    @Bean
    public Queue AMsg() {
        return new Queue("fanout.A");
    }

    @Bean
    public Queue BMsg() {
        return new Queue("fanout.B");
    }

    @Bean
    public Queue CMsg() {
        return new Queue("fanout.C");
    }

    @Bean
    FanoutExchange fanoutExchange() {
        return new FanoutExchange("fanoutExchange");
    }

    @Bean
    Binding bindingExchangeA(Queue AMsg,FanoutExchange fanoutExchange) {
        return BindingBuilder.bind(AMsg).to(fanoutExchange);
    }

    @Bean
    Binding bindingExchangeB(Queue BMsg, FanoutExchange fanoutExchange) {
        return BindingBuilder.bind(BMsg).to(fanoutExchange);
    }

    @Bean
    Binding bindingExchangeC(Queue CMsg, FanoutExchange fanoutExchange) {
        return BindingBuilder.bind(CMsg).to(fanoutExchange);
    }
}
package com.oysept.springboot.fanout.receiver;

import java.io.IOException;
import java.util.Date;

import org.springframework.amqp.core.Message;
import org.springframework.amqp.rabbit.annotation.RabbitHandler;
import org.springframework.amqp.rabbit.annotation.RabbitListener;
import org.springframework.stereotype.Component;

import com.rabbitmq.client.Channel;

/**
 * 给fanout.A队列推送消息
 * @author ouyangjun
 */
@Component
@RabbitListener(queues = "fanout.A")
public class HelloAMsgReceiver {

    // 接收字符串消息,确认消息收到之后,把消息从队列中移除,如未移除,项目重启之后还会继续推送消息
    @RabbitHandler
    public void process(String str, Channel channel, Message message) {
        System.out.println("-->HelloAMsgReceiver AAAA Println: " + str +", 收到时间: " + new Date());
        
        try {
            // 告诉服务器收到这条消息 已经被我消费了 可以在队列删掉 这样以后就不会再发了 否则消息服务器以为这条消息没处理掉 后续还会在发
            // 消息的标识,false只确认当前一个消息收到,true确认所有consumer获得的消息
            channel.basicAck(message.getMessageProperties().getDeliveryTag(), false);
            System.out.println("-->HelloAMsgReceiver AAAA SUCCESS!");
        } catch (IOException e) {
            e.printStackTrace();
            // ack返回false,并重新回到队列
            // channel.basicNack(message.getMessageProperties().getDeliveryTag(), false, true);
            // 拒绝消息
            // channel.basicReject(message.getMessageProperties().getDeliveryTag(), true);
            System.out.println("-->HelloAMsgReceiver AAAA FAIL!");
        }
    }
}
package com.oysept.springboot.fanout.receiver;

import java.io.IOException;
import java.util.Date;

import org.springframework.amqp.core.Message;
import org.springframework.amqp.rabbit.annotation.RabbitHandler;
import org.springframework.amqp.rabbit.annotation.RabbitListener;
import org.springframework.stereotype.Component;

import com.rabbitmq.client.Channel;

/**
 * 给fanout.B队列推送消息
 * @author ouyangjun
 */
@Component
@RabbitListener(queues = "fanout.B")
public class HelloBMsgReceiver {
	
    // 接收字符串消息,确认消息收到之后,把消息从队列中移除,如未移除,项目重启之后还会继续推送消息
    @RabbitHandler
    public void process(String str, Channel channel, Message message) {
        System.out.println("-->HelloBMsgReceiver BBBB Println: " + str +", 收到时间: " + new Date());
        
        try {
            // 告诉服务器收到这条消息 已经被我消费了 可以在队列删掉 这样以后就不会再发了 否则消息服务器以为这条消息没处理掉 后续还会在发
            // 消息的标识,false只确认当前一个消息收到,true确认所有consumer获得的消息
            channel.basicAck(message.getMessageProperties().getDeliveryTag(), false);
            System.out.println("-->HelloBMsgReceiver BBBB SUCCESS!");
        } catch (IOException e) {
            e.printStackTrace();
            // ack返回false,并重新回到队列
            // channel.basicNack(message.getMessageProperties().getDeliveryTag(), false, true);
            // 拒绝消息
            // channel.basicReject(message.getMessageProperties().getDeliveryTag(), true);
            System.out.println("-->HelloBMsgReceiver BBBB FAIL!");
        }
    }
}
package com.oysept.springboot.fanout.receiver;

import org.springframework.amqp.core.Message;
import org.springframework.amqp.rabbit.annotation.RabbitHandler;
import org.springframework.amqp.rabbit.annotation.RabbitListener;
import org.springframework.stereotype.Component;

import com.rabbitmq.client.Channel;

/**
 * 给fanout.C队列推送消息
 * @author ouyangjun
 */
@Component
@RabbitListener(queues = "fanout.C")
public class HelloCMsgReceiver {
	
    // 接收字符串消息,确认消息收到之后,把消息从队列中移除,如未移除,项目重启之后还会继续推送消息
    @RabbitHandler
    public void process(String str, Channel channel, Message message) {
        System.out.println("-->HelloCMsgReceiver CCCC Println: " + str);
    }
}
package com.oysept.springboot.fanout.sender;

import org.springframework.amqp.rabbit.connection.CorrelationData;
import org.springframework.amqp.rabbit.core.RabbitTemplate;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

/**
 * Fanout Exchange模式, @Component中的命名主要是为了避免冲突
 * @author ouyangjun
 */
@Component(value="fanoutSenderConfirm")
public class HelloSenderConfrim implements RabbitTemplate.ConfirmCallback {

    // 用RabbitTemplate,而不用AmqpTemplate
    @Autowired
    private RabbitTemplate rabbitTemplate;
	
    public void send() {
        String str = "Hello Fanout Exchange Msgs Confirm!";
        this.rabbitTemplate.setConfirmCallback(this);
		
        // 调用
        this.rabbitTemplate.convertAndSend("fanoutExchange", "", str);
    }

    @Override
    public void confirm(CorrelationData correlationData, boolean ack, String cause) {
        if (!ack) {
            System.out.println("HelloSenderConfrim Confirm 消息发送失败。" + cause + correlationData.toString());
        } else {
            System.out.println("HelloSenderConfrim Confirm 消息发送成功。 ");
        }
    }
}
package com.oysept.springboot.fanout.sender;

import org.springframework.amqp.core.Message;
import org.springframework.amqp.rabbit.core.RabbitTemplate;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

/**
 * Fanout Exchange模式, @Component中的命名主要是为了避免冲突
 * @author ouyangjun
 */
@Component(value="fanoutSenderReturn")
public class HelloSenderReturn implements RabbitTemplate.ReturnCallback {

    // 用RabbitTemplate,而不用AmqpTemplate
    @Autowired
    private RabbitTemplate rabbitTemplate;
	
    public void send() {
        String str = "Hello Fanout Exchange Msgs Return!";
		
        this.rabbitTemplate.setReturnCallback(this);
        this.rabbitTemplate.setConfirmCallback((correlationData, ack, cause) -> {
            if (!ack) {
                System.out.println("HelloSenderReturn Return 消息发送失败。" + cause + correlationData.toString());
            } else {
                System.out.println("HelloSenderReturn Return 消息发送成功。 ");
            }        
        });
        // 调用
        this.rabbitTemplate.convertAndSend("fanoutExchange", "", str);
    }
	
    @Override
    public void returnedMessage(Message message, int i, String s, String s1, String s2) {
        System.out.println("-->HelloSenderReturn return success" + message.toString()+"==="+i+"==="+s1+"==="+s2);    
    }
}

 

先启动springboot项目,再运行测试工具类

package com.oysept.springboot.test;

import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.junit4.SpringRunner;

import com.oysept.springboot.fanout.sender.HelloSenderConfrim;
import com.oysept.springboot.fanout.sender.HelloSenderReturn;

@RunWith(SpringRunner.class)
@SpringBootTest
public class FanoutHelloTest {

    @Autowired
    private HelloSenderReturn helloSenderReturn;
	
    @Autowired
    private HelloSenderConfrim helloSenderConfrim;
	
    // 测试
    @Test
    public void helloMsgReturn() throws Exception {
        helloSenderReturn.send();
    }

    // 测试
    @Test
    public void helloMsgConfirm() throws Exception {
        helloSenderConfrim.send();
    }
}

 

识别二维码关注个人微信公众号

本章完结,待续,欢迎转载!
 
本文说明:该文章属于原创,如需转载,请标明文章转载来源!

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值