当前位置: 首页 > news >正文

如何保证 RocketMQ 消息不丢失

🚀 一句话总览:消息不丢 = 生产端不丢 + Broker 不丢 + 消费端不丢

你要牢牢记住:

任何 MQ 最容易丢的不是 Broker,而是 Producer 和 Consumer。

消息可靠性必须三段一起设计:

Producer(发送)  
Broker(存储)  
Consumer(消费)

我带你分段讲透。


🚀 一、Producer 如何保证消息不丢

Producer 端的丢消息风险其实最大,因为:

  • 网络问题
  • Producer 崩溃
  • 发送失败没有感知

要做到不丢,必须配置以下 5 点。


⭐1. 使用同步发送(send())而不是异步 / oneway

最关键的一点:

只有同步发送才能收到 Broker 的返回结果(SendResult)。

SendResult result = producer.send(message);

异步(sendAsync)可能回调没来就宕机,oneway 更是直接不保证成功。


⭐2. 开启发送失败重试

RocketMQ 默认发送失败重试 2 次,你应该显式配置:

producer.setRetryTimesWhenSendFailed(3);
producer.setRetryTimesWhenSendAsyncFailed(3);

当网络抖动、broker 瞬时负载高时非常关键。


⭐3. 打开“失败切换 Broker”机制(默认开启)

RocketMQ 默认如果一个 broker 不可用,会自动换另一台 broker 发送(failover)。

你不用额外配置,但你要知道这是原因之一。


⭐4. 避免“先提交本地事务、后发消息”(经典误区)

比如:

先写数据库成功  
再 send 消息 → send 失败  
业务不一致

正确做法:

用 RocketMQ 事务消息,两阶段提交。

RocketMQ 事务消息模型:

1)发送 half message
2)执行本地事务
3)commit 或 rollback
4)RocketMQ 回查未决事务

这样才不会丢。


⭐5. Producer 端做好消息持久化/重试机制(可选)

在更严格的企业系统里,会做:

  • 本地消息表
  • Redis 去重
  • 定时补偿任务

核心思想是:

发送前先存一份,发送失败时可以继续重试

这个属于高级玩法,但面试加分。


🚀 二、Broker 如何保证消息不丢(核心)

Broker 是最关键的一环。RocketMQ 不丢消息靠三件事:


⭐1. 使用同步刷盘(SYNC_FLUSH)

默认是异步刷盘:

异步刷盘 = 内存写成功就返回 Producer → 电源断了就丢。

要保证不丢,必须切换为同步刷盘:

SYNC_FLUSH

特点:

  • 写入 commitlog
  • 立即刷入磁盘
  • 返回 Producer

虽然牺牲一点性能,但可靠性最高。


⭐2. 使用同步复制(SYNC_MASTER)

主从复制有两种:

模式 会不会丢消息
ASYNC_MASTER 主节点挂了就可能丢
SYNC_MASTER 主从都写成功才 ack,几乎零丢失

必须用:

SYNC_MASTER

这也是大厂“核心链路”统一做法。


⭐3. 使用 DLedger(RocketMQ 5 推荐)

DLedger 是多副本一致性机制(类似 Raft)。

特点:

  • 多数派写成功才算成功
  • 自动选主
  • 零人工干预
  • 不丢数据

这比传统主从架构更安全。

面试时这样讲:

RocketMQ 5 使用 DLedger 多副本一致性存储,只要多数派节点写入成功,消息就不会丢失。

面试官会直接点头。


🚀 三、Consumer 如何保证消息不丢

消费者丢消息主要体现在:

  • 执行业务成功但是 offset 提交失败
  • 业务执行失败但 offset 提交成功
  • 自动提交 offset 导致漏消费

你按下面做就不会丢。


⭐1. 正确处理消费失败:必须返回 RECONSUME_LATER

PushConsumer:

return ConsumeConcurrentlyStatus.RECONSUME_LATER;

RocketMQ 会自动重试:

  • 1m
  • 5m
  • 10m
  • 最多 16 次
  • 失败进入 DLQ(死信队列)

这样单靠 RocketMQ 机制就能做到“不丢”。


⭐2. 业务处理成功后再提交 offset

不要提前提交 offset。

