当前位置:开发工具->.NET ->自已动手做高性能消息队列--C#实现

原创版权标志自已动手做高性能消息队列--C#实现

作者:阿郎  发表时间:2018/5/16 8:39:20  阅读:
[摘要] 消息队列是分布式高并发面目中必不可少的一部分,随着互联网、云计算、大数据的使用,消息队列的应用越来越多,消息队列在系统的可伸缩性、稳定性、提升吞吐量等方面有着显著的作用
广告招租:800元/月,QQ:1162839541

     本人觉得码农的技术提升应该是从how to do到why do,而项目或产品都是从why do到how to do,按题来,所以呢下面先从大的方面介绍一下消息队列。

            消息队列是分布式高并发面目中必不可少的一部分,随着互联网、云计算、大数据的使用,消息队列的应用越来越多,消息队列在系统的可伸缩性、稳定性、提升吞吐量等方面有着显著的作用;它主要的作用一般如下:

    

           1.通过异步处理提高系统性能

    

    如上图,在不使用消息队列服务器的时候,用户的请求数据直接写入数据库,在高并发的情况下数据库压力剧增,使得响应速度变慢。但是在使用消息队列之后,用户的请求数据发送给消息队列之后立即 返回,再由消息队列的消费者进程从消息队列中获取数据,异步写入数据库。由于消息队列服务器处理速度快于数据库(消息队列也比数据库有更好的伸缩性),因此响应速度得到大幅改善。

            通过以上分析我们可以得出消息队列具有很好的削峰作用的功能——即通过异步处理,将短时间高并发产生的事务消息存储在消息队列中,从而削平高峰期的并发事务。 举例:在电子商务一些秒杀、促销活动中,合理使用消息队列可以有效抵御促销活动刚开始大量订单涌入对系统的冲击。如下图所示:

    

    因为用户请求数据写入消息队列之后就立即返回给用户了,但是请求数据在后续的业务校验、写数据库等操作中可能失败。因此使用消息队列进行异步处理之后,需要适当修改业务流程进行配合,比如用户在提交订单之后,订单数据写入消息队列,不能立即返回用户订单提交成功,需要在消息队列的订单消费者进程真正处理完该订单之后,甚至出库后,再通过电子邮件或短信通知用户订单成功,以免交易纠纷。这就类似我们平时手机订火车票和电影票。

           2.降低系统耦合性

            我们知道模块分布式部署以后聚合方式通常有两种:1.分布式消息队列和2.分布式服务。先来简单说一下分布式服务目前使用比较多的用来构建SOA(Service Oriented Architecture面向服务体系结构)分布式服务框架是阿里巴巴开源的Dubbo.如果想深入了解Dubbo的可以看我写的关于Dubbo的这一篇文章:《高性能优秀的服务框架-dubbo介绍》我们知道如果模块之间不存在直接调用,那么新增模块或者修改模块就对其他模块影响较小,这样系统的可扩展性无疑更好一些。

            我们最常见的事件驱动架构类似生产者消费者模式,在大型网站中通常用利用消息队列实现事件驱动结构。如下图所示:

    

    

    消息队列使利用发布-订阅模式工作,消息发送者(生产者)发布消息,一个或多个消息接受者(消费者)订阅消息。 从上图可以看到消息发送者(生产者)和消息接受者(消费者)之间没有直接耦合,消息发送者将消息发送至分布式消息队列即结束对消息的处理,消息接受者从分布式消息队列获取该消息后进行后续处理,并不需要知道该消息从何而来。对新增业务,只要对该类消息感兴趣,即可订阅该消息,对原有系统和业务没有任何影响,从而实现网站业务的可扩展性设计

            消息接受者对消息进行过滤、处理、包装后,构造成一个新的消息类型,将消息继续发送出去,等待其他消息接受者订阅该消息。因此基于事件(消息对象)驱动的业务架构可以是一系列流程。

            另外为了避免消息队列服务器宕机造成消息丢失,会将成功发送到消息队列的消息存储在消息生产者服务器上,等消息真正被消费者服务器处理后才删除消息。在消息队列服务器宕机后,生产者服务器会选择分布式消息队列服务器集群中的其他服务器发布消息。

            前面说了这么多消息队列的重要性、使用场景、工作模式,有很多人就可能会说了,现有的ActiveMQ、RabbitMQ、Kafka、RocketMQ等多了去了,那在项目架构的时候选一个用上去就不行了,完全没有必要重复造轮子啊!本人认为对于重复造轮子的事情和其它任何事情都是一样的——任何事情没有绝对的好处或者坏处,比如是刚入门的码农、又或者很急的项目,完全可以选用现有一种通用的、成熟的产品,没必要去从零开始做;实际上没有任何一个优秀的产品全部使用三方的产品来组装完成的,任何一个好一点的项目发展到一定的时候都不约而同的进行底层开发。原因很简单:第一个任何通用型的产品总用功能覆盖不到的场景;第二个任何通用型的产品为了实现通用必将做了一些性能或架构的牺牲;现在道理都讲完了,开始动手了(都听你逼半天,能动手就尽量少逼逼!)。

     概述

    动手前先构思一下,本人需要一个简单的、可发布订阅的、高吞吐量的消息队列,并将之简单大的方面分成QServer、QClient;QServer主要有Exchange、Binding、MessageQueue构成;QClient和QServer共用一套相同的传输编解码器QCoder ,主要实现Publish、Subscribe、Unsubcribe、Closes等功能;先想这么多,开干!

    源代码请看:

    https://github.com/yswenli/SAEA

    原文:https://www.cnblogs.com/yswenli/p/9029587.html

    

    

    

文章来源:C++技术网

原文地址:https://www.cnblogs.com/yswenli/p/9029587.html

返回顶部

在线提问
问题标题:
问题描述:(简陋的描述会导致问题被最后回答、没有针对性回答甚至无法解答。请确保问题描述的足够清楚。)