总结RocketMQ中的常见问题

news/2025/9/19 18:56:27/文章来源:https://www.cnblogs.com/randolf/p/19101513

总结RocketMQ中的常见问题

一、MQ 如何保证消息不丢失

1. 丢消息的关键环节

  • 跨网络环节:消息链路中1(生产者→Broker)、2(Broker 主→从)、4(Broker→消费者) 三个场景,因网络不稳定性可能导致请求丢失。
  • 本地缓存环节:3(Broker 存盘),消息默认先写入操作系统PageCache(内存缓存),再由操作系统异步刷盘至硬盘;若 Broker 非正常宕机,缓存中未刷盘的消息会丢失。

2. 生产者发送消息的保障措施

核心逻辑:通过生产者确认机制,让 Broker 向生产者反馈消息写入结果,失败则生产者自行补救(重发 / 抛异常)。各 MQ 实现差异如下表:

MQ 产品 同步发送方式 异步发送方式 关键特点
RocketMQ producer.send(msg, 20*1000)(超时 20 秒) producer.send(msg, SendCallback)(回调通知) 异步需额外线程,平衡安全与效率
Kafka producer.send(record).get()(Future 阻塞) producer.send(record)(返回 Future) 同步依赖Future.get()获取结果
RabbitMQ - 基于Publisher Confirms,添加 ack/nack 回调 通过回调区分成功 / 失败
  • RocketMQ 事务消息机制:专为 “本地事务与消息发送原子性” 设计(如电商下单 + 支付),流程核心:
    1. 生产者发送half 消息(预发送,Broker 暂不投递);
    2. Broker 反馈 half 消息发送成功;
    3. 生产者执行本地事务(如 MySQL 下单);
    4. 根据事务结果向 Broker 发送Commit/Rollback
    5. 若 Broker 未收到 Step4,主动回查生产者本地事务状态;
    6. 最终 Broker 按状态投递消息(Commit)或丢弃(Rollback)。

3. Broker 写入数据的保障措施

核心解决PageCache 异步刷盘的丢失风险,各 MQ 刷盘策略差异显著:

  • RocketMQ:通过配置flushDiskType指定刷盘模式:
    • SYNC_FLUSH(同步刷盘):写入消息后触发刷盘,实际间隔10 毫秒(平衡 IO 压力),安全性高,但 IO 负担重;
    • ASYNC_FLUSH(异步刷盘):固定时间批量刷盘,性能稳定,存在断电丢失风险。
  • Kafka:无明确 “同步 / 异步” 划分,通过 4 个参数控制刷盘频率:
    • flush.ms:强制刷盘的时间间隔;
    • log.flush.interval.messages:单 Partition 积累指定条数(默认Long.MAX)触发刷盘;
    • log.flush.interval.ms:消息在内存保留时间(默认空,依赖下一个参数);
    • log.flush.scheduler.interval.ms:检查刷盘需求的频率(默认Long.MAX)。
  • RabbitMQ:官网明确限制:
    • Classic 队列:即使声明为持久化,也不实时调用fsync,断电可能丢失;
    • Stream 队列:不主动fsync,完全依赖操作系统;
    • 建议:需高安全时结合Publisher Confirms机制二次保障。

4. Broker 主从同步的保障措施

主从同步用于数据备份,风险点为 “主节点宕机时未同步数据丢失”,各 MQ 集群策略差异源于 “安全” 与 “可用性” 的取舍:

  • RocketMQ:两种集群方案:
    1. 普通集群:配置brokerRole(ASYNC_MASTER/SYNC_MASTER/SLAVE),Slave 不自动切换为 Master;Master 宕机后,未同步数据保留在 Master,重启后继续同步(无丢失,需 Master 磁盘完好);
    2. Dledger 高可用集群:基于Raft 协议(多数派同意机制),消息同步至多数节点后提交,优先保证数据一致性,极端场景(如网络分区)丢失风险极低。
  • Kafka:优先保障可用性:Leader Partition 宕机后,Follower 选举为新 Leader;旧 Leader 重启后作为 Follower,删除HighWater(高水位)后的数据并重新同步,导致 “旧 Leader 未同步数据丢失”。

5. 消费者消费消息的保障措施

  • 消费确认机制:消费者处理完消息后必须向 Broker 反馈 “消费成功”,未反馈则 Broker 重复投递:
    • RocketMQ/Kafka:基于Offset(消费偏移量)重新投递未确认消息;
    • RabbitMQ(Classic Queue):将未确认消息重新入队。
  • 核心风险:异步处理消息(如消费者内启新线程处理业务,却提前返回ConsumeConcurrentlyStatus.CONSUME_SUCCESS),若业务处理失败,消息已被标记 “成功”,导致丢失。

6. MQ 集群全挂的应对方案:降级缓存

  • 策略:生产者发送消息失败时,将消息写入临时降级缓存(如本地文件 / Redis),正常执行后续业务;
  • 补偿:启动独立线程,循环重试将缓存消息发送至 MQ,MQ 恢复后消息可快速入队,避免丢失。

7. 消息零丢失方案总结(权衡取舍)

保障环节 具体措施 代价
生产者→Broker 同步发送 + 多次重试;事务消息 降低吞吐;增加网络请求次数
Broker 存盘 + 主从同步 同步刷盘;Dledger 集群 加重操作系统 IO 负担;增加网络负载
Broker→消费者 同步处理消息后提交 Offset 无法通过异步提升消费效率
MQ 集群全挂 增加临时降级存储 额外存储开销;需维护重试线程

核心结论:无 “最优解”,需结合业务场景选择(如金融场景优先安全,日志场景优先吞吐)。

二、MQ 如何保证消息顺序性

1. 核心认知:局部有序而非全局有序

  • 业务意义:仅需 “同一业务组” 内消息有序(如同一订单的创建、支付、发货消息),全局有序(所有消息按发送时间排序)无实际业务场景;
  • 反例:RocketMQ/Kafka 将 Topic 分区数设为 1 实现全局有序,仅为 “思维体操”,会严重限制吞吐,无实际价值。

2. 局部有序的保障措施

需生产者与消费者协同,核心是 “同一队列串行处理”:

  • 生产者端:将同一业务组的有序消息写入同一个队列
    • RocketMQ/Kafka:通过定制 “分区计算算法”,指定消息写入的 MessageQueue/Partition;
    • RabbitMQ:通过 Exchange 与 Queue 的绑定规则,将消息转发至同一 Queue。
  • 消费者端:控制并发,确保同一队列消息串行处理:
    • RocketMQ:注入特定消息监听器,通过消费线程并发控制(同一 MessageQueue 仅一个线程处理)保障顺序;
    • Kafka:Consumer 拉取单个 Partition 消息时天生单线程,无需额外控制;
    • RabbitMQ(Classic Queue):一个 Queue 仅对应一个 Consumer(多 Consumer 会分拆消息,破坏顺序)。

三、MQ 如何保证消息幂等性

幂等性定义:避免消息重复发送 / 消费导致业务异常(如重复下单、重复扣款)。

1. 生产者发送消息的幂等保障

风险点:生产者重试时,可能因 “Broker 已处理但响应丢失” 导致重复发送。

  • RocketMQ:自动为每条消息分配唯一 UniqID(通过MessageClientIDSetter.setUniqID(msg)设置,键为MessageConst.PROPERTY_UNIQ_CLIENT_MESSAGE_ID_KEYIDX),Broker 通过该 ID 判断消息是否重复。
  • Kafka:开启idempotence(默认开启,需避免配置冲突),通过两个核心概念保障:
    • PID:每个新 Producer 初始化时分配唯一 PID(用户不可见);
    • Sequence Number:Producer 对每个 Partition 维护从 0 递增的序列号,随消息发送至 Broker;
    • Broker 逻辑:针对<PID, Partition>维护 SN(当前序列号),仅当消息 Sequence Number = SN+1 时接收,否则:
      • 序列号过小:判定已处理,拒绝重复;
      • 序列号过大:判定中间消息丢失,抛OutOfOrderSequenceException

2. 消费者消费消息的幂等保障

风险点:网络波动导致 Broker 未收到消费确认,重复投递消息。

  • 核心手段:唯一标识
    • 通用标识:RocketMQ 的messageId(批量发送 / 事务消息场景可能失效);
    • 推荐标识:业务唯一 ID(如订单 ID、支付流水号),通过消息key属性传递,稳定性更高(消费者处理前查询 “该 ID 是否已处理”)。
  • 补偿机制
    • 重试队列:重复投递的消息放入 “消费者组维度” 的重试队列,默认重试16 次(间隔递增);
    • 死信队列:多次重试仍失败的消息进入死信队列,默认无消费权限,需手动调整权限后单独处理(标识消费者逻辑异常,需人工排查)。

