「 预计阅读 6 分钟 」

旁白:这是一篇拖更了N久的文章...0.0(看不见我~)

往期回顾

前端框架 jQuery 和 Vue 如何选择?

安全框架 Shiro 和 Spring Security 如何选择?

正文

 

消息队列(MQ)

在百度百科中,消息队列(MQ)是这么解释的:“消息队列”是在消息的传输过程中保存消息的容器(可存可取)。

它是分布式系统中重要的组件,使用消息队列主要是为了通过异步处理提高系统性能和削峰和降低系统耦合性。

  • 异步处理:多应用对消息队列中同一消息进行处理,应用间并发处理消息,相比较串行处理,减少处理时间;

  • 应用耦合:多应用通过消息队列对同一消息进行处理,避免调用接口失败导致整个过程失败;

  • 限流消峰:广泛应用于秒查或抢购活动中,避免某一刻流量过导致应用系统挂掉的情况;

目前使用较多的消息队列有 ActiveMQ 、RocketMQ 、RabbitMQ 和 Kafka 等。

消息队列的两种模式
消息队列包括两种模式:点对点模式 和 发布/订阅模式。
1)点对点模式

点对点模式下包括三个角色:

  • 消息队列

  • 发送者 (生产者)

  • 接收者(消费者)

消息发送者生产消息发送到queue中,然后消息接收者从queue中取出并且消费消息。消息被消费以后,queue中不再有存储,所以消息接收者不可能消费到已经被消费的消息。

点对点模式特点:

  • 每个消息只有一个接收者(Consumer)(即一旦被消费,消息就不再在消息队列中);

  • 发送者和接收者间没有依赖性,发送者发送消息之后,不管有没有接收者在运行,都不会影响到发送者下次发送消息;

  • 接收者在成功接收消息之后需向队列应答成功,以便消息队列删除当前接收的消息;

2)发布/订阅模式

发布/订阅模式下包括三个角色:

  • 角色主题(Topic)

  • 发布者(Publisher)

  • 订阅者(Subscriber)

发布者将消息发送到Topic,系统将这些消息传递给多个订阅者。

发布/订阅模式特点:

  • 每个消息可以有多个订阅者;

  • 发布者和订阅者之间有时间上的依赖性。针对某个主题(Topic)的订阅者,它必须创建一个订阅者之后,才能消费发布者的消息。

  • 为了消费消息,订阅者需要提前订阅该角色主题,并保持在线运行;

异步处理

具体场景:用户为了使用某个应用,进行注册,系统需要发送注册邮件和注册短信。

对于该流程有两种处理方式:并行和串行。

1)串行处理:写入注册信息后,先发送注册邮件,再发送注册短信。

这种方式下,需要等发送短信处理完成后才完成注册。

2)并行处理:写入注册信息后,同时处理发邮件和发短信。

这种方式下,需要等发送短信和发送邮件处理完成后才完成注册。

假设上面三个子系统处理耗时均为:50ms,且不考虑网络延迟,系统卡顿等因素,则总的处理时间为:
串行:50ms + 50ms + 50 ms = 150ms
并行:50ms + 50ms = 100ms
使用消息队列结果将如何呢?
若使用消息队列,写入完注册信息后,再将信息写入消息队列就能直接返回成功给客户端了,然后注册完成。
现在总的响应时间依赖于写入消息队列的时间,而写入消息队列的时间是很快的,基本可以忽略不计。因此总的处理时间相比串行提高了 2 倍,相比并行提高了 1 倍。
应用解耦
具体场景:A 系统每次产生数据时,都要将数据发给 BC 两个系统(通过接口调用)。这个时候新增了一个 D 系统,如下图:

在这个场景中,A 系统和其他几个系统乱七八糟的耦合在一起,当 A 系统中产生一条数据时,需要将数据发给各个系统。
每次项目中新增了系统,A 系统都需要修改代码,还要时刻担心那个系统挂掉了,信息没发送过去要不要重发,那个系统又不要该数据了,这时求 A 系统负责人的心理阴影...
如果使用 MQ,A 系统产生一条数据后,只需要插入到 MQ 里面去,那个系统需要就去 MQ 里消费。如果新增了一个系统,那么订阅 MQ 的消息即可;同理那个系统不再需要该数据,那么只要取消订阅就行了。

通过一个 MQ, Pub/Sub 发布订阅消息模型,A 系统就跟其他系统实现解耦了。
限流削峰
具体场景:某电商网站开展秒杀活动,一般由于瞬间访问暴增,服务器收到请求过大,可能出现无法处理请求或崩溃的情况。

