RocketMQ 如何保证消息不丢失?

RocketMQ 的消息想要确保不丢失,需要生产者、消费者以及 Broker 的共同努力,缺一不可。

生产者(Producer)

1、发送方式:选择同步发送

  • 同步发送:发送消息后,需要阻塞等待 Broker 确认收到消息,生产者才能拿到返回的 SendResult
  • 异步发送:Producer 首先构建一个向 broker 发送消息的任务,把该任务提交给线程池,等执行完该任务时,回调用户自定义的回调函数,执行处理结果。

2、重试机制

生产者因为网络故障、服务异常等原因导致调用, RocketMQ 内置请求重试逻辑,默认重试 3 次。

重试 3 次意思是一共会发 4 次消息,1 次原始消息,3 次重试消息。

Broker

1、刷盘策略:选择同步刷盘

  • 同步刷盘:如果想要保证消息不丢失,可以将消息保存机制修改为同步刷盘,这样,Broker会在同步请求中把数据保存在磁盘上,确保保存成功后再返回确认结果给生产者。
  • 异步刷盘:异步发送的话就需要生产者重写 SendCalback 的 onSuccess 和 onException 方法,用于给 Broker 进行回调。在方法中实现消息的确认或者重新发送。
java 复制代码
# 默认情况为 ASYNC_FLUSH
flushDiskType = SYNC_FLUSH

2、同步机制:同步复制

为了保证消息不丢失,RocketMQ肯定要通过集群方式进行部署,Broker 通常采用一主多从部署方式,并且采用主从同步的方式做数据复制

默认方式下,Broker 在接收消息后,写入 master 成功,就可以返回确认响应给生产者了,接着消息将会异步复制到 slave 节点。但是如果这个过程中,Master 的磁盘损坏了。那就会导致数据丢失了。

如果想要解决这个问题,可以配置同步复制的方式,即 Master 在将数据同步到 Slave 节点后,再返回给生产者确认结果。

java 复制代码
# 默认为 ASYNC_MASTER
brokerRole = SYNC_MASTER

消费者(Consumer

1、At least Once 机制(先业务后ack)

At least Once:
Consumer 先 pull【主动拉取Broker中的信息】 消息到本地,消费完成后,才向服务器返回 ack。

通常消费消息的 ack 机制一般分为两种思路:

  • 第一种:先提交后消费;
  • 第二种:先消费,消费成功后再提交【这个更稳当】

思路一可以解决重复消费的问题但是会丢失消息,因此 Rocketmq 默认实现的是思路二,由各自 consumer 业务方保证幂等来解决重复消费问题。

幂等:通过给每个消息携带一个唯一标识信息,去数据库进行判断。或者在 producer 的时候就存储一个唯一标识(消息),消费成功删除redis中的消息确保不被重复消费

简单来说就是,在消费者的代码中,一定要在业务逻辑的最后一步returnConsumeConcurrentlyStatuS.CONSUME SUCCESS;
当然,也可以先把数据保存在数据库中,就返回,然后自己再慢慢处理。

2、消费消息重试机制

在消费者端,需要确保在消息拉取并消费成功之后再给 Broker 返回 ACK,就可以保证消息不丢失了,如果这个过程中 Broker 一直没收到 ACK,那么就可以重试。默认 16 次。

相关推荐
liangbo78 分钟前
06-JVM垃圾回收器之CMS
java·jvm
黑马程序员毕设10 分钟前
基于Java的仪器管理系统设计与实现
java·开发语言·spring boot·后端·微信小程序
骇客野人23 分钟前
SpringBoot电商购物车、结算、下单、库存方案设计与落地实施步骤
java·spring boot·后端
哪 吒43 分钟前
华为OD机试 - 云服务安全策略最优选择 - 深度优先搜索DFS(Java 新系统 200分)
java·华为od·深度优先
拒绝内耗。44 分钟前
程序员学架构(一):一张图看懂 Java 后端架构:一个请求怎样从手机到数据库?
java·智能手机·架构
棣廷1 小时前
初识Python面向对象
java·开发语言
用户3126874877201 小时前
ThreadLocal 到底会不会内存泄漏?源码级拆解 + 线程池陷阱
java
珍珠先生1 小时前
P11 · MySQL 驱动版本过旧:Client does not support authentication protocol
java
~木雨1 小时前
Java 并发编程架构全景:并发层的五域设计 —— 线程模型、线程池隔离、并发安全到问题治理(全体系汇总)
java·安全·架构·线程池·并发编程·高并发架构
极小狐1 小时前
从复制粘贴到可复用组件:极狐GitLab CI/CD 组件目录实战
java·ci/cd·gitlab·devops·组件化