四、MQ 如何快速处理积压的消息

1. 消息积压的风险

MQ 产品 积压风险点 关键影响
RocketMQ/Kafka 日志文件(CommitLog/Partition 日志)过期后自动删除,未消费消息丢失 数据丢失
RabbitMQ Classic/Quorum Queue:大量积压占用内存 / 磁盘,严重影响服务端性能 服务响应变慢、崩溃风险
RabbitMQ Stream Queue:类似 RocketMQ/Kafka,承受能力强,但仍有日志过期丢失风险 数据丢失

2. 积压消息的解决策略

核心目标:提升 Consumer 消费效率,突破队列数量限制。

  • 策略 1:优化业务逻辑(根本方案):简化 Consumer 处理流程(如减少 DB 查询、异步处理非核心逻辑),提升单实例处理速度。
  • 策略 2:增加 Consumer 实例(有上限):
    • RabbitMQ(Classic Queue):无上限,按 Work Queue 模式平均分配消息,可通过Qos属性调整各 Consumer 的消息分配比重;
    • RocketMQ/Kafka:上限为 Topic 的 MessageQueue/Partition 个数(一个队列仅被一个 Consumer 消费),超量实例处于空闲状态。
  • 策略 3:拆分 Topic(应急方案,适用于队列不足场景):
    1. 创建新 Topic,配置足够多的 MessageQueue/Partition(突破原 Topic 限制);
    2. 上线临时 Consumer,仅负责将旧 Topic 的积压消息 “快速转存” 至新 Topic(不处理业务逻辑,速度提升 10 倍以上);
    3. 在新 Topic 上部署足量 Consumer 实例,并行消费积压消息;
    4. 消费完成后,按需恢复原 Topic 架构(思路与 RocketMQ “固定级别延迟消息” 一致:临时 Topic 暂存消息)。

关键问题(3 个,不同侧重)

问题 1:MQ 保证消息不丢失的方案为何必须 “权衡”?以 RocketMQ 的刷盘模式和 Kafka 的主从选举为例,说明权衡的核心矛盾是什么?

答案:因为所有保障消息不丢失的方案,均需以 “牺牲系统性能或增加资源负载” 为代价,核心矛盾是 **“消息安全性” 与 “系统吞吐 / 可用性” 的取舍 **。

  • 以 RocketMQ 刷盘模式为例:同步刷盘(SYNC_FLUSH) 通过 10 毫秒间隔强制刷盘,大幅降低断电丢失风险(安全性高),但频繁 IO 操作会加重操作系统负担,导致消息写入吞吐量下降;而异步刷盘(ASYNC_FLUSH) 批量刷盘提升吞吐,但存在 Broker 宕机时缓存消息丢失的风险。
  • 以 Kafka 主从选举为例:Kafka 优先保障服务可用性——Leader Partition 宕机后,Follower 会快速选举为新 Leader,确保消息能继续接收;但旧 Leader 未同步给 Follower 的消息,会在旧 Leader 重启后被删除(因需与新 Leader 数据一致),导致数据丢失(安全性降低);而 RocketMQ 普通集群的 Slave 不自动切换,虽牺牲了 “服务快速恢复能力”(可用性下降),但未同步数据保留在 Master,重启后可继续同步(安全性高)。
    最终需结合业务场景选择:金融支付场景选 RocketMQ 同步刷盘 + Dledger 集群(优先安全),日志收集场景选 Kafka 异步刷盘(优先吞吐 / 可用性)。

问题 2:各 MQ 产品在 “消费者端保障局部消息顺序性” 的实现上,为何存在显著差异?这些差异分别适配了什么业务场景?

