尧图网站设计 尧图网站设计YAOTU DESIGN
ARTICLE DETAIL

资讯详情

深耕网站设计与一线实操的经验洞察。

RocketMQ消息存储机制:刷盘、副本、高可用原理详解

RocketMQ消息存储机制:刷盘、副本、高可用原理详解 RocketMQ消息存储机制刷盘、副本、高可用原理详解作者黒漂技术佬适用读者对RocketMQ有基础了解想深入理解存储机制的同学一、为什么你要搞懂消息存储机制先说个场景你负责一套无人售货柜系统用户扫码开门、拿走商品、关门扣款。整个链路里订单消息、出货指令、支付回调——全压在RocketMQ上。某天Broker所在机器突然断电你老板问你“刚才那几笔订单消息丢没丢”你要是只会producer.send(msg)这问题你答不上来。但如果你懂存储机制你就能明确告诉他同步刷盘同步复制下消息不会丢异步刷盘可能丢未刷盘部分。所以搞懂存储机制 面试加分 生产排障不慌。二、消息存储的三大核心文件RocketMQ的消息存储不是一张数据库表而是三个文件协同工作。你把它理解成一个图书馆文件类比作用CommitLog书库所有书按入库顺序排列所有Topic的消息顺序写入的统一日志文件ConsumeQueue书目索引卡片按书架分类消息的逻辑索引队列按TopicQueueId组织IndexFile搜索引擎按书名/日期查书消息索引文件支持按Key和时间查询2.1 CommitLog万物之基CommitLog是RocketMQ存储的核心。不管你是哪个Topic、哪个Queue的消息统统写进同一个CommitLog文件。每个CommitLog文件固定1GB写满就创建新文件。/root/store/commitlog/ ├── 00000000000000000000 (第1个文件1GB) ├── 00000000001073741824 (第2个文件1GB) └── ...为什么要这样设计关键词顺序写。磁盘的随机写性能极差机械硬盘随机写约100-200 IOPS但顺序写性能极高——可达几百MB/s接近内存写速度。所有消息不分Topic统一写一个文件就是在充分利用顺序写。小白疑问那消费者要读某个Topic的消息怎么办总不能把整个CommitLog扫一遍吧答案这就是ConsumeQueue的用处了。2.2 ConsumeQueue消息的GPS导航ConsumeQueue是CommitLog的索引队列。每个Topic的每个MessageQueue队列都有一个对应的ConsumeQueue文件里面记录的是每条索引记录 20字节 - CommitLog Offset (8字节) —— 消息在CommitLog中的物理偏移量 - Message Length (4字节) —— 消息总长度 - Tag HashCode (8字节) —— Tag的哈希值用于Tag过滤消息写入CommitLog后Broker会异步构建对应的ConsumeQueue索引。消费者拉取消息时先查ConsumeQueue拿到CommitLog物理偏移量再去CommitLog精确读取——这就是先查索引再取数据的经典套路。消费者请求 Topicorder_topic, QueueId0, offset100 │ ▼ 查 ConsumeQueue: order_topic/queue0 │ 得到 offset100 对应的 CommitLog physicalOffsetxxxxx ▼ 查 CommitLog: 从 physicalOffset 读取消息2.3 IndexFile按Key查消息当业务需要按消息Key查询比如查某笔订单的消息发送记录或者按时间范围查询就用IndexFile。它内部是一个类似HashMap的结构哈希槽slot500万个槽每个4字节哈希链表冲突的消息用链表串起来存储记录包含Key HashCode、CommitLog Offset、消息存储时间、上一条相同Key的记录位置。典型使用场景售货柜订单异常时用订单号作为消息Key快速找到这条订单消息的全生命周期记录。三、消息写入全流程把三个文件串起来消息写入的完整流程如下Producer 发送消息 │ ▼ Broker 接收 │ ▼ ① 写入 CommitLog顺序写磁盘/PageCache │ ▼ ② 异步线程 ReputMessageService 扫描 CommitLog │ ├─→ 构建 ConsumeQueue 索引每条消息对应一条索引 │ └─→ 构建 IndexFile 索引如果消息有 Key │ ▼ ③ 消费者可拉取消息依赖ConsumeQueue已构建这里有个关键点ConsumeQueue是异步构建的。消息写进CommitLog后有一个短暂的时间窗口——ConsumeQueue还没来得及构建此时消费者还拉不到这条消息。这个延迟通常在毫秒级业务上一般无感知。四、刷盘策略可靠还是性能你选刷盘Flush是指把PageCache中的数据真正写到物理磁盘上。什么是PageCache操作系统为了提升IO性能会把磁盘数据缓存在内存中。你写数据时实际先写PageCache操作系统择机刷到磁盘。但如果断电PageCache中未刷盘的数据就没了。RocketMQ提供两种刷盘策略通过Broker配置flushDiskType选择4.1 同步刷盘SYNC_FLUSH消息写入PageCache → 立即调用force()刷到磁盘 → 确认写到磁盘后才返回成功给Producer可靠性极高机器断电也不丢消息性能低每条消息都要等磁盘IO完成适用场景金融交易、支付通知等绝对不能丢消息的场景4.2 异步刷牌ASYNC_FLUSH消息写入PageCache → 立即返回成功给Producer → 后台定时任务默认每500ms批量刷盘可靠性一般断电可能丢失PageCache中未刷盘的消息性能高消息写入几乎等于内存写速度适用场景日志收集、埋点上报、心跳上报等容忍少量丢失的场景4.3 无人售货柜场景选型建议消息类型刷盘策略理由订单/支付消息同步刷盘涉及扣款不能丢出货指令同步刷盘丢了就没人出货了设备心跳上报异步刷盘5秒一条丢几条无所谓销售统计报表异步刷盘允许少量误差默认配置是ASYNC_FLUSH。生产环境如果选同步刷盘建议用SSD否则TPS会被磁盘IO拖垮。五、副本机制Master和SlaveRocketMQ Broker有两种角色Master和Slave。Master负责消息读写Producer和Consumer主要连MasterSlave负责消息只读备份Consumer也可以从Slave拉取消息Master和Slave之间通过同步复制或异步复制来保持数据一致。5.1 同步复制SYNC_MASTERProducer发消息 → Master写入 → 等待Slave也写入 → Slave确认 → Master返回成功Master挂了Slave有完整数据可无缝接管每条消息要等Slave确认写入延迟增大5.2 异步复制ASYNC_MASTERProducer发消息 → Master写入 → 立即返回成功 → 后台异步同步给Slave性能高Master不等SlaveMaster挂了Slave可能少一部分最新数据有丢失风险5.3 刷盘复制组合选型组合可靠性性能适用场景同步刷盘同步复制最高最低金融级不差钱异步刷盘同步复制高中等推荐大多数生产环境异步刷盘异步复制一般最高日志类高吞吐同步刷盘异步复制高单机中等较少使用六、高可用方案Master挂了怎么办6.1 基础方案Slave接管消费Master宕机后Slave可以继续提供消息消费服务因为Slave有完整的CommitLog和ConsumeQueue副本。消费者会自动切换到Slave拉取消息。但有个问题Slave不能写。如果Master一直起不来新消息就没法发送了。6.2 DLedger模式RocketMQ 4.xDLedger是RocketMQ自研的基于Raft协议的分布式一致性组件。它做的事情多个Broker组成DLedger集群Master通过Raft选举产生Master挂了自动重新选举新Master数据在多个节点间通过Raft保证强一致这样Master宕机后集群能自动选出新Master实现自动故障转移。6.3 Controller模式RocketMQ 5.xRocketMQ 5.x引入了独立的Controller组件职责更清晰管理Broker的注册、心跳检测Broker存活状态Master挂了Controller指挥Slave晋升为新Master相比DLedger内嵌在Broker里Controller是独立部署的架构上更解耦适合大规模集群管理。6.4 售货柜场景高可用架构建议无人售货柜系统对消息可靠性要求较高订单和出货不能丢建议部署2Master2Slave同步复制开启Controller或DLedger自动主从切换订单/出货类消息用同步刷盘心跳/统计类消息用异步刷盘这样即使某台Broker物理机宕掉业务依然能正常运行消息不丢失。七、总结一张图概括RocketMQ消息存储全貌Producer → CommitLog(顺序写) → 异步构建 → ConsumeQueue(逻辑索引) └→ IndexFile(Key索引) │ 刷盘 ← PageCache ←────┘ │ ┌─────┴─────┐ 同步刷盘 异步刷盘 │ ┌─────┴─────┐ 同步复制 异步复制 │ │ Master←──→Slave │ Controller/DLedger 自动切换记住几个关键词CommitLog ConsumeQueue 顺序写 索引查找同步刷盘 不丢但慢异步刷盘 快但可能丢同步复制 Slave有完整数据异步复制 Slave可能少数据Controller/DLedger Master挂了自动选新Master搞懂这些遇到消息可靠性问题你心里就有谱了。
返回列表