RabbitMQ死信队列

死信队列

面试题: 你们是如何保证消息不丢失的?

1、什么是死信

在 RabbitMQ 中充当主角的就是消息,在不同场景下,消息会有不同地表现。

死信就是消息在特定场景下的一种表现形式,这些场景包括:

  1. 消息被拒绝访问,即消费者返回 basicNack 的信号时 或者拒绝basicReject

2. 消费者发生异常,超过重试次数 。 ( 其实spring框架调用的就是 basicNack**)**

  1. 消息的Expiration 过期时长或队列TTL过期时间。.ttl(20*1000) 进入的是 先进业务队列的数据

  2. 消息队列达到最大容量 .maxLength(5)

上述场景经常产生死信,即消息在这些场景中时,被称为死信。

2、什么是死信队列

死信队列就是用于储存死信的消息队列,在死信队列中,有且只有死信构成,不会存在其余类型的消息。

死信队列在 RabbitMQ 中并不会单独存在,往往死信队列都会绑定这一个普通的业务消息队列,当所绑定的消息队列中,有消息变成死信了,那么这个消息就会重新被死信交换机路由到指定的死信队列中去,我们可以通过对这个死信队列进行监听,从而手动的去对这一消息进行补偿。 人工干预

3、那么,我们到底如何来使用死信队列呢?

死信队列基本使用,只需要在声明业务队列的时候,绑定指定的死信交换机和RoutingKey即可。

java 复制代码
 @Bean //死信交换机
    public DirectExchange deadExchange() {
        return   ExchangeBuilder.directExchange("dead_ex").durable(true).build();
    }
    @Bean //死信队列
    public Queue deadQueue() {
        return  QueueBuilder.durable("dead_ordering_ok_wms").build();
    }
    @Bean //绑定死信队列与死信交换机的关系
    public Binding bindingDead(){
        return   BindingBuilder.bind(deadQueue()).to(deadExchange()).with("dead_ordering_ok_wms");
    }
    @Bean  //业务交换机
    public FanoutExchange exchange() {
        return    ExchangeBuilder.fanoutExchange("ordering_ok").durable(true).build();
    }
    @Bean //业务队列
    public Queue queue() {
        return  QueueBuilder
                .durable("ordering_ok_wms")
                .deadLetterExchange("dead_ex")
                .deadLetterRoutingKey("dead_ordering_ok_wms")
                //.ttl(20*1000) //该属性是队列的属性,设置消息的过期时间,消息在队列里面停留时间n毫秒后,就会把这个消息投递到死信交换机,针对的是所有的消息
                //.maxLength(5) //设置队列存放消息的最大个数,x-max-length属性值,当队列里面消息超过20,会把队列之前的消息依次放进死信队列
                .build();
    }

    @Bean //业务绑定队列与交换机的关系
    public Binding binding(){
      return   BindingBuilder.bind(queue()).to(exchange());
    }


   // @RabbitListener(queues = "ordering_ok_wms")
    public  void  consume(OrderingOk msg) throws IOException {
            log.debug("wms处理订单->{}",msg);
            int i = 1/0;
    }

4. 自动应答死信配置

#-------------MQ 高级配置---------

#预抓取数量

spring.rabbitmq.listener.simple.prefetch=250

#设置消费者手动应答模式

spring.rabbitmq.listener.simple.acknowledge-mode = auto

#开启自动应答重试机制

spring.rabbitmq.listener.simple.retry.enabled=true

#默认重试3次

spring.rabbitmq.listener.simple.retry.max-attempts=3

#重试间隔时间 单位ms

spring.rabbitmq.listener.simple.retry.initial-interval=1000ms

#时间间隔倍数,默认是1倍

spring.rabbitmq.listener.simple.retry.multiplier=2

#最大间隔时间

spring.rabbitmq.listener.simple.retry.max-interval=5000ms

相关推荐
添砖java_8579 小时前
基于RabbitMQ实现的轻量队列测试报告
分布式·rabbitmq
Zhu75810 小时前
使用腾讯CNB构建Hadoop定制容器镜像
大数据·hadoop·分布式
TTBIGDATA11 小时前
【Ambari Plus】13.Spark 安装
大数据·hadoop·分布式·spark·ambari·sqoop·ambari plus
sunxunyong13 小时前
Hadoop租户创建
大数据·hadoop·分布式
得物技术13 小时前
得物 OceanBase 落地实践
数据库·分布式·架构
GuangdongTong14 小时前
基于RabbitMQ实现延迟任务
后端·rabbitmq
heimeiyingwang15 小时前
【架构实战】分布式ID生成:从自增ID到雪花算法
分布式·架构
微三云 - 廖会灵 (私域系统开发)1 天前
电商系统微服务拆分实战:从单体到Spring Cloud的分布式事务踩坑与补偿方案
分布式·spring cloud·微服务
ACP广源盛139246256732 天前
破局 PCIe 4.0 交换瓶颈@ACP#IX8024 / ASM58024参数及应用对比
大数据·人工智能·分布式·嵌入式硬件
淡然的煎蛋2 天前
开始使用RabbitMQ
分布式·rabbitmq·ruby