RocketMQ知识图谱总结

1,178 阅读3分钟

前言

本博客是观看中通架构师丁威老师《rocketmq技术内幕》总结,以及网上一些技术博客,仅用于个人学习以及分享个人知识盲区。

RocketMQ

组成

producer,consumer,broker,namespace

提高性能地方

Message Queue 是broker上分片的最小单位,也能提高消费性能

过期机制

commitlog不管有没有消费,72小时之后会删除

高可用

producer:重试,broker不可用暂时跳过 broker:同步、异步刷盘 consumer:ack,至少一次消费

NameSpace

为broker提供注册服务,让producer可以拿到对应的ip然后请求储存数据。 10s检测存活 broker宕机,客户端去拉取,30s后才能感应

如果broker宕机会咋样?

A:namespace集群是不会进行互相同步的,就是各自有各自的数据。broker宕机不会立刻删除,而是会超过120s心跳之后再删除。

那如果不删除producer怎么保证消息正常发送?

A:producer会重试去发送消息,然后也会避开之后失败的broker。

刷盘

同步刷盘 MapperFile flush

异步刷盘 先追加ByteBuffer,但是没有刷盘,过一段时间再刷盘

消息储存

为了性能,Message Queue 很多文件

Index File加快消息的检索 offset关系:key topic#msgId commitlog:储存所有消息 consume queue :供消费者消费,会储存commitlog offset|size|tag hashcode 通过offset去检索commitlog

MQ写入过程

  1. 写入commitlog
  2. 创建消息全局唯一id(需要获取写锁)
  3. IP+端口号+消息偏移量
  4. msgId-->内容
  5. 改之前的偏移量
  6. 释放锁
  7. 异步写入consumer queue,以及index file。(通过)

提高性能所做操作

内存映射文件,提高IO

异步写入consumer queue不同步的问题 比如说commitlog写入成功,但是在异步写入consume queue的时候,宕机了。这时会根据abort文件去判断,启动的时候如果存在则是异常宕机,不存在则是正常关机,会有个关闭回调钩子去删除这个文件。 如果abort文件存在,则需要检测是否同步正常。

消息发送

顺序消息 全局顺序:只能设置止盈一个主题队列,牺牲性能 局部顺序:把它放在同一个消息队列里头

send(List<MessageQueue> queue){
	orderId%queue.size = ?;
	return ?;
}

消息发送流程

graph LR
A(校验消息) -->B(查找路由)
B(校验消息) -->C(namespace会根据broker去排序) --> D(消息发送)

消息消费

具体原理

rocketmq采用长轮询去拉取消息,5s一次,避免消费端消息堆积、压力啥的。 依据:消息队列最大偏移量>待拉取偏移量

无法实时监听消息到达? 到达的时候会去唤醒线程出发检查

消费模式 集群:监听一个topic的消费组,只有一个能消费 广播:都能消费一次

拉取流程

集群:会向broker加锁(队列)比如说忽然新增消费者,broker进行queue重新分配,由于queue当前锁没有释放,所以之前分配的队列不用当心会被其他新的消费者消费,会延迟等到下一次负载

在这里插入图片描述 消费之后会将本地offersetSrote跟broker offerset进行同步 在这里插入图片描述

消费流程

graph LR
A(消费成功 consume_success) -->C(ack)
B(消费失败 consume_later) -->C(ack) 
C(ack) --> D(发送成功,消费失败的话,重新消费)
C(ack) --> E(发送失败,会延迟5S继续消费)

接收到consume_later

会创建跟之前一样的消息,唯一的msgid,放到commitlog,异步到consume queue

消息重复消费场景

消息消费之后,ack因为网络问题没有提交成功,需要做消息幂等性问题

多次消费失败

如果多次消费失败会进入DLQ,然后进行人工处理

消费进度,offerset储存

我们可以看到不管是消息储存,或者消费等等都是依据offerset去处理的,在集群模式下是保存在broker,为了集群一致。在广播模式是保存在消费端各自保存。

tag过滤

consume queue |- 8 Byte -|-4 Byte-|- 8 Byte -| commitlog offerset size tag hashcode

事务消息

采用两段式,以及定时扫描消息状态表来回滚或者提交(主要防范超时问题)