加载中...
avatar
文章
42
标签
25
分类
21
首页
Java
Spring全家桶
  • Spring
  • SpringBoot
  • SpringCloud
JVM
源码
  • Mybatis
  • HashMap
归档
其他
  • 互联网电子书汇总
  • JAVA八股文指南
  • 历史
  • 相册
关于
Logo码农StormlingMQ系列(六)| RocketMQ 快速入门
搜索
首页
Java
Spring全家桶
  • Spring
  • SpringBoot
  • SpringCloud
JVM
源码
  • Mybatis
  • HashMap
归档
其他
  • 互联网电子书汇总
  • JAVA八股文指南
  • 历史
  • 相册
关于

MQ系列(六)| RocketMQ 快速入门

发表于2024-11-28|更新于2024-12-22|消息队列架构
|总字数:2.9k|阅读时长:9分钟|浏览量:

RocketMQ 快速入门


本参考链接:RocketMQ 是什么?
原作者:小白debug

前言

作为一个程序员,假设你有 A、B 两个服务,A 服务发出消息后,不想让 B 服务立马处理到。而是要过半小时才让 B 服务处理到,该怎么实现?
这类延迟处理消息的场景非常常见,举个例子,比如我每天早上到公司后都会点个外卖,我希望外卖能在中午送过来,而不是立马送过来,这就需要将外卖消息经过延时后,再投递到商家侧。

延时消息场景

延时消息场景

那么问题就来了,有没有优雅的解决方案?
当然有,没有什么是加一层中间层不能解决的,如果有,那就再加一层。
这次我们要加的中间层是消息队列 **RocketMQ**。

RocketMQ

RocketMQ 是什么?

RocketMQ 是阿里自研的国产消息队列,目前已经是 Apache 的顶级项目。和其他消息队列一样,它接受来自生产者的消息,将消息分类,每一类是一个 topic,消费者根据需要订阅 topic,获取里面的消息。

消息队列模型

是不是很像我们上篇文章里提到的消息队 Kafka,那么问题很自然就来了,既然都是消息队列,那它们之间有什么区别呢?

RocketMQ 和 Kafka 区别

RocketMQ 的架构其实参考了 Kafka 的设计思想,同时又在 Kafka 的基础上做了一些调整。

RocketMQ参考Kafka架构

这些调整,用一句话总结就是,”和 Kafka 相比,RocketMQ 在架构上做了减法,在功能上做了加法“。我们来看下这句话的含义。

在架构上做减法

我们来简单回顾下消息队列 Kafka 的架构。
kakfa 也是通过多个 topic 对消息进行分类。

topic分类

  • 为了提升单个 topic 的并发性能,将单个 topic 拆为多个 partition。

partition

  • 为了提升系统扩展性,将多个 partition 分别部署在不同 broker 上。
  • 为了提升系统的可用性,为 partition 加了多个副本。
  • 为了协调和管理 Kafka 集群的数据信息,引入Zookeeper作为协调节点。

kakfa架构

如果你对这些依旧很陌生,可以看看上篇文章《**MQ系列(五)|Kafka 快速入门**》。
Kafka 已经是非常强的消息队列了,我们来看下 RocketMQ 在 Kafka 架构的基础上,还能玩出什么花样来。

简化协调节点

zookeeper 太重 ,nameserver 替代 zookeeper

Zookeeper 在 Kafka 架构中会和 broker 通信,维护 Kafka 集群信息。一个新的 broker 连上 Zookeeper 后,其他 broker 就能立马感知到它的加入,像这种能在分布式环境下,让多个实例同时获取到同一份信息的服务,就是所谓的分布式协调服务。

Zookeeper的作用Zookeeper的作用

但 Zookeeper 作为一个通用的分布式协调服务,它不仅可以用于服务注册与发现,还可以用于分布式锁、配置管理等场景。 Kafka 其实只用到了它的部分功能,多少有点杀鸡用牛刀的味道。太重了。

所以 RocketMQ 直接将 Zookeeper 去掉,换成了 nameserver,用一种更轻量的方式,管理消息队列的集群信息。生产者通过 nameserver 获取到 topic 和 broker 的路由信息,然后再与 broker 通信,实现服务发现和负载均衡的效果。

nameserver是什么

当然,开发 Kafka 的大佬们后来也意识到了 Zookeeper 过重的问题,所以从 2.8.0 版本就支持将 Zookeeper 移除,通过 在 broker 之间加入一致性算法 raft 实现同样的效果,这就是所谓的 KRaft 或 Quorum 模式。