加入消息队列后,系统就可以从消息队列中读取数据,相当于做了一次缓冲,超出系统处理之外的请求会积压在消息队列中,等高峰期已过,就会快速将积压在队列中的数据处理完。
消息队列有什么优缺点
优点上面已经说了,就是在特殊场景下有其对应的好处,解耦、异步、削峰。
缺点有以下几个:
  • 系统可用性降低
    系统引入的外部依赖越多,越容易挂掉。本来你就是 A 系统调用 BCD 三个系统的接口就好了,人 ABCD 四个系统好好的,没啥问题,你偏加个 MQ 进来,万一 MQ 挂了咋整,MQ 一挂,整套系统崩溃的,你不就完了?如何保证消息队列的高可用,可以点击这里查看。
  • 系统复杂度提高
    硬生生加个 MQ 进来,你怎么保证消息没有重复消费?怎么处理消息丢失的情况?怎么保证消息传递的顺序性?头大头大,问题一大堆,痛苦不已。
  • 一致性问题
    A 系统处理完了直接返回成功了,人都以为你这个请求就成功了;但是问题是,要是 BCD 三个系统那里,BD 两个系统写库成功了,结果 C 系统写库失败了,咋整?你这数据就不一致了。
所以消息队列实际是一种非常复杂的架构,你引入它有很多好处,但是也得针对它带来的坏处做各种额外的技术方案和架构来规避掉,做好之后,系统复杂度提升了一个数量级,也许是复杂了 10 倍。但是关键时刻,用,还是得用的。
RabbitMQ/ActiveMQ/RocketMQ/Kafka对比
这里列举了上述四种消息队列的差异对比(图片来源:https://www.cnblogs.com/javalyy/p/8856731.html):
图片来源(https://doocs.gitee.io/advanced-java/#/docs/high-concurrency/why-mq)
总结
一般业务系统要引入 MQ,最早大家都是用 ActiveMQ,但是现在大家用的不多了,没经过大规模吞吐量场景的验证,社区也不是很活跃,不推荐使用。
中小型公司,技术实力较为一般,技术挑战不是特别高,用 RabbitMQ 是不错的选择,大型公司,基础架构研发实力较强,用 RocketMQ 是很好的选择。
如果是高性能分布式、大数据领域的实时计算、日志采集等场景,用 Kafka 是业内标准。

广泛来说,电商、金融等对事务性要求很高的,可以考虑RabbitMQ和RocketMQ,对性能要求高的可考虑Kafka。

 
如果你觉得文章不错,欢迎在看、转发、赞赏一条龙,你的支持就是我最大的动力。
 

本文原发于 同名微信公众号「程序员的成长之路」,回复「1024」你懂得,给个赞呗。

回复 [ 520 ] 领取程序员最佳学习方式

回复 [ 256 ] 查看 Java 程序员成长规划

消息队列 ActiveMQ 、RocketMQ 、RabbitMQ 和 Kafka 如何选择?的更多相关文章

  1. 为什么使用消息队列?消息队列有什么优点和缺点?Kafka、ActiveMQ、RabbitMQ、RocketMQ 都有什么优点和缺点?

    面试题 为什么使用消息队列? 消息队列有什么优点和缺点? Kafka.ActiveMQ.RabbitMQ.RocketMQ 都有什么区别,以及适合哪些场景? 面试官心理分析 其实面试官主要是想看看: ...

  2. 消息队列—ActiveMQ

    1.   学习计划 1.什么是MQ 2.MQ的应用场景 3.ActiveMQ的使用方法. 4.使用消息队列实现商品同步. 2.   同步索引库分析 方案一:在manager(后台)中,添加商品的业务逻 ...

  3. 消息队列——ActiveMQ使用及原理浅析

    文章目录 引言 正文 一.ActiveMQ是如何产生的? 产生背景 JMS规范 基本概念 JMS体系结构 二.如何使用? 基本功能 消息传递 P2P pub/sub 持久订阅 消息传递的可靠性 事务型 ...

  4. 消息队列介绍、RabbitMQ&Redis的重点介绍与简单应用

    消息队列介绍.RabbitMQ&Redis的重点介绍与简单应用 消息队列介绍.RabbitMQ.Redis 一.什么是消息队列 这个概念我们百度Google能查到一大堆文章,所以我就通俗的讲下 ...

  5. 进击的Python【第十一章】:消息队列介绍、RabbitMQ&Redis的重点介绍与简单应用

    消息队列介绍.RabbitMQ.Redis 一.什么是消息队列 这个概念我们百度Google能查到一大堆文章,所以我就通俗的讲下消息队列的基本思路. 还记得原来写过Queue的文章,不管是线程queu ...

  6. 20190418 CentOS7实用技能综合:系统安装 + WinScp客户端连接 + 防火墙端口号iptables + Nginx编译安装 + MySQL编译安装 + Redis编译安装 + MongoDB编译安装 + ActiveMQ/RocketMQ/RabbitMQ编译安装 + ...各类常用生产环境软件的编译安装

    系统安装 + WinScp客户端连接 + 防火墙端口号iptables + Nginx编译安装 + MySQL编译安装 + Redis编译安装 + MongoDB编译安装 + ActiveMQ/Roc ...

  7. 消息队列ActiveMQ的使用详解

    通过上一篇文章 <消息队列深入解析>,我们已经消息队列是什么.使用消息队列的好处以及常见消息队列的简单介绍. 这一篇文章,主要带大家详细了解一下消息队列ActiveMQ的使用. 学习消息队 ...

  8. activemq、rabbitmq、kafka原理和比较

    一.activemq 虽然是java写的消息队列,但是提供Java, C, C++, C#, Ruby, Perl, Python, PHP各种客户端,所以语言上是没什么问题的.配置和使用,基本上是j ...

  9. java之消息队列ActiveMQ实践

    原创论文:https://www.cnblogs.com/goujh/p/8510239.html 消息队列的应用场景: 消息队列应用场景 异步处理,应用解耦,流量削锋和消息通讯四个场景 异步处理: ...

随机推荐

  1. java通过代理创建Conncection对象与自定义JDBC连接池

    最近学习了一下代理发现,代理其实一个蛮有用的,主要是用在动态的实现接口中的某一个方法而不去继承这个接口所用的一种技巧,首先是自定义的一个连接池 代码如下 import java.lang.reflec ...

  2. uC/OS-III 时钟节拍(一)

    时钟节拍就是操作系统的时基,操作系统要实现时间上的管理,必须依赖于时基(时基即时间基准,操作系统的基准时钟). uC/OS-III时钟节拍的实现过程 时钟节拍就是系统以固定的频率产生中断(时基中断), ...

  3. php-fpm启动,重启,退出

    首先确保php-fpm正常安装,运行命令php-fpm -t输出查看: ##确定php-fpm配置正常 [root@iz2vcf47jzvf8dxrapolf7z php7.-Oct-::] NOTI ...

  4. Shell之脚本检查与调试

    目录 Shell之脚本检查与调试 参考 脚本语法检查 脚本运行调试 Shell之脚本检查与调试

  5. 除了Web和Node,JavaScript还能做什么

    前言 提起JavaScript,我们也许经常会想到的是,可以用来写Web页面嘛,又或者,会想起Node.js 这个服务端环境,搞前后端同构. 那么,除此之外, JavaScript还可以做什么?   ...

  6. linux分析工具之vmstat详解

    一.概述 vmstat命令是最常见的Linux/Unix监控工具,可以展现给定时间间隔的服务器的状态值,包括服务器的CPU使用率,内存使用,虚拟内存交换情况,IO读写情况.首先我们查看下帮助.如下图所 ...

  7. Vim 使用 DrawIt 画图

    简介 DrawIt 插件用来在 Vim 中进行简单的画图功能.可以方便地移动光标并画出横线.竖线.斜线.箭头和交叉字符,也带有实用的画图功能,轻松画带箭头的线.矩形及椭圆. 官方主页:https:// ...

  8. [Swoole] 在Ubuntu下安装、快速开始

    本文主要讲述在 Ubuntu 下编译安装 Swoole,并根据官方文档给出的demo进行了测试和搬运,包括:TCP服务器.UDP服务器.HTTP服务器.WebSocket服务器.异步客户端.定时器和协 ...

  9. Ubuntu部署Tomcat Web服务

    在Ubuntu平台中安装TomCat 本文将为大家介绍TomCat在Ubuntu平台中如何进行部署使用,带你快速入门使用TomCat TomCat简介 Tomcat是Apache 软件基金会(Apac ...

  10. PHP array_udiff_uassoc

    1.函数的参数:返回数组的差集.用定义的函数比较键值和值. 2.函数的参数: @params array $array @params array $array1 ... @params callab ...