深入学习RocketMQ的底层存储设计原理

简介: 文章深入探讨了RocketMQ的底层存储设计原理,分析了其如何通过将数据和索引映射到内存、异步刷新磁盘以及消息内容的混合存储来实现高性能的读写操作,从而保证了RocketMQ作为一款低延迟消息队列的读写性能。

前言

RocketMQ的是一款追求低延迟的消息队列,虽然他是存储在磁盘上的,但是他的读写性能还是非常之高,本文将分析他的存储设计,看看他是从哪些方面对性能有改善。

image.png

RocketMQ存储组成

我们可以把RocketMQ的Broker理解成一个数据库一样,数据库存储功能主要是读和写的功能,RocketMQ也一样。在数据库中,我们将数据写入数据和索引中,在RocketMQ中,我们将数据写到commitlog文件和consumequeue文件。RocketMQ数据和索引默认都存储在user.home目录下的store文件夹。

image.png

从上图可以看出,在RocketMQ中,数据存储存储在commitlog文件夹,就是消息内容存储,消息内容是通过commitlog文件存储的,并且消息内容是混合存储的,里面包含了所有topic的消息数据。

而索引有两部分,一个是consumequeue, 一个是index文件夹。

consumequeue部分是先按topic,topic下按队列进行分开存储的。我们一般是按topic消费我们的消息。这个时候consumequeue就可以派上用场了。

index索引文件是存储支持时间和消息key来检索消息的索引数据。

commitlog文件结构和写操作

发送消息到broker后,broker会开始写commitlog文件。在CommitLog类有对commitlog文件的写操作。

看下CommitLog的组成,里面包含了MappedFileQueue image.png

MappedFileQueue里面包含了文件数组,对应多个commitlog文件,每个commitlog文件默认存储1G大小的消息。 image.png

image.png

我们再看下MappedFileQueue里面真实操作文件的的对象其实是MappedFile

MappedFile的构造函数会调用init方法,里面就是通过RandomAccessFile创建commitlog的文件对象,并且将文件映射到内存MappedByteBuffer,也就是每次都是把消息先写入内存缓冲区,再写入磁盘。

image.png

发送消息的时候,其实会操作MappedFile将消息写入内存缓冲区MappedByteBuffer。这就是RocketMQ发消息快的一个原因。

image.png

最终刷新到磁盘是怎么做的呢? 会通过mappedByteBuffer.force()函数刷新到磁盘。

image.png

commitlog文件结构和读操作

读操作体现在查找消息的方法,在org.apache.rocketmq.store.CommitLog#getMessage函数。

首先是根据偏移量查找MapperFileimage.png

最终通过MapperFile查询消息内容。 image.png

consumeQueue组成以及读写操作

看到ConsumeQueue类里面的组成,和commitlog一样,同样持有了MappedFileQueue,那么读写consumeQueue,也是操作MappedFile

image.png

这样我们也能知道consumequeue的组成 image.png

需要注意的是,consumequeue不是同步构建的。RocketMQ专门设计了一个任务ReputMessageService。 他是异步将consumequeue数据构建出来,并且使用了一个异步线程FlushConsumeQueueService将consumequeu数据刷入磁盘。

image.png

也就是索引数据都是异步构建出来的。这个也是RocketMQ消息存储性能极高的原因。

总结

1、RocketMQ存储模块包含消息数据commitlog和消息索引consumequeu部分,他们都会将文件映射到内存,不会直接操作磁盘,这样做提高了IO效率。

2、消息数据comitlog是先写入内存缓存区,再异步刷新磁盘,而消息索引consumequeue是通过异步构建的