raft 算法可以看下这里:Raft 算法详解 | JavaGuide

KRaft模式

简化分区

Queue 替换 partition,增加一个 commitLog ,Queue放消息的简要信息(包含消息偏移量),commitLog 放具体的消息

我们知道,Kafka 会将 topic 拆分为多个 partition,用来提升并发性能。

partition是什么

在 RocketMQ 里也一样,将 topic 拆分成了多个分区,但换了个名字,叫 Queue,也就是”队列“。

RocketMQ中的队列

Kafka 中的 partition 会存储完整的消息体,而 RocketMQ 的 Queue 上却只存一些简要信息,比如消息偏移 offset,而消息的完整数据则放到”一个”叫 commitlog 的文件上,通过 offset 我们可以定位到 commitlog 上的某条消息。
Kafka 消费消息,broker 只需要直接从 partition 读取消息返回就好,也就是读第一次就够了。

img

而在 RocketMQ 中,broker 则需要先从 Queue 上读取到 offset 的值,再跑到 commitlog 上将完整数据读出来,也就是需要读两次。

img

那么问题就来了,看起来 Kafka 的设计更高效?为什么 RocketMQ 不采用 Kafka 的设计?
这就不得说一下 Kafka 的底层存储了。

Kafka 的底层存储

segment 小文件

Kafka 的 partition 分区,其实在底层由很多段(**segment)组成,每个 segment 可以认为就是个小文件**。将消息数据写入到 partition 分区,本质上就是将数据写入到某个 segment 文件下。

segment是什么

segment是什么

多个segment 文件下顺序列劣化成随机写,性能下降指标:8个分区 64个 topic

我们知道,操作系统的机械磁盘,顺序写的性能会比随机写快很多,差距高达几十倍。为了提升性能,Kafka 对每个小文件都是顺序写。
如果只有一个 segment 文件,那写文件的性能会很好。
但当 topic 变多之后,topic 底下的 partition 分区也会变多,对应的 partition 底下的 segment 文件也会变多。同时写多个 topic 底下的 partition,就是同时写多个文件,虽然每个文件内部都是顺序写,但多个文件存放在磁盘的不同地方,原本顺序写磁盘就可能劣化变成了随机写。于是写性能就降低了。

顺序写劣化为随机写

那问题又又来了,究竟多少 topic 才算多?这个看实际情况,但打太极从来不是我的风格。
我给一个经验值仅供参考,8 个分区的情况下,超过 64 topic, Kafka 性能就会开始下降。

RocketMQ 的底层存储

为了缓解同时写多个文件带来的随机写问题,RocketMQ 索性将单个 broker 底下的多个 topic 数据,全都写到”一个“逻辑文件 CommitLog 上,这就消除了随机写多文件的问题,将所有写操作都变成了顺序写。大大提升了 RocketMQ 在多 topic 场景下的写性能。

CommitLog的作用CommitLog的作用

注意上面提到的”一个“是带引号的,虽然逻辑上它是一个大文件,但实际上这个 CommitLog 由多个小文件组成。每个文件的大小是固定的,当一个文件被写满后,会创建一个新的文件来继续存储新的消息。这种方式可以方便地管理和清理旧的消息。

简化备份模型

kafka 将主broker 中 partition 同步 segment 文件数据到到 从 broker的副本 partition下 segement文件

rocketMQ 直接同步主 broker中的 commitLog 文件到 从 broker 中

我们知道,Kafka 会将 partition 分散到多个 broker 中,并为 partition 配置副本,将 partition 分为 leader和 follower,也就是主和从。broker 中既可能有 A topic 的主 partition,也可能有 B topic 的从 partition。
主从 partition 之间会建立数据同步,本质上就是同步 partition 底下的 segment 文件数据

Kafka主从parttion同步数据

RocketMQ 将 broker 上的所有 topic 数据到写到 CommitLog 上。如果还像 Kafka 那样给每个分区单独建立同步通信,就还得将 CommitLog 里的内容拆开,这就还是退化为随机读了。
于是 RocketMQ 索性以 broker 为单位区分主从,主从之间同步 CommitLog 文件,保持高可用的同时,也大大简化了备份模型。

RocketMQ主从broker同步

好了,到这里,我们熟悉的 Kafka 架构,就成了 RocketMQ 的架构。

Kafka架构

是不是跟 Kafka 的很像但又简化了不少?

RocketMQ架构

在功能上做加法

虽然 RocketMQ 的架构比 Kafka 的简单,但功能却比 Kafka 要更丰富,我们来看下。

消息过滤

RocketMQ 支持对消息打标,消费者根据 tag 过滤需要的数据,支持二级分类

kafka 需要获取全部消息,再过滤出需要的消息

我们知道,Kafka 支持通过 topic 将数据进行分类,比如订单数据和用户数据是两个不同的 topic,但如果我还想再进一步分类呢?比如同样是用户数据,还能根据 vip 等级进一步分类。假设我们只需要获取 vip6 的用户数据,在 Kafka 里,消费者需要消费 topic 为用户数据的所有消息,再将 vip6 的用户过滤出来。

而 RocketMQ 支持对消息打上标记,也就是打 tag,消费者能根据 tag 过滤所需要的数据。比如我们可以在部分消息上标记 tag=vip6,这样消费者就能只获取这部分数据,省下了消费者过滤数据时的资源消耗。

相当于 RocketMQ 除了支持通过 topic 进行一级分类,还支持通过 tag 进行二级分类。

tag二级过滤

支持事务

我们知道 Kafka 支持事务,比如生产者发三条消息 ABC,这三条消息要么同时发送成功,要么同时发送失败。

Kafka的事务
是,这确实也叫事务,但跟我们要的不太一样。

写业务代码的时候,我们更想要的事务是,”执行一些自定义逻辑“和”生产者发消息“这两件事,要么同时成功,要么同时失败。

而这正是 RocketMQ 支持的事务能力。

RocketMQ的事务

加入延时队列

kafka 实现费劲

如果我们希望消息投递出去之后,消费者不能立马消费到,而是过个一定时间后才消费,也就是所谓的延时消息,就像文章开头的定时外卖那样。如果我们使用 Kafka, 要实现类似的功能的话,就会很费劲。
但 RocketMQ 天然支持延时队列,我们可以很方便实现这一功能。

加入死信队列

kafka 原生不支持

消费消息是有可能失败的,失败后一般可以设置重试。如果多次重试失败,RocketMQ 会将消息放到一个专门的队列,方便我们后面单独处理。这种专门存放失败消息的队列,就是死信队列。
Kafka 原生不支持这个功能,需要我们自己实现。

消息回溯

kafka 调整offset

rocketMQ 还可以调整时间

Kafka 支持通过调整 offset 来让消费者从某个地方开始消费,而 RocketMQ,除了可以调整 offset, 还支持调整时间。

总结

  • RocketMQ 和 Kafka 相比,在架构上做了减法,在功能上做了加法
  • 跟 Kafka 的架构相比,RocketMQ 简化了协调节点和分区以及备份模型。同时增强了消息过滤、消息回溯和事务能力,加入了延迟队列,死信队列等新特性

延伸

最后遗留一个问题。
现在看起来,RocketMQ 好像各方面都比 Kafka 更能打。
但 Kafka 却一直没被淘汰,说明 RocketMQ 必然是有着不如 Kafka 的地方。
是啥呢?
性能,严格来说是吞吐量。
这就很奇怪了,**为什么 RocketMQ 参考了 Kafka 的架构,性能却还不如 Kafka**?

