RabbitMQ

50 阅读3分钟

RabbitMQ

MQ如何保证消息可靠性?如何保证消息不丢失?

生产者:

  • 开启重试策略,保证消息正确到达MQ,如果重试次数耗尽,则写入数据库,后期交由人工处理
  • 开启confirm机制,保证消息正确到达交换机
  • 开启return机制,保证消息正确到达队列

持久化操作:

  • 创建交换机、队列、消息时设置持久化(默认就是持久化),保证MQ宕机后重启不丢失

消费者:

  • 开启自动ack,并且设置本地重试策略,当本地重试次数耗尽后,失败消息路由到错误队列。
  • 监听错误队列,把消息写入数据库,后期交由人工处理

消费者的操作是否是一个幂等性操作?

天生幂等的操作:一般不管 非幂等性操作

  • 消费者先从Redis中获取消息ID,如果存在,则表示有人在消费消息,我什么都不做。如果不存在,表示是该消息是第一次被消费,正常消费,并且向存储Key为消息ID的数据到Redis,同时设置过期时间
  • 业务判断:由一个状态到另一个状态,必须加条件是初始状态
  • MQ可靠性保证并不是100%,所以有可能消费者没有收到MQ的消息,那么后续就无法执行了。我们可以主动发起查询去获取最新结果,然后继续完成后面的业务操作

多个消费者,如何保证消息的顺序消费?

消费者指定线程消费数为1

image.png MQ增加队列属性为 x-single-active-consumer 为true

  • 表示当前队列,只能同时有一个消费者消费消息

image.png

消息积压问题

1、首先:消息积压的原因,大部分情况是消费者消费速度 跟不上生产者生产速度
2、这种情况下,我们可以采用惰性队列先将生产的消息存入磁盘,在消费时再加载到内存。以此来缓解队列存储消息的压力
3、分析积压消息的原因,大概率是消费者出问题了。那么首先先修复消费者代码、启动消费者程序。然后再临时增加消费者程序节点,以倍速的形式去消费积压的消息,当积压的消息被处理的差不多的时候,再把增加的节点下线

死信交换机

成为死信的几种情况:
1、消费者使用basic.reject 或 basic.nack 声明消费失败,并且消息的requeue参数设置为false
2、消息设置了过期时间,或者消息存放的队列设置了过期时间,超时无人消费
3、要投递的队列消息满了,无法投递
这些就是死信,然后会通过路由规则经过交换机路由到一个队列,这个交换机就叫死信交换机,这个队列就是死信队列

与Kafka的区别

Kafka

  • 优点:
    1、吞吐量大
    2、功能强大:处理流媒体
  • 缺点:
    1、时效性差:消息延迟时间比MQ长
  • 特点:
    1、重Topic:收发消息都必须指定Topic
    2、拉模式:由消费者主动去Broker中拉取消息
    3、消息消费完后,不会删除,保留历史消息

RabbitMQ

  • 优点:
    1、时效性强、可靠性高
  • 缺点:
    1、吞吐量比Kafka小
  • 特点:
    1、轻Topic:不同工作模式可以选择是否使用Topic
    2、推模式:由Broker主动把消息推送给消费者
    3、消息阅后即焚