亿级流量系统架构之如何在上万并发场景下设计可扩展架构(下)?【石杉的架构笔记】

欢迎关注我的公众号:石杉的架构笔记(ID:shishan100)
面试

周一至周五早8点半!精品技术文章准时送上!算法

1、前情提示


上一篇文章亿级流量系统架构之如何在上万并发场景下设计可扩展架构(中)?分析了一下如何利用消息中间件对系统进行解耦处理。数据库

同时,咱们也提到了使用消息中间件还有利于一份数据被多个系统同时订阅,供多个系统来使用于不一样的目的。缓存

目前的一个架构以下图所示。性能优化


在这个图里,咱们能够清晰的看到,实时计算平台发布的一份数据到消息中间件里,接着,会进行以下步骤:bash

  1. 数据查询平台,会订阅这份数据,并落入本身本地的数据库集群和缓存集群里,接着对外提供数据查询的服务
  2. 数据质量监控系统,会对计算结果按照必定的业务规则进行监控,若是发现有数据计算错误,则会立马进行报警
  3. 数据链路追踪系统,会采集计算结果做为一个链路节点,同时对一条数据的整个完整计算链路都进行采集并组装出来一系列的数据计算链路落地存储,最后若是某个数据计算错误了,就能够立马经过计算链路进行回溯排查问题


所以上述场景中,使用消息中间件一来能够解耦,二来还能够实现消息“Pub/Sub”模型,实现消息的发布与订阅。架构

这篇文章,我们就来看看,假如说基于RabbitMQ做为消息中间件,如何实现一份数据被多个系统同时订阅的“Pub/Sub”模型。并发


2、基于消息中间件的队列消费模型

上面那个图,其实就是采用的RabbitMQ最基本的队列消费模型的支持。
分布式

也就是说,你能够理解为RabbitMQ内部有一个队列,生产者不断的发送数据到队列里,消息按照前后顺序进入队列中排队。微服务

接着,假设队列里有4条数据,而后咱们有2个消费者一块儿消费这个队列的数据。

此时每一个消费者会均匀的被分配到2条数据,也就是说4条数据会均匀的分配给各个消费者,每一个消费者只不过是处理一部分数据罢了,这个就是典型的队列消费模型。

若是有同窗对这块基于RabbitMQ如何实现有点不太清楚的话,能够参考以前的一些文章:


以前这几篇文章,基本给出了上述那个最基本的队列消费模型的RabbitMQ代码实现,以及如何保证消费者宕机时数据不丢失,如何让RabbitMQ集群对queue和message都进行持久化。基本上总体代码实现都比较完整,你们能够去参考一下。


3、基于消息中间件的“Pub/Sub”模型


可是消息中间件还能够实现一种“Pub/Sub”模型,也就是“发布/订阅”模型,Pub就是Publish,Sub就是Subscribe。

这种模型是能够支持多个系统同时消费一份数据的。也就是说,你发布出去的每条数据,都会广播给每一个系统。

给你们来一张图,一块儿来感觉一下。

如上图所示。也就是说,咱们想要实现的上图的效果,实时计算平台发布一系列的数据到消息中间件里。

而后数据查询平台、数据质量监控系统、数据链路追踪系统,都会订阅数据,都会消费到同一份完整的数据,每一个系统均可以根据本身的须要使用数据。

这,就是所谓的“Pub/Sub”模型,一个系统发布一份数据出去,多个系统订阅和消费到如出一辙的一份数据。

那若是要实现上述的效果,基于RabbitMQ应该怎么来处理呢?


4、RabbitMQ中的exchange究竟是个什么东西?


实际上来讲,在RabbitMQ里面是不容许生产者直接投递消息到某个queue(队列)里的,而是只能让生产者投递消息给RabbitMQ内部的一个特殊组件,叫作“exchange”。

关于这个exchange,大概你能够把这个组件理解为一种消息路由的组件。

也就是说,实时计算平台发送出去的message到RabbitMQ中都是由一个exchange来接收的。

而后这个exchange会根据必定的规则决定要将这个message路由转发到哪一个queue里去,这个实际上就是RabbitMQ中的一个核心的消息模型。

你们看下面的图,一块儿来理解一下。


5、默认的exchange


在以前的文章里,咱们投递消息到RabbitMQ的时候,也没有用什么exchange,可是为何就仍是把消息投递到了queue里去呢?

那是由于咱们用了默认的exchange,他会直接把消息路由到你指定的那个queue里去,因此若是简单用队列消费模型,不就省去了exchange的概念了吗。


上面这段就是以前咱们给你们展现的,让消息持久化的一种投递消息的方式。

你们注意里面的第一个参数,是一个空的字符串,这个空字符串的意思,就是说投递消息到默认的exchange里去,而后他就会路由消息到咱们指定的queue里去。


6、将消息投递到fanout exchange


在RabbitMQ里,exchange这种组件有不少种类型,好比说:direct、topic、headers以及fanout。这里我们就来看看最后一种,fanout这种类型的exchange组件。

这种exchange组件其实很是的简单,你能够建立一个fanout类型的exchange,而后给这个exchange绑定多个queue。

接着只要你投递一条消息到这个exchange,他就会把消息路由给他绑定的全部queue。

使用下面的代码就能够建立一个exchange,好比说在实时计算平台(生产者)的代码里,能够加入下面的一段,建立一个fanout类型的exchange。第一个参数咱们叫作“rt_compute_data”,这个就是exchange的名字,rt就是“RealTime”的缩写,意思就是实时计算系统的计算结果数据。

第二个参数就是定义了这个exchange的类型是“fanout”。

channel.exchangeDeclare(
            "rt_compute_data", 
            "fanout");
复制代码

接着咱们就采用下面的代码来投递消息到咱们建立好的exchange组件里去:

你们会注意到,此时消息就是投递到指定的exchange里去了,可是路由到哪一个queue里去呢?此时咱们暂时还没肯定,要让消费者本身来把本身的queue绑定到这个exchange上去才能够。


7、绑定本身的队列到exchange上去消费


咱们对消费者的代码也进行修改,以前咱们在这里关闭了autoAck机制,而后每次都是本身手动ack。


上面的代码里,每一个消费者系统,都会有一些不同,就是每一个消费者都须要定义本身的队列,而后绑定到exchange上去。好比:

  • 数据查询平台的队列是“rt_compute_data_query
  • 数据质量监控平台的队列是“rt_compute_data_monitor
  • 数据链路追踪系统的队列是“rt_compute_data_link


这样,每一个订阅这份数据的系统其实都有一个属于本身的队列,而后队列里被会被exchange路由进去实时计算平台生产的全部数据。

并且由于是多个队列的模式,每一个系统均可以部署消费者集群来进行数据的消费和处理,很是的方便。


8、总体架构图


最后,给你们来一张大图,咱们再跟着图,来捋一捋整个流程。

如上图所示,首先,实时计算平台会投递消息到“rt_compute_data”这个“exchange”里去,可是他没指定这个exchange要路由消息到哪一个队列,由于这个他自己是不知道的。

接着数据查询平台、数据质量监控系统、数据链路追踪系统,就能够声明本身的队列,都绑定到exchange上去。

由于queue和exchange的绑定,在这里是要由订阅数据的平台本身指定的。并且由于这个exchange是fanout类型的,他只要接收到了数据,就会路由数据到全部绑定到他的队列里去,这样每一个队列里都有一样的一份数据,供对应的平台来消费。

并且针对每一个平台本身的队列,本身还能够部署消费服务集群来消费本身的一个队列,本身的队列里的数据仍是会均匀分发给各个消费服务实例来处理,每一个消费服务实例会获取到一部分的数据。

你们思考一下,这样是否是就实现了不一样的系统订阅一份数据的“Pub/Sub”的模型?

固然,其实RabbitMQ还支持各类不一样类型的exchange,能够实现各类复杂的功能。

后续咱们将会给你们经过实际的线上系统架构案例,来阐述消息中间件技术的各类用法。

END


若有收获,请帮忙转发,您的鼓励是做者最大的动力,谢谢!


一大波微服务、分布式、高并发、高可用的原创系列文章正在路上

欢迎扫描下方二维码,持续关注:


石杉的架构笔记(id:shishan100)

十余年BAT架构经验倾囊相授


推荐阅读:

一、拜托!面试请不要再问我Spring Cloud底层原理

二、【双11狂欢的背后】微服务注册中心如何承载大型系统的千万级访问?

三、【性能优化之道】每秒上万并发下的Spring Cloud参数优化实战

四、微服务架构如何保障双11狂欢下的99.99%高可用

五、兄弟,用大白话告诉你小白都能听懂的Hadoop架构原理

六、大规模集群下Hadoop NameNode如何承载每秒上千次的高并发访问

七、【性能优化的秘密】Hadoop如何将TB级大文件的上传性能优化上百倍

八、拜托,面试请不要再问我TCC分布式事务的实现原理坑爹呀!

九、【坑爹呀!】最终一致性分布式事务如何保障实际生产中99.99%高可用?

十、拜托,面试请不要再问我Redis分布式锁的实现原理!

十一、【眼前一亮!】看Hadoop底层算法如何优雅的将大规模集群性能提高10倍以上?

十二、亿级流量系统架构之如何支撑百亿级数据的存储与计算

1三、亿级流量系统架构之如何设计高容错分布式计算系统

1四、亿级流量系统架构之如何设计承载百亿流量的高性能架构

1五、亿级流量系统架构之如何设计每秒十万查询的高并发架构

1六、亿级流量系统架构之如何设计全链路99.99%高可用架构

1七、七张图完全讲清楚ZooKeeper分布式锁的实现原理

1八、大白话聊聊Java并发面试问题之volatile究竟是什么?

1九、大白话聊聊Java并发面试问题之Java 8如何优化CAS性能?

20、大白话聊聊Java并发面试问题之谈谈你对AQS的理解?

2一、大白话聊聊Java并发面试问题之公平锁与非公平锁是啥?

2二、大白话聊聊Java并发面试问题之微服务注册中心的读写锁优化

2三、互联网公司的面试官是如何360°无死角考察候选人的?(上篇)

2四、互联网公司面试官是如何360°无死角考察候选人的?(下篇)

2五、Java进阶面试系列之一:哥们,大家的系统架构中为何要引入消息中间件?

2六、【Java进阶面试系列之二】:哥们,那你说说系统架构引入消息中间件有什么缺点?

2七、【行走的Offer收割机】记一位朋友斩获BAT技术专家Offer的面试经历

2八、【Java进阶面试系列之三】哥们,消息中间件在大家项目里是如何落地的?

2九、【Java进阶面试系列之四】扎心!线上服务宕机时,如何保证数据100%不丢失?

30、一次JVM FullGC的背后,竟隐藏着惊心动魄的线上生产事故!

3一、【高并发优化实践】10倍请求压力来袭,你的系统会被击垮吗?

3二、【Java进阶面试系列之五】消息中间件集群崩溃,如何保证百万生产数据不丢失?

3三、亿级流量系统架构之如何在上万并发场景下设计可扩展架构(上)?

3四、亿级流量系统架构之如何在上万并发场景下设计可扩展架构(中)?



做者:石杉的架构笔记 连接:https://juejin.im/post/5c23901a51882565986a1909 来源:掘金 著做权归做者全部。商业转载请联系做者得到受权,非商业转载请注明出处。
相关文章
相关标签/搜索