RocketMQ 默认是自动提交,但你要做到“处理完再 ack”。

PushConsumer 的 ack 机制是:

return CONSUME_SUCCESS 才会提交 offset。

你一定要保证:

业务 → 成功  
|  
ack

而不是:

ack  
|  
业务(失败的话消息就丢了)

⭐3. 保证幂等性(至少一次语义)

RocketMQ 是“至少一次”模型:

一条消息可能会投递多次,但绝不会不投递。

你必须使用幂等:

  • MySQL 唯一约束(推荐)
  • Redis setnx 去重
  • 消费幂等表
  • 分布式锁(不推荐)

幂等做对了,消息绝不会乱。


🚀 四、完整串联:从端到端实现“不丢消息”

你把这些组合起来就是终极方案。


🔥 Producer:

  • 同步发送
  • 失败重试
  • 消息落表/本地事务
  • 使用事务消息(强一致)

🔥 Broker:

  • SYNC_FLUSH
  • SYNC_MASTER
  • DLedger 多副本
  • = 2 副本架构

  • 优化 JVM + 磁盘配置

🔥 Consumer:

  • 失败返回 RECONSUME_LATER
  • 不自动 ack
  • 幂等性
  • 死信队列监控

🚀 五、面试版总结(你能一口气答完)

你可以这样总结:

RocketMQ 保证消息不丢主要从三个层面做的:

1)Producer:

  • 同步发送(send)
  • 重试机制
  • Failover 切换 broker
  • 事务消息避免“本地事务成功但消息发送失败”

2)Broker:

  • 同步刷盘 + 同步复制(SYNC_FLUSH + SYNC_MASTER)
  • DLedger 多副本一致性(多数派成功才算成功)
  • CommitLog 顺序写磁盘

3)Consumer:

  • 消费失败返回 RECONSUME_LATER
  • 业务成功后再提交 offset
  • 幂等机制(至少一次语义)

这三段组合起来,就能保证消息在任何节点都不会丢。

面试官会非常满意这样的回答。

http://www.zskr.cn/news/76255.html

相关文章:

  • Flutter for HarmonyOS 创建指南(一):环境搭建与项目创建
  • 详细介绍:[特殊字符] 微前端部署实战:Nginx 配置 HTTPS 与 CORS 跨域解决方案(示例版)
  • Git预提交钩子实现代码美化自动化
  • 122_尚硅谷_init函数
  • Windows 11全面AI化:语音助手与自主代理技术解析
  • 氛围编程工具个人推荐
  • MyBatis自定义拦截器
  • 网线大鲨鱼
  • 【P1】win10安装 Docker教程 - 详解
  • 卷积神经网络是从多层感知机基础上发展起来的吗?
  • 详细介绍:python logging模块:专业日志记录
  • JAX核心设计解析:函数式编程让代码更可控
  • 澄清:梯度下降优化的是模型参数,而非损失函数本身
  • core学习之路
  • XXL-JOB v3.3.1 发布 | 升级SpringBoot4、健壮性增强
  • 陪诊不是“陪跑”——北京陪诊机构调研榜出炉,三家机构凭实力登榜
  • 微信小程序开发案例 | 幸运抽签小工具(上)
  • 10407_基于springboot的就业信息分享系统
  • NOIP 2025 订正
  • Linux 运维100 条命令
  • [豪の算法奇妙冒险] 代码随想录算法训练营第十六天 | 513-找树左下角的值、112-路径总和、113-路径总和Ⅱ、106-从中序与后序遍历序列构造二叉树、105-从前序与中序遍历序列构造二叉树
  • 北京上门收画回收名家字画机构公司推荐和排行
  • 2025NOIP游记(有空更新)
  • JDK的安装与删除
  • C语言字符串函数学习 - hillo
  • 北京上门收酒服务权威推荐榜,四家机构获评优质服务商
  • 20232406 2024-2025-1 《网络与系统攻防技术》实验八实验报告
  • P2163 [SHOI2007] 园丁的烦恼 做题笔记
  • 20232424 2025-2026-1 《网络与系统攻防技术》实验八实验报告
  • 北京上门收酒机构调研排行:四家靠谱机构推荐,藏家变现别踩坑