面试知识库
中 进阶

RocketMQ架构#

一句话答案#

RocketMQ 四大组件:NameServer(无状态注册中心)、Broker(消息存储与转发)、Producer(发送方)、Consumer(消费方),Broker 主从部署,NameServer 去中心化。

核心要点

四大组件#

Producer → NameServer(查 Broker 地址)→ Broker(存储消息)→ Consumer
plaintext
组件职责特点
NameServer路由注册与发现无状态,去中心化,各节点独立
Broker消息存储、转发、过滤主从部署;默认读写都走 Master,Master 宕机或开启 slaveReadEnable 且 Master 内存压力大时才从 Slave 读
Producer消息发送从 NameServer 获取路由,直连 Broker
Consumer消息消费支持 Push / Pull(Push 底层是长轮询拉取);5.x 新增 SimpleConsumer + POP 消费

NameServer vs ZooKeeper#

维度NameServerZooKeeper
一致性最终一致(各节点独立)强一致(ZAB 协议)
复杂度极简,无选举复杂,需要选举
依赖无外部依赖需要独立集群

RocketMQ 选择 NameServer 因为消息路由不需要强一致性,最终一致够用。

Broker 存储模型#

CommitLog: 所有消息顺序追加写(逻辑上一个,物理上按 1G 切成多个 mmap 文件)
  → 高性能顺序写

ConsumeQueue: 每个 Topic 的每个 Queue 一个索引文件
  → 记录消息在 CommitLog 中的偏移量
  → 消费时先查 ConsumeQueue 再读 CommitLog

IndexFile: 可选的消息索引(按 Key 查询消息)
plaintext

设计优势: 所有 Topic 共用一个 CommitLog 顺序写 → 写性能不随 Topic 数增加而下降(对比 Kafka 每个 Partition 独立文件)。

RocketMQ 5.x 的变化#

  • Proxy:新增无状态 Proxy 层(gRPC 协议),客户端只连 Proxy,存储和计算可分开扩缩;也可以和 Broker 合并部署(Local 模式)。
  • POP 消费:Broker 端按消息分配,不再把队列绑死给某个消费者,消费者数可以超过队列数,Rebalance 影响小。
  • 任意时间延迟:定时/延迟消息不再限 18 个级别,可指定任意时间点(最长时长有上限:官方文档写默认 24h,开源 Broker 由 timerMaxDelaySec 控制,源码默认 3 天)。
  • 自动切主:Controller 模式(基于 DLedger/Raft)支持主从自动切换。

Kafka vs RocketMQ#

维度KafkaRocketMQ
定位高吞吐日志/流处理业务消息(事务/延迟/顺序)
存储每个 Partition 独立文件所有消息共用 CommitLog
事务消息面向流处理半消息 + 回查(业务事务)
延迟消息不原生支持原生支持(4.x 18 个固定级别;5.x 任意时间,有最长时长上限)
消息回溯按 offset 或时间戳(offsetsForTimes / --reset-offsets --to-datetime)按时间

面试回答(2分钟版)

RocketMQ的架构由四大组件组成:NameServer是无状态的路由注册中心,各节点独立互不通信,Broker启动时向所有NameServer注册;Broker负责消息的存储和转发,支持主从部署实现高可用,5.x 还能用 Controller 模式自动切主;Producer从NameServer获取路由信息后直连Broker发送消息;Consumer支持Push和Pull两种消费模式。RocketMQ选择自研NameServer而不用ZooKeeper,是因为消息路由不需要强一致性,最终一致就够用,而NameServer更简单无选举无外部依赖。存储模型是RocketMQ的核心亮点:所有Topic的消息都顺序追加写入同一个CommitLog文件,保证了极高的写入性能;每个Topic的每个Queue有一个ConsumeQueue索引文件记录消息在CommitLog中的偏移量,消费时先查ConsumeQueue再读CommitLog。这个设计和Kafka的区别在于Kafka每个Partition独立文件,Topic多了写性能会下降,而RocketMQ共用CommitLog写性能不受Topic数量影响。功能上RocketMQ更偏向业务消息,原生支持事务消息和延迟消息,5.x 起延迟消息支持任意时间,并引入无状态 Proxy 和 POP 消费模式。

追问与易错

追问方向:

  • “为什么不用 ZooKeeper?”→ 消息路由不需要强一致,NameServer 更简单
  • “CommitLog 和 ConsumeQueue 的关系?”→ CommitLog 存消息体,ConsumeQueue 存索引

易错点:

  • ❌ “NameServer 之间会同步数据”——各节点独立,Broker 向所有 NameServer 注册
  • ❌ “RocketMQ 和 Kafka 一样每个 Topic 独立存储”——RocketMQ 共用 CommitLog