答案:差异源于各 MQ 的设计初衷与目标业务场景不同,具体适配场景如下:

  • RocketMQ:通过 “消费线程并发控制” 实现(同一 MessageQueue 仅一个线程处理),适配复杂业务场景(如电商订单、金融交易)—— 这类场景需在 “顺序保障” 与 “消费并发” 间平衡(如同一订单消息串行处理,不同订单消息并行处理),灵活的并发控制可提升整体吞吐。
  • Kafka:Consumer 拉取单个 Partition 消息时 “天生单线程”,无需额外控制,适配日志 / 监控数据采集场景—— 这类场景中,日志按分区串行写入,单线程消费可满足顺序需求,且简化设计、降低维护成本(无需处理并发控制逻辑)。
  • RabbitMQ(Classic Queue):依赖 “一个 Queue 对应一个 Consumer” 保障顺序,适配简单任务队列场景(如邮件发送、日志处理)—— 这类场景业务逻辑简单,单 Consumer 处理单个 Queue 的消息即可满足需求,无需复杂的并发控制,设计更轻量化。

问题 3:当 RocketMQ 的 Topic 因 MessageQueue 数量不足,无法通过增加 Consumer 实例解决消息积压时,应急处理方案是什么?该方案的设计思路与 RocketMQ 的哪种内部机制一致?

答案:应急处理方案是 “拆分 Topic,临时转存积压消息”,具体步骤如下:

  1. 新建一个 Topic(如 “topic_backlog”),配置远超原 Topic 的 MessageQueue 数量(如原 Topic 有 4 个 Queue,新 Topic 设为 32 个),突破原 Topic 的队列数量限制;
  2. 紧急上线一组 “临时 Consumer”,仅负责从原 Topic 拉取积压消息,不处理业务逻辑,直接将消息转存至新 Topic(转存速度远快于业务处理,可提升 10 倍以上);
  3. 在新 Topic 上部署足量 Consumer 实例(数量不超过新 Topic 的 MessageQueue 数),并行消费积压消息;
  4. 积压消息处理完成后,按需恢复原 Topic 的消费架构(如将临时 Consumer 下线,业务 Consumer 切回原 Topic)。

该方案的设计思路与 RocketMQ 的 “固定级别延迟消息机制” 一致:均通过 “临时 Topic 暂存消息” 的方式,规避原 Topic 的资源限制(如延迟消息会先存入系统内部的延迟 Topic,到达延迟时间后再转存至目标 Topic),利用 Topic 的队列扩展性提升处理效率,本质是 “空间换时间” 的应急策略。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/908014.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

The 2025 ICPC Asia EC Regionals Online Contest (II)

疑似第一场没题解?那先写第二场了。 大家打得很棒,状态起来了!继续保持。 B. Rectangular Wooden Block给定 \(L\times W\times H\) 的长方体,每个 \(1\times 1\times 1\) 的小立方体有价值 \(V(i,j,k)\),选择其中…

Python实现Elman RNN与混合RNN神经网络对航空客运量、啤酒产量、电力产量时间序列数据预测可视化对比

全文链接:https://tecdat.cn/?p=43924原文出处:拓端数据部落公众号视频出处:拓端抖音号@拓端tecdat一、引言 作为长期深耕时间序列预测领域的数据科学家,我们在项目中频繁发现一个共性痛点:多数团队在选择循环神…

4G/Wi-Fi/以太网三网合一,智能融合通信实战案例集

聚焦通信技术落地痛点,4G/Wi-Fi/以太网智能多网融合方案,通过动态负载均衡与故障自愈机制,构建高可用通信链路。实战场景覆盖远程监控、智能交通等领域,技术细节与实施步骤全解析。 本文以Air8000开发板WebSocket应…

关于介绍自己的第一篇随笔

你好啊,我是张家瑞,一名普通平凡的学生。 仔细想来我的兴趣爱好也没什么特别的,也同他人一样爱打打游戏听听音乐,非常喜欢格斗游戏和卡牌游戏,若有喜欢街霸,罪恶装备,游戏王的同学可以找我打(开个玩笑),稍微…

深入解析:N32G43x Flash 驱动移植与封装实践

