RabbitMQ消息丢失、积压如何处理(阿里二面)

消息积压处理

我们现有的业务就面临此问题,消息生产太快,消费不过来,导致队列堆积很长,把服务器内存耗尽,这时RabbitMQ的处理能力很低下。

总结起来解决方案大体包括:

  • 增加消费者的处理能力,或减少发布频率,增加消费端实例。说白了就是增加机器。
  • 如果申请机器行不通,毕竟公司的机器是有限的,此时可以增加消费端的消费能力。在MQ的配置中配置"最大消费者数量"与"每次从队列中获取的消息数量"
  • 考虑使用队列最大长度限制,RabbitMQ 3.1支持
  • 给消息设置年龄,超时就丢弃
  • 发送者发送流量太大上线更多的消费者,紧急上线专门用于记录消息的队列,将消息先批量取出来,记录数据库,离线慢慢处理

这也是实现了柔性事务-可靠消息+最终一致性解决方案

做好消息确认机制(生产者、消费者)+手动确认机制

消息丢失处理

RabbitMQ的事务:事务可以保证消息100%传递,可以通过事务的回滚去记录日志,后面定时再次发送当前消息。事务的操作,效率太低,加了事务操作后,比平时的操作效率的至少要慢250倍。 RabbitMQ除了事务,还提供了Confirm的确认机制,这个效率比事务高很多。

  1. 普通Confirm方式。

image.png

  1. 批量Confirm:

image.png

3.异步Confirm:

image.png

image.png

Return机制:

Confirm只能保证消息到达exchange,无法保证消息可以被exchange分发到指定queue。而且exchange是不能持久化消息的,queue是可以持久化消息。 采用Return机制来监听消息是否从exchange送到了指定的queue中。

image.png

image.png

在业务环境下也有可能又这几种情况:

1、只要订单完成我们就会发送一条消息给MQ,这个途中突然MQ服务器网络中断,导致消息无法抵达

做好容错方法需要在消息发送前加上异常处理; 还可以将消息存入数据库,把失败的消息定期重新再发一遍 image.png

2、当消息发送给MQ,通过Brock通过交换机抵达队列,MQ关机了,只有抵达队列才能实现消息持久化

这时候需要使用生产者的确认机制(Confirm,Return)

image.png

3、自动ACK的状态下。消费者收到消息,但没来得及消息然后宕机

一定开启手动ACK,消费成功才移除,失败或者没来得及处理就NoAck并重新入队

猜你喜欢

转载自juejin.im/post/7130471165130178591