相关实践学习
快速体验阿里云云消息队列RocketMQ版
本实验将带您快速体验使用云消息队列RocketMQ版Serverless系列实例进行获取接入点、创建Topic、创建订阅组、收发消息、查看消息轨迹和仪表盘。
消息队列 MNS 入门课程
1、消息队列MNS简介 本节课介绍消息队列的MNS的基础概念 2、消息队列MNS特性 本节课介绍消息队列的MNS的主要特性 3、MNS的最佳实践及场景应用 本节课介绍消息队列的MNS的最佳实践及场景应用案例 4、手把手系列:消息队列MNS实操讲 本节课介绍消息队列的MNS的实际操作演示 5、动手实验:基于MNS,0基础轻松构建 Web Client 本节课带您一起基于MNS,0基础轻松构建 Web Client
相关文章
|
7月前
|
消息中间件 存储 缓存
RocketMQ原理—4.消息读写的性能优化
本文详细解析了RocketMQ消息队列的核心原理与性能优化机制,涵盖Producer消息分发、Broker高并发写入、Consumer拉取消息流程等内容。重点探讨了基于队列的消息分发、Hash有序分发、CommitLog内存写入优化、ConsumeQueue物理存储设计等关键技术点。同时分析了数据丢失场景及解决方案,如同步刷盘与JVM OffHeap缓存分离策略,并总结了写入与读取流程的性能优化方法,为理解和优化分布式消息系统提供了全面指导。
RocketMQ原理—4.消息读写的性能优化
|
7月前
|
消息中间件 存储 设计模式
RocketMQ原理—5.高可用+高并发+高性能架构
本文主要从高可用架构、高并发架构、高性能架构三个方面来介绍RocketMQ的原理。
2288 21
RocketMQ原理—5.高可用+高并发+高性能架构
|
7月前
|
存储 消息中间件 缓存
RocketMQ原理—3.源码设计简单分析下
本文介绍了Producer作为生产者是如何创建出来的、启动时是如何准备好相关资源的、如何从拉取Topic元数据的、如何选择MessageQueue的、与Broker是如何进行网络通信的,Broker收到一条消息后是如何存储的、如何实时更新索引文件的、如何实现同步刷盘以及异步刷盘的、如何清理存储较久的磁盘数据的,Consumer作为消费者是如何创建和启动的、消费者组的多个Consumer会如何分配消息、Consumer会如何从Broker拉取一批消息。
332 11
RocketMQ原理—3.源码设计简单分析下
|
7月前
|
存储 消息中间件 网络协议
RocketMQ原理—1.RocketMQ整体运行原理
本文详细解析了RocketMQ的整体运行原理,涵盖从生产者到消费者的全流程。首先介绍生产者发送消息的机制,包括Topic与MessageQueue的关系及写入策略;接着分析Broker如何通过CommitLog和ConsumeQueue实现消息持久化,并探讨同步与异步刷盘的优缺点。同时,讲解基于DLedger技术的主从同步原理,确保高可用性。消费者部分则重点讨论消费模式(集群 vs 广播)、拉取消息策略及负载均衡机制。网络通信层面,基于Netty的高性能架构通过多线程池分工协作提升并发能力。最后,揭示mmap与PageCache技术优化文件读写的细节,总结了RocketMQ的核心运行机制。
RocketMQ原理—1.RocketMQ整体运行原理
|
7月前
|
消息中间件 Java 数据管理
RocketMQ原理—2.源码设计简单分析上
本文介绍了NameServer的启动脚本、启动时会解析哪些配置、如何初始化Netty网络服务器、如何启动Netty网络服务器,介绍了Broker启动时是如何初始化配置的、BrokerController的创建以及包含的组件、BrokerController的初始化、启动、Broker如何把自己注册到NameServer上、BrokerOuterAPI是如何发送注册请求的,介绍了NameServer如何处理Broker的注册请求、Broker如何发送定时心跳
|
12月前
|
消息中间件 存储 Kafka
RocketMQ 工作原理图解,看这篇就够了!
本文详细解析了 RocketMQ 的核心架构、消息领域模型、关键特性和应用场景,帮助深入理解消息中间件的工作原理。关注【mikechen的互联网架构】,10年+BAT架构经验倾囊相授。
RocketMQ 工作原理图解,看这篇就够了!
|
消息中间件 存储 Kafka
MQ 消息队列核心原理,12 条最全面总结!
本文总结了消息队列的12个核心原理,涵盖消息顺序性、ACK机制、持久化及高可用性等内容。关注【mikechen的互联网架构】,10年+BAT架构经验倾囊相授。
|
4月前
|
消息中间件 数据管理 Serverless
阿里云消息队列 Apache RocketMQ 创新论文入选顶会 ACM FSE 2025
阿里云消息团队基于 Apache RocketMQ 构建 Serverless 消息系统,适配多种主流消息协议(如 RabbitMQ、MQTT 和 Kafka),成功解决了传统中间件在可伸缩性、成本及元数据管理等方面的难题,并据此实现 ApsaraMQ 全系列产品 Serverless 化,助力企业提效降本。
|
2月前
|
消息中间件 Java Kafka
消息队列比较:Spring 微服务中的 Kafka 与 RabbitMQ
本文深入解析了 Kafka 和 RabbitMQ 两大主流消息队列在 Spring 微服务中的应用与对比。内容涵盖消息队列的基本原理、Kafka 与 RabbitMQ 的核心概念、各自优势及典型用例,并结合 Spring 生态的集成方式,帮助开发者根据实际需求选择合适的消息中间件,提升系统解耦、可扩展性与可靠性。
185 1
消息队列比较:Spring 微服务中的 Kafka 与 RabbitMQ
|
消息中间件 JSON Java
开发者如何使用轻量消息队列MNS
【10月更文挑战第19天】开发者如何使用轻量消息队列MNS
823 99