深入解析:N32G43x Flash 驱动移植与封装实践pre { white-space: pre !important; word-wrap: normal !important; overflow-x: auto !important; display: block !important; font-family: "Consolas", &qu…

Backblaze上如何传大文件

问题 创建好一个存储桶后,直接点击上传文件即可。但是当文件很大时将会显示:第一次通过以下步骤解决 第一步:准备工作 1.安装命令行工具 (B2 CLI) pip install --upgrade b2检验安装是否成功(可选) b2 version显示:…

解题报告-老逗找基友 (friends)

老逗找基友 (friends) 题目背景 吴老逗有 \(n\) 个基友,位于平面直角坐标系的整点上。每个基友已与其最近的基友(如有多个则取编号最小)建立了双向心灵感应。但这样形成的网络可能不连通,因此吴老逗可以使用爱之魔…

Python_occ 学习记录 | 细观建模(1) - 教程

pre { white-space: pre !important; word-wrap: normal !important; overflow-x: auto !important; display: block !important; font-family: "Consolas", "Monaco", "Courier New", …

深入解析:uv:用 Rust 重写的极速 Python 包管理器

pre { white-space: pre !important; word-wrap: normal !important; overflow-x: auto !important; display: block !important; font-family: "Consolas", "Monaco", "Courier New", …

Caused by: java.lang.ClassNotFoundException: org.apache.rocketmq.remoting.common.RemotingUtil

前言 启动报错,打包可以,启动报错; 针对这个问题 可以看下.ClassNotFoundException和NoClassDefFoundError:有啥区别先 org.springframework.beans.factory.BeanCreationException: Error creating bean with name …

VAE In JAX【个人记录向】

和上一篇 SAC In JAX 一样,我们用 JAX 实现 VAE,配置一样,只需要安装符合版本的 torchvision 即可,实现中提供了 tensorboard 记录以及最后的可视化展示,测试集即为最经典的 MNIST,代码如下: import jax import…

BLE蓝牙配网双模式实操:STA+SoftAP技术原理与避坑指南

想让设备同时支持蓝牙快速配网与AP热点备份?STA+SoftAP双模式是关键!本文深度解析技术原理,结合真实项目案例总结实操避坑点,助你一文搞懂双模式配网逻辑,开发少走90%弯路。 本文特别分享蓝牙配网方案: 以Air800…

【小白也能懂】PyTorch 里的 0.5 到底是干啥的?——一次把 Normalize 讲透! - 教程

pre { white-space: pre !important; word-wrap: normal !important; overflow-x: auto !important; display: block !important; font-family: "Consolas", "Monaco", "Courier New", …

第58天:RCE代码amp;命令执行amp;过滤绕过amp;异或无字符amp;无回显方案amp;黑白盒挖掘

第58天:RCE代码&命令执行&过滤绕过&异或无字符&无回显方案&黑白盒挖掘 案例演示RCE & 代码执行 & 命令执行 RCE-利用&绕过&异或&回显 白盒-CTF-RCE代码命令执行 黑盒-运行-R…

057-Web攻防-SSRFDemo源码Gopher项目等

057-Web攻防-SSRF&Demo源码&Gopher项目等 知识点知识点: 1、SSRF-原理-外部资源加载 2、SSRF-利用-伪协议&无回显 3、SSRF-挖掘-业务功能&URL参数案例演示1、SSRF-原理&挖掘&利用&修复 2…

060-WEB攻防-PHP反序列化POP链构造魔术方法流程漏洞触发条件属性修改

060-WEB攻防-PHP反序列化&POP链构造&魔术方法流程&漏洞触发条件&属性修改 知识点: 1、PHP-反序列化-应用&识别&函数 2、PHP-反序列化-魔术方法&触发规则 3、PHP-反序列化-联合漏洞&P…

059-Web攻防-XXE安全DTD实体复现源码等

059-Web攻防-XXE安全&DTD实体&复现源码等 知识点 XML&XXE-传输-原理&探针&利用&玩法 XML&XXE-黑盒-JS&黑盒测试&类型修改 XML&XXE-白盒-CMS&PHPSHE&无回显什么是XML?…

061-WEB攻防-PHP反序列化原生类TIPSCVE绕过漏洞属性类型特征

061-WEB攻防-PHP反序列化&原生类TIPS&CVE绕过漏洞&属性类型特征知识点 1、PHP-反序列化-属性类型&显示特征 2、PHP-反序列化-CVE绕过&字符串逃逸 3、PHP-反序列化-原生类生成&利用&配合1、…

051-Web攻防-文件安全目录安全测试源码等

051-Web攻防-文件安全&目录安全&测试源码等 知识点1、文件安全-前后台功能点-下载&读取&删除 2、目录安全-前后台功能点-目录遍历&目录穿越演示案例:➢文件安全-下载&删除-案例黑白盒 ➢目录…