文章作者: stormling
文章链接: http://www.stormling.top/posts/15036.html
版权声明: 本博客所有文章除特别声明外,均采用 CC BY-NC-SA 4.0 许可协议。转载请注明来源 码农Stormling!
消息队列架构
cover of previous post
上一篇
MQ系列(七)| RocketMQ 为什么性能不如Kafka?
RocketMQ 为什么性能不如 Kafka? RocketMQ 使用的是 mmap 零拷贝技术,而 kafka 使用的是 sendfile (硬件设备技术 SG-DMA,不影响(不占用)CPU工作) mmap 内核缓冲区->映射用户缓冲区->内核缓冲区->网卡sendfile 内核缓冲区-> SG-DMA -> 网卡 在上篇文章《rocketmq 是什么》中,我们了解到 RocketMQ 的架构其实参考了 kafka 的设计思想,同时又在 kafka 的基础上做了一些调整。看起来,RocketMQ 好像各方面都比 kafka 更能打。 但 kafka 却一直没被淘汰,说明 RocketMQ 必然是有着不如 kafka 的地方。是啥呢?性能,严格来说是吞吐量。阿里中间件团队对它们做过压测,同样条件下,kafka 比 RocketMQ 快 **50%**左右。但即使这样,RocketMQ 依然能每秒处理 10w 量级的数据,依旧非常能打。你不能说 RocketMQ 弱,只能说 Kafka 性能太强了。 不过这就很奇怪了,为什么...
cover of next post
下一篇
MQ系列(五)| Kafka 快速入门
Kafka 快速入门介绍 参考:Kafka 是什么? 架构一个高性能,高扩展性,高可用,支持持久化的超强消息队列,它就是我们常说的消息队列 KafkaZookeeper 协调管理多个 broker 组成,内部有多个 topic 分类,每个 topic 又分成多个 partition ,每个 partition 有多个副本 replia,不同的partition 会分布在不同 broker 上,提升性能同时,还增加了系统可用性和可扩展性 高性能 对消息进行分类,每个类是一个 topic 单个 topic 的消息可能过多,可将单个队列拆分成多个段,每段就是一个分区 partition ,每个消费者负责一个 partition 高扩展性可将 partition 分部在多台设备,每台设备代表一个 broker 高可用存在一个问题,如果其中一个partition所在的 broker 挂了,那么这部分的消息不久丢失了吗? 可以给partition 多加几个副本 replica,从中分为 Leader 和 Follower,Leader 负责生产者和消费者的读写,Follower...
相关推荐
cover
2024-11-30
MQ系列(七)| RocketMQ 为什么性能不如Kafka?
RocketMQ 为什么性能不如 Kafka? RocketMQ 使用的是 mmap 零拷贝技术,而 kafka 使用的是 sendfile (硬件设备技术 SG-DMA,不影响(不占用)CPU工作) mmap 内核缓冲区->映射用户缓冲区->内核缓冲区->网卡sendfile 内核缓冲区-> SG-DMA -> 网卡 在上篇文章《rocketmq 是什么》中,我们了解到 RocketMQ 的架构其实参考了 kafka 的设计思想,同时又在 kafka 的基础上做了一些调整。看起来,RocketMQ 好像各方面都比 kafka 更能打。 但 kafka 却一直没被淘汰,说明 RocketMQ 必然是有着不如 kafka 的地方。是啥呢?性能,严格来说是吞吐量。阿里中间件团队对它们做过压测,同样条件下,kafka 比 RocketMQ 快 **50%**左右。但即使这样,RocketMQ 依然能每秒处理 10w 量级的数据,依旧非常能打。你不能说 RocketMQ 弱,只能说 Kafka 性能太强了。 不过这就很奇怪了,为什么...
cover
2024-11-27
MQ系列(五)| Kafka 快速入门
Kafka 快速入门介绍 参考:Kafka 是什么? 架构一个高性能,高扩展性,高可用,支持持久化的超强消息队列,它就是我们常说的消息队列 KafkaZookeeper 协调管理多个 broker 组成,内部有多个 topic 分类,每个 topic 又分成多个 partition ,每个 partition 有多个副本 replia,不同的partition 会分布在不同 broker 上,提升性能同时,还增加了系统可用性和可扩展性 高性能 对消息进行分类,每个类是一个 topic 单个 topic 的消息可能过多,可将单个队列拆分成多个段,每段就是一个分区 partition ,每个消费者负责一个 partition 高扩展性可将 partition 分部在多台设备,每台设备代表一个 broker 高可用存在一个问题,如果其中一个partition所在的 broker 挂了,那么这部分的消息不久丢失了吗? 可以给partition 多加几个副本 replica,从中分为 Leader 和 Follower,Leader 负责生产者和消费者的读写,Follower...
cover
2024-11-24
MQ系列(四)| RabbitMQ 死信队列和延迟队列
死信队列死信是什么死信:无法被消费的消息。由于特定的原因导致队列中的某些消息无法被消费,这些消息没有后续的处理,就会变成死信。当消息在队列中无法被正常消费时,会被发送到死信队列中。 死信来源消息 TTL队列达到最大长度消息拒签(basicNack 或 basicReject)且重入队列为false(requeue=false) 死信架构 消息TTL 名称 交换机 路由键 类型 特征 参数 普通交换机 normal_exchange zhangsan direct / / 普通队列 normal_queue zhangsan / TTL DLX DLK x-dead-letter-exchange:dead_exchangex-dead-letter-routing-key:lisix-message-ttl: 10 * 1000 死信交换机 dead_exchange lisi direct / / 死信队列 dead_queue lisi / / / 生产者发送消息10条消息到队列...
cover
2024-11-20
MQ系列(三)| RabbitMQ 消息确认机制
RabbitMQ 消息确认机制 :heavy_exclamation_mark::heavy_exclamation_mark::heavy_exclamation_mark:温馨提示:基于JDK17、SpringBoot 2.1.8.RELEASE 版本,由于RabbitMQ 在 SpringBoot3+ 的配置项有所不同, 所以请严格按照该本版来使用,挖一坑:【后续会出一个SpringBoot3+版本的配置相关教程】 架构 概念保证消息不丢失,可靠抵达,可以使用事务消息,性能下降250倍 为此引入确认机制 生产者确认回调:publisher confirmCallback 生产者退回回调:publisher returnCallback未投递到queue退回模式 消费者确认:consumer ack确认机制 ComfirmCallback【生产者确认回调】 概念:ComfirmCallback是生产者消息确认机制的一部分。当生产者发送消息到 RabbitMQ 的交换器(Exchange)后,RabbitMQ 会返回一个确认消息给生产者,这个确认过程可以通过...
cover
2024-11-14
MQ系列(二)| RabbitMQ 整合 SpringBoot
RabbitMQ 整合 SpringBoot概述 大多应用中,可通过消息服务中间件来提升系统异步通信、扩展解耦能力、流量削峰 消息服务中两个重要概念:消息代理(`message broker`)和目的地(`destination`) 当消息发送者发送消息以后,将由消息代理接管,消息代理保证消息传递到指定目的地。 消息队列主要有两种形式的目的地1. 队列(`queue`):点对点消息通信(`point-to-point`) 2. 主题(`topic`):发布(`publish`)/订阅(`subscribe`)消息通信 RabbitMQ 架构图 概念生产者 Producer生产者是消息的发送方,它将消息发送到 RabbitMQ 的交换器中。 ✨消息 Message 消息=消息头+消息体,根据routekey发送到指定的交换机 Exchange 消息头:含有各种属性 routing-key(路由键)、priority(优先级)、delivery-mode(指出该消息可能需要持久性存储)等。 ✨消息代理...
cover
2024-11-10
MQ系列(一)| RabbitMQ 快速入门
RabbitMQ 快速入门 官网:https://www.rabbitmq.com/ 入门教程:https://www.rabbitmq.com/tutorials 最新版本:4.0.2 版本参考:JDK17、Maven Or Gradle 1、简介RabbitMQ是一个可靠且成熟的消息传递和流代理,易于部署在云环境、本地和本地机器上。它目前被全球数百万人使用。 2、为什么使用公司业务场景核心:解耦、异步、削峰 2.1、解耦A系统发数据给到BCD系统,如果E系统需要接入?C系统不需要了?A系统的负责人就需要来回修改接口对接其他系统。 如果使用MQ,A系统产生一条数据,发送到MQ中,那个系统需要数据自己去MQ消费。如果新的系统需要数据,直接从MQ中消费;某个系统不需要数据的话,取消消费这个MQ即可。这样A系统不需要考虑谁发送数据给谁,不需要考虑是否调用成功、失败超时等问题。 总结:通过一个MQ,Pub/Sub发布订阅消息模型,A系统就和其他系统彻底耦合了。 2.2.1、项目应用...

评论
ValineGitalk
avatar
stormling
文章
42
标签
25
分类
21
Follow Me
公告
欢迎大家来到Stormling博客
目录
  1. 1. RocketMQ 快速入门
    1. 1.1. 前言
    2. 1.2. 延时消息场景
      1. 1.2.1. RocketMQ 是什么?
      2. 1.2.2. RocketMQ 和 Kafka 区别
    3. 1.3. 在架构上做减法
      1. 1.3.1. 简化协调节点
      2. 1.3.2. 简化分区
    4. 1.4. Kafka 的底层存储
      1. 1.4.1. segment是什么
    5. 1.5. RocketMQ 的底层存储
      1. 1.5.1. 简化备份模型
    6. 1.6. 在功能上做加法
      1. 1.6.1. 消息过滤
      2. 1.6.2. 支持事务
      3. 1.6.3. 加入延时队列
      4. 1.6.4. 加入死信队列
      5. 1.6.5. 消息回溯
    7. 1.7. 总结
    8. 1.8. 延伸
最新文章
面向八股文面试专场
面向八股文面试专场2025-01-22
【每日早报】-2025-01-21 - 星期二
【每日早报】-2025-01-21 - 星期二2025-01-21
规则引擎 Drools 8+ 快速入门
规则引擎 Drools 8+ 快速入门2024-12-11
数据库系列(二) | Mybatis Plus 3.0+快速入门
数据库系列(二) | Mybatis Plus 3.0+快速入门2024-12-09
分布式系列(二) | Redisson分布式锁
分布式系列(二) | Redisson分布式锁2024-12-05
©2019 - 2025 By stormling
码农Stormling程序员,关注公众号【码农Stormling】回复【面试】获取最全面试pdf
搜索
数据加载中