一、源码环境搭建
主要功能模块
最新版本:5.3.3
- broker:Broker模块(broke启动进程)。
- client:消息客户端,包含消息生产者、消费者相关类。
- example:RocketMQ示例代码。
- namesrv:NameServer模块。
- store:消息存储模块。
- remoting:远程访问模块。
(二)源码启动服务
- 编译指令:
mvn clean install -Dmaven.test.skip=true。 - 启动NameServer:运行
org.apache.rocketmq.namesrv.NamesrvStartup类,可通过-c参数指定配置文件,-p参数打印生效参数。 - 启动Broker:启动入口为
broker模块的BrokerStartup类,可通过-c参数指定broker.conf文件,-p或-m参数打印配置信息。
(三)读源码的方法
- 带着问题读源码,避免盲目阅读。
- 采用“小步快走”策略,分阶段逐步理解源码。
- 及时总结,验证扩展功能,理解单元测试。
二、源码热身阶段
(一)NameServer的启动过程
- 核心作用:提供Broker端的服务注册与发现功能,类似微服务中的注册中心。
- 启动入口:
org.apache.rocketmq.namesrv.NamesrvStartup类,核心是构建并启动NamesrvController。 - 核心组件:包括
RouteInfoManager(路由管理)、BrokerHousekeepingService(Broker状态管理)、NettyRemotingServer(Netty服务端)等。

(二)Broker服务启动过程
- 核心作用:处理消息存储、转发等核心业务。
- 启动入口:
BrokerStartup类的main方法,围绕BrokerController对象启动。 - 核心配置:
BrokerConfig(服务配置)、MessageStoreConfig(消息存储配置)、NettyServerConfig(Netty服务端配置)等。 - 核心服务:启动了
messageStore(消息存储)、remotingServer(Netty服务端)、brokerOuterAPI(对外通信)等服务。

三、小试牛刀阶段
(一)Netty服务注册框架
- 核心组件:
RemotingServer(服务端)和RemotingClient(客户端),基于Netty实现远程调用。 - 通信协议:
RemotingServer接口有NettyRemotingServer和MultiProtocolRemotingServer实现,支持不同协议。 - 请求处理:请求封装为
RemotingCommand对象,通过processorTable注册处理器处理不同请求,支持同步和异步调用。

(二)Broker心跳注册管理
- 注册过程:Broker启动后通过
registerBrokerAll方法向NameServer注册心跳,定时任务以30秒间隔持续发送心跳。 - NameServer管理:通过
RouteInfoManager维护Broker信息,启动定时任务扫描不活动Broker。 - 设计优势:NameServer轻量,集群只需一个节点存活,牺牲数据一致性换取可用性。

(三)Producer发送消息过程
- 启动流程:调用
DefaultMQProducerImpl.start方法,通过MQClientFactory启动服务,注册到producerTable。

- 负载均衡:默认轮询
MessageQueue,失败后跳过该Broker;可通过MessageQueueSelector指定队列,实现局部有序。 - 路由管理:维护
topicPublishInfoTable缓存,NameServer挂掉后仍可基于本地缓存发送消息。

(四)Consumer拉取消息过程
- 启动流程:通过
MQClientFactory启动,注册到consumerTable,设置AllocateMessageQueueStrategy分配队列。

- 消费模式:
- 集群模式:Offset保存在Broker,MessageQueue平均分配给消费者。
- 广播模式:Offset保存在本地,所有消费者获取所有MessageQueue。
- 顺序消费:通过锁定队列,保证同一队列消息顺序处理;并发消费不控制队列,多线程并发处理。

(五)客户端负载均衡管理总结
- Producer负载均衡:轮询MessageQueue,支持故障规避和自定义选择器。

- Consumer负载均衡:集群模式下通过多种算法分配MessageQueue,广播模式下所有消费者获取所有队列。

四、融汇贯通阶段
(一)消息持久化设计
- 文件结构:
- CommitLog:存储消息元数据,顺序写入,每个文件1G。
- ConsumeQueue:存储消息在CommitLog的索引,一个MessageQueue一个文件。
- IndexFile:提供按key或时间查询消息的索引。
- 辅助文件:
checkpoint(检查点)、config(配置)、abort(服务关闭标识)。

- commitLog写入:加锁保证顺序写入,通过
mappedFile.appendMessage实现顺序写,写入后触发刷盘和主从复制。 - 刷盘机制:
- 同步刷盘:通过
GroupCommitService等待刷盘完成,数据安全性高。
- 同步刷盘:通过

-
- 异步刷盘:通过
CommitRealTimeService定时刷盘,性能更高。
- 异步刷盘:通过
- 主从复制:
DefaultHAService启动守护进程,实现主从同步复制和异步复制。 - 索引分发:
reputMessageService后台线程分发消息,构建ConsumeQueue和IndexFile索引。 - 过期文件删除:定时任务检查CommitLog和ConsumeQueue文件,超过72小时删除,可通过配置调整。

7.文件索引结构

(二)延迟消息机制
- 固定延迟级别:消息存入
SCHEDULE_TOPIC_XXXX主题对应队列,scheduleMessageService定时扫描,延迟时间到后转储回原主题。 - 指定时间点:消息存入
rmq_sys_wheel_timer主题,通过时间轮算法(TimerWheel)判断到期时间,到期后转储。



(三)长轮询机制
- 功能作用:避免Consumer空轮询,缓存Pull请求,消息到达时及时通知Consumer。
- 实现流程:
PullMessageProcessor处理请求,PullRequestHoldService后台线程检查缓存请求,消息到达时触发通知。

五、基于RocketMQ源码理解零拷贝与顺序写
(一)顺序写加速文件写入磁盘
- 原理:提前申请连续磁盘空间,避免随机写寻址,性能接近内存级别。
- 实现:RocketMQ通过
mappedFile.appendMessage实现顺序写,CommitLog文件固定大小。


(二)刷盘机制保证消息不丢失
- PageCache缓存:消息先写入PageCache,需刷盘到磁盘才能持久化。
- 刷盘方式:同步刷盘和异步刷盘,可通过
flushDiskType配置。
(三)零拷贝加速文件读写
- mmap文件映射:将文件映射到用户态内存,减少内核态与用户态数据拷贝,适合小文件。


- sendFile机制:内核态直接传输数据,无需用户态参与,适合大数据传输。


- RocketMQ应用:大量使用mmap机制,功能丰富;Kafka更多使用sendfile,性能更高。

1514

被折叠的 条评论
为什么被折叠?



