市面上有好多消息队列,例如:ActiveMQ、RabbitMQ、RocketMQ、kafka等等。可是,我们为什么要使用消息队列,也就是消息队列用在什么场景?简单的讲,有三个主要好的好处:
1,解耦。2,异步。3,消峰。
正因为有这三个好处,所以决定了它的使用场景。
介绍:
一)系统解耦:
假设有这么一个需求,A系统完成某个业务之后,需要向B,C系统发送业务核心数据。传统很简单,A系统直接调用B,C的接口传递数据即可,如图:
可是,现在客户需求又来了,不仅要向B,C系统发送业务核心数据,也要向D,E,F,G...系统发送数据。这回开发人员头就大了,于是,就加班加点在A系统上继续开发调用D,E,F,G...系统的接口。最后效果如图:
这个时候,好不容易开发结束了。B系统突然就跟开发人员说:“我的使命已经结束,你不需要给我发数据”。开发人员就继续在A系统将发送给B的代码给屏蔽了。
从这里我们看出,如果全部采取这种系统耦合的方式,系统耦合度太严重了。因此,我们用消息队列进行改进。
改进:
当A系统完成业务之后,只需要将业务核心数据发送给消息队列。你们哪个系统想要数据的,自己去消息队列中拿,我只负责将数据成功发送给消息队列即可。改进后,效果如图:
二)异步调用
同理,有这么一个业务:A系统调用B系统,B系统又调用C系统,在C中又调用D系统。这些任务都完成,才算是一个完整的业务。但是他们各自调用消耗的时间如图:
整个流程走下来,共花费:500ms + 1000ms + 500ms = 2s
哇,感觉好漫长。光是B调用C就得1000ms。也就是用户需要花费2s来等待结果。
改进:
我们在BC之间加入一个消息队列,D直接就是发送个消息到消息队列里,由系统C消费到消息之后慢慢的异步来执行这个。如图:
这样一来,用户只需要花费:500ms+5ms来等待结果。性能瞬间提升~
三)消峰
我们有这么一个系统,平常每秒能应付几百一千个请求,部署在服务器上是没问题的。但是在高峰期,比如中午1点-2点这段时间呢,每秒达到几千几万请求,我们传统的方法是不是增加硬件机器来应付这些上千上万个请求呢?当然,这种方式也正确,但是每天也就是一个小时左右的高峰期,增加硬件机器来应付请求太浪费成本了。
如果你就部署一台机器,那会导致瞬时高峰时,一下子压垮你的系统,因为绝对无法抗住每秒几千的请求高峰。那么我们就可以使用消息队列来改善这种问题,在机器前加入消息队列,高峰时,每秒几千个请求全部积压到队列中,然后我们的机器,就可以按照每秒钟最多处理1000个请求来消化掉这些请求。
如何选择消息中间件?
但是,市面上常用消息中间件ActiveMQ、RabbitMQ、RocketMQ、kafka,我们如何进行选择呢?下面从网上拷贝出各个消息中间件的优缺点:
性能
ActiveMQ
RabbitMQ
RocketMQ
Kafka
单机吞吐量
万级,比 RocketMQ、Kafka 低一个数量级
同 ActiveMQ
10 万级,支撑高吞吐
10 万级,高吞吐
topic 数量对吞吐量的影响
topic 可以达到几百/几千的级别,吞吐量会有较小幅度的下降
Kafka 尽量保证 topic 数量不要过多,如果要支撑大规模的 topic,需要增加更多的机器资源
时效性
ms 级
微秒级别
ms 级
ms 级
可用性
高
同 ActiveMQ
非常高,分布式架构
非常高,分布式,一个数据多个副本,少数机器宕机,不会丢失数据,不会导致不可用
消息可靠性
有较低的概率丢失数据
基本不丢失
可以做到基本不丢失
同 RocketMQ
功能支持
MQ 领域的功能极其完备
并发能力很强,性能极好,延时很低
MQ 功能较为完善,还是分布式的,扩展性好
功能较为简单,主要支持简单的 MQ 功能,在大数据领域的实时计算以及日志采集被大规模使用
各种对比之后,大家在选择消息中间件时,可以根据自己的业务需求衡量选择:ActiveMQ,但是现在确实大家用的不多了,没经过大规模吞吐量场景的验证,社区也不是很活跃。RabbitMQ,基于 erlang 语言开发,阻止了大量的 Java 工程师去深入研究和掌控它,对公司而言,几乎处于不可控的状态,但是确实人家是开源的,比较稳定的支持,活跃度也高;RocketMQ,确实很不错,毕竟是阿里出品。如果自己公司技术实力有绝对自信的,推荐用RocketMQ,否则用RabbitMQ ,人家有活跃的开源社区。如果是大数据领域的实时计算、日志采集等场景,用 Kafka 是业内标准的,绝对没问题,社区活跃度很高,何况几乎是全世界这个领域的事实性规范
本人水平有限,难免有错误或遗漏之处,望大家指正和谅解,提出宝贵意见,愿与之交流。
欢迎关注公众号: