消息队列

消息中间件是一种由消息传送机制或消息队列模式组成的中间件技术,利用高效可靠的消息传递机制进行平台无关的数据交流,并基于数据通信来进行分布式系统的集成。目前业界有很多的MQ产品,像RabbitMQ、ActiveMQ、ZeroMQ、kafka等都是极好的消息中间件。

消息队列解决的是将突发大量请求转换为后端能承受的队列请求,比如服务器一秒能处理100个订单,但秒杀活动1秒进来1000个订单,持续10秒,在后端能力无法增加的情况下,你可以用消息队列将总共10000个请求压在队列里,后台consumer按原有能力处理,100秒后处理完所有请求(而不是直接宕机丢失订单数据)

所以说首先别自己实现消息队列(在你用过各种消息队列,还看过一两份源码之前),其次没有合适的需求别用消息队列。队列是一种数据结构,内部是用数组或链表实现的,队列的特点是只能队头放入,队尾取出,即先入先出,具体应用看下生产者消费者。
通俗的说,就是一个容器,你把消息丢进去,不需要立即处理。然后有个程序去从你的容器里面把消息一条条读出来处理。

消息队列,可以是activeMQ,kafka之类的,也可以是数据库的一张任务表。个人觉得消息队列,主要有两个作用:
1 降低耦合
2 消息可以暂时存在在消息队列中,等待消息接收者根据自身的负载处理能力控制处理消息的处理速度,减小在大并发访问时候的压力。

 



中间件(Middleware)

根据维基百科的说法

    中间件(英语:Middleware)提供系统软件和应用软件之间连接的软件,以便于软件各部件之间的沟通,特别是应用软件对于系统软件的集中的逻辑,在现代信息技术应用框架如Web服务、面向服务的体系结构等中应用比较广泛。如数据库、Apache的Tomcat。

    中间件技术创建在对应用软件部分常用功能的抽象上,将常用且重要的过程调用、分布式组件、消息队列、事务、安全、连结器、商业流程、网络并发、HTTP服务器、Web Service等功能集于一身或者分别在不同品牌的不同产品中分别完成

    一般认为在商业中间件及信息化市场主要存在微软阵营、Java阵营、开源阵营。阵营的区分主要体现在对下层操作系统的选择以及对上层组件标准的制订

我此前对中间件的理解是 对应用软件部分常用功能的抽象 ,它运行在操作系统之上,对外提供一种常用而抽象的服务,典型代表有数据库、缓存、消息队列

 



消息队列(Message queue)

我们同样引用维基百科

消息队列(英语:Message queue)是一种进程间通信或同一进程的不同线程间的通信方式.消息队列提供了异步的通信协议,每一个贮列中的纪录包含详细说明的数据,包含发生的时间,输入设备的种类,以及特定的输入参数,也就是说:消息的发送者和接收者不需要同时与消息队列互交。消息会保存在队列中,直到接收者取回它。

有了消息队列,事件可以异步地发生



实现

1. 消息队列常常保存在链表结构中。拥有权限的进程可以向消息队列中写入或读取消息



优缺点

1. 很多情况下我们需要异步的通信协议。比如,一个进程通知另一个进程发生了一个事件,但不需要等待回应。但消息队列的异步特点,也造成了一个缺点,就是接收者必须轮询消息队列,才能收到最近的消息。

2. 和信号相比,消息队列能够传递更多的信息。与管道相比,消息队列提供了有格式的数据,这可以减少开发人员的工作量

 



ZeroMQ ( ØMQ )

号称最快的消息队列系统,尤其针对大吞吐量的需求场景。是一个非常轻量级的消息系统,专门为高吞吐量/低延迟的场景开发,在金融界的应用中经常可以发现它。与RabbitMQ相比,ZeroMQ支持许多高级消息场景,但是你必须实现ZeroMQ框架中的各个块(比如Socket或Device等)。

它能够实现RabbitMQ不擅长的高级/复杂的队列,但是开发人员需要自己组合多种技术框架,技术上的复杂度是对这MQ能够应用成功的挑战。ZeroMQ具有一个独特的非中间件的模式,你不需要安装和运行一个消息服务器或中间件,因为你的应用程序将扮演了这个服务角色。你只需要简单的引用ZeroMQ程序库,可以使用NuGet安装,然后你就可以愉快的在应用程序之间发送消息了。但是ZeroMQ仅提供非持久性的队列,也就是说如果down机,数据将会丢失。

ZeroMQ没有中间件架构,不需要任何服务进程和运行。事实上,你的应用程序端点扮演了这个服务角色。这让部署起来非常简单,但担心的是,你没有地方可以观察它是否有问题出现。就目前了解到的,ZeroMQ仅提供非持久性的队列。你可以在需要的地方实现自己的审计和数据恢复功能。

 



RabbitMQ

RabbitMQ是使用Erlang编写的一个开源的消息队列,本身支持很多的协议:AMQP,XMPP, SMTP, STOMP,也正是如此,使的它变的非常重量级,更适合于企业级的开发。是AMQP协议领先的一个实现,它实现了代理(Broker)架构,意味着消息在发送到客户端之前可以在中央节点上排队。对路由(Routing),负载均衡(Load balance)或者数据持久化都有很好的支持。此特性使得RabbitMQ易于使用和部署,适宜于很多场景如路由、负载均衡或消息持久化等,用消息队列只需几行代码即可搞定。但是,这使得它的可扩展性差,速度较慢,因为中央节点增加了延迟,消息封装后也比较大。如需配置RabbitMQ则需要在目标机器上安装Erlang环境。

 

RabbitMQ是实现AMQP(高级消息队列协议)的消息中间件的一种

ZeroMQ 和 RabbitMQ 都支持一个开源的消息协议: AMQP 。AMQP的一个优点是它是一个灵活和开放的协议.不过ZeroMQ不支持消息持久化和崩溃恢复, RabbitMQ支持持久化 。如果RabbitMQ死掉了,消息并不会丢失,当队列重启,一切都会回来。

 



AMQP 0.9.1 模型解析

  • 消息代理(message brokers)从发布者(publishers)亦称生产者(producers)那儿接收消息,并根据既定的路由规则把接收到的消息发送给处理消息的消费者(consumers)。由于AMQP是一个网络协议,所以这个过程中的发布者,消费者,消息代理 可以存在于不同的设备上。
  • AMQP 0-9-1 模型简介:消息(message)被发布者(publisher)发送给交换机(exchange),交换机常常被比喻成邮局或者邮箱。然后交换机将收到的消息根据路由规则分发给绑定的队列(queue)。最后AMQP代理会将消息投递给订阅了此队列的消费者,或者消费者按照需求自行获取。
  • 当“消息确认”被启用的时候,消息代理不会完全将消息从队列中删除,直到它收到来自消费者的确认回执(acknowledgement)
  • 消费者
  • 将消息投递给应用 ("push API")
  • 应用根据需要主动获取消息 ("pull API")
  • AMQP连接通常是长连接

 



消息队列,任务队列和消息中间件的区别

消息中间件是消息队列的一种封装实现,提供了应用程序和API!

消息队列=任务队列更像是一种解决方案,一般都是异步,发布和订阅模型,订阅还可以分成是pull和push!

具体场景为:不用实时响应,任务处理时间较长的地方,比如视频格式转换服务,你视频上传成功就可以提示你可以离开本页面,随时可以回来查看任务处理进度,实际就是一个异步任务处理的场景,有N个订阅者收到消息以后在执行处理任务

 

消息队列和任务队列其实有很大的相似性,消息队列更着重的是消息,也就是告知,而任务队列着重与任务,也就是执行。所以说一般是外部发送消息通过消息队列所在的消息处理服务器,消息处理服务器再转发给相应任务所在的任务服务器并在任务队列中排队等待执行。消息中间件就是用在消息队列服务器中用于过滤、区分和根据规则进行转发的程序,在分布式系统中更为常见。