什么是消息中间件,例如IBM MQ,能否用通俗的语言帮忙解释一下。。

2024-05-16 03:16

1. 什么是消息中间件,例如IBM MQ,能否用通俗的语言帮忙解释一下。。

先给你讲一下什么叫中间件再举个例子
1.百度百科中中间件含义的链接 我就不粘贴了
http://baike.baidu.com/view/23710.htm
 
2.举个简单的例子,
有这样一个需求,sap有一组hr的相关信息,比如姓名,工号等等要求显示到一个portal上面,供user使用 查看信息。
 
数据怎么从sap到portal呢,可能的一种情况是,使用一个中间件,通过rfc或者idoc把相关信息从sap取出来,整合以后在通过jdbc插入到 portal的后台db里去。
 
这就是一个中间件参与数据整合 协同的简单过程。这样一个过程是由中间件完成的。所以简单的说,中间件就是在异构系统间起数据传输,整合作用的一个软件。
 
3.还是以刚才的例子为例,看看什么是消息中间件
如果是消息中间件,就要把刚才例子中的hr数据看成一个消息,具体的数据结构可以根据需要和开发平台自己来定义。
把从rfc出来的数据,先形成一个消息,然后发布到一个消息队列里面,然后再通过一定规则去取这个消息解析再使用jdbc插入数据库
这个过程可以是一对一,以可以是多对多。
也许上面这个简单的例子并不能体现消息中间件的优点,但是在复杂的网络环境下,例如多个通讯方式,多个业务系统之间进行消息交互,他的优点是显而易见的。

什么是消息中间件,例如IBM MQ,能否用通俗的语言帮忙解释一下。。

2. 消息中间件(MQ)的技术选型(Kafka、RabbitMQ、RocketMQ)

  优势:    在性能方面kafka可以说是业界非常优秀的一款中间件,在常规的机器配置下,一台机器可以达到每秒几十万的QPS。并且Kafka的性能也非常高,基本上发给kafka的消息都是毫米级别的,可用性也特别高,kafka是支持集群部署的,并且其中部分机器宕机,还是可以运行的。    劣势:    kafka有可能会丢失数据,因为kafka收到消息之后,会写一个磁盘缓冲区里,并没有直接落地到物理磁盘上去,所以机器故障之后,可能会导致磁盘缓冲区的数据丢失。另外一个缺点就是,kafka的功能比较单一,主要是支持发送消息给它,然后从里面消费消息,其它就没有什么额外的高级功能了,所以基于kafka有限的功能,可能适用的场景并不是很多。    综上所述: 一般公司会利用kafka收集一些日志之类的消息,因为日志一般量特别大,即使丢几条数据也没事,并且要求吞吐量也高,一般就是收发消息,不需要太多的功能,所以kafka非常适合这个场景。
    优势:    在RocketMQ没有出现之前,好多公司都从ActiveMQ切换到了RabbitMQ,它的优势在于可以保证数据不丢失,也能保证高可用性,即使集群部署部分机器宕机也能运行,然后支持部分高级功能,比如死信队列,消息重试之类的。    缺点:    RabbitMQ的吞吐量比较低,一般就是几万的级别,如果遇到特别高的并发时,支撑起来有点困难。并且进行集群的扩展也是比较麻烦的。还有就是开发语言用的是erlang,国内使用此语言的很少,所以对其深入的研究也是比较麻烦的。
    优点:    RocketMQ几乎同时解决了Kafka和RabbitMQ的缺陷。它的吞吐量也非常高,单机可以达到10万的QPS以上,而且可以保证高可用性,并且可以通过配置达到数据保证不会丢失,可以部署大规模的集群,还支持各种高级功能,比如说延迟消息、事务消息、消息回溯、死信队列、消息积压等。而且RocketMQ是利用java开发的,符合国内的大多数公司的技术栈,很容易进行阅读源码和修改其内容。    缺点:    RocketMQ的官方文档相比较于kafka和RabbitMQ来说的话会相对简单一些,没有人家kafka和RabbitMQ的文档写的详细。

3. 厉害!一文了解消息中间件-RabbitMQ

  RabbitMQ是2007年发布,是一个在AMQP(高级消息队列协议)基础上完成的,简称MQ全称为Message Queue, 消息队列(MQ)是一种应用程序对应用程序的通信方法,由Erlang(专门针对于大数据高并发的语言)语言开发,可复用的企业消息系统,是当前最主流的消息中间件之一,具有可靠性、灵活的路由、消息集群简单、队列高可用、多种协议的支持、管理界面、跟踪机制以及插件机制。 
         
    1.消息 就是数据,增删改查的数据。例如在员工管理系统中增删改查的数据 
    2.队列 指的是一端进数据一端出数据,例如C#中(Queue数据结构) 
         
    1.消息队列指:一端进消息,一端出消息 
    2.RabbitMQ就是实现了消息队列概念的一个组件,以面向对象的思想去理解,消息队列就是类,而RabbitMQ就是实例,当然不仅仅只有RabbitMQ,例如ActiveMQ,RocketMQ,Kafka,包括Redis也可以实现消息队列。 
         
    1.在常见的单体架构中,主要流程是用户UI操作发起Http请求>服务器处理>然后由服务器直接和数据库交互,最后同步反馈用户结果 
       2.在微服务架构中,UI与微服务通信,主要是通过Http或者gRPC同步通信 
            
    问题分析 
    在上述2种情况下,我们发现在UI请求时都是同步操作 ,第2种架构虽然将整体服务按业务拆分成不同的微服务并且对应各自的数据库,但是在用户与微服务通信时,存在的问题依然没有解决,例如数据库的承载能力只能处理10w个请求,如果遇到高并发情况下,UI发起50w请求,那数据库是远远承载不了的,从而导致如下问题。 
    1.高并发请求导致系统性能下降响应慢,同时数据库承载风险加大 
    2.扩展性不强UI操作的交互对业务的依赖较大,导致用户体验下降 
    3.瞬时流量涌入巨大的话,服务器可能直接挂了 
         
    解决方案 
       RabbitMQ的优势 
    RabbitMQ的不足 
         
    1.ConnectionFactory 为Connection的制造工厂。 
    2.Connection是RabbitMQ的socket链接,它封装了socket协议相关部分逻辑。 
    3.Channel是我们与RabbitMQ打交道的最重要的一个接口,我们大部分的业务操作是在Channel这个接口中完成的,包括定义Queue、定义Exchange、绑定Queue与Exchange、发布消息等。 
    4.Exchange(交换机) 我们通常认为生产者将消息投递到Queue中,实际上实际的情况是,生产者将消息发送到Exchange,由Exchange将消息路由到一个或多个Queue中(或者丢弃),而在RabbitMQ中的Exchange一共有4种策略,分别为:fanout(扇形)、direct(直连)、topic(主题)、headers(头部) 
    1.下载RabbitMQ 
    2.运行环境erlang 
    3.安装完成之后,加载RabbitMQ管理插件 
    4.安装成功访问RabbitMQ管理后台http://localhost:15672 
    1.分别创建考勤服务,请假服务,计算薪酬服务,邮件服务,短信服务消费者角色 
    2.创建员工管理网站用于模拟前端调用,主要充当生产者角色 
    3.在员工管理网站和每一个模拟微服务中通过nuget引入RabbitMQ.Client 
    4.在员工管理网站中创建模拟添加考勤的控制器并加入生产者代码 
    5.在考勤微服务中创建接口,并在接口中加入消费者代码 
         
    fanout类型的Exchange路由规则非常简单,工作方式类似于多播一对多,它会把所有发送到该Exchange的消息路由到所有与它绑定的Queue中。 
        业务实例 
    当我们有员工需要请假,在员工管理系统提交请假,但是由于公司规定普通员工请假,需要发送短信到他的主管领导,针对此业务场景我们需要调用请假服务的同时去发送短信,这时需要两个消费者(请假服务,短信服务)来消费同一条消息,其实本质就是往RabbitMQ写入一个能被多个消费者接收的消息,所以可以使用 扇形交换机,一个生产者,多个消费者. 
    生产者模拟使用调用控制器来实现 
    消费者实现IHostedService 接口创建一个监听主机 
         
    直接交换器,工作方式类似于单播一对一,Exchange会将消息发送完全匹配ROUTING_KEY的Queue,缺陷是无法实现多生产者对一个消费者 
        当我们员工管理系统需要计算薪资并将结果以发送短信的方式告诉员工,这个时候我们就不太适合用“扇形交换机”了,因为换做是你,你也不想你的工资全公司都知道吧?这个时候就需要定制了一对一的场景了,那就在生产消息时使用直连交换机根据routingKey发送指定的消费者. 
    生产者模拟使用调用控制器来实现 
    消费者实现IHostedService 接口创建一个监听主机 
         
    Exchange绑定队列需要制定Key; Key 可以有自己的规则;Key可以有占位符;   或者# ,   匹配一个单词、#匹配多个单词,在Direct基础上加上模糊匹配;多生产者一个消费者,可以多对对,也可以多对1, 真实项目当中,使用主题交换机。可以满足所有场景 
    1.生产者定义Exchange,然后不同的routingKey绑定 
      3.消费者routingKey的模糊匹配,生产者发送消息时routingKey定义以sms.开头, * 号只能匹配的routingKey为一级,例如(sms.A)或(sms.B)的发送的消息,# 能够匹配的routingKey为一级及多级以上 ,例如 (sms.A)或者(sms.A.QWE.IOP) 
    在月底的时候我们需要把员工存在异常考勤信息,薪资结算信息,请假信息分别以邮件的形式发送给我们的员工查阅,我们知道这是一个典型的多个生产者,一个消费者场景,异常考勤信息,薪资结算信息,请假信息分别需要生产消息发送到RabbitMQ,然后供我们员工消费 
    分别模拟3个生产者:异常考勤信息,薪资结算信息,请假信息 
         
    headers类型的Exchange不依赖于routing key与binding key的匹配规则来路由消息,而是根据发送的消息内容中的headers属性进行匹配。  在绑定Queue与Exchange时指定一组键值对以及x-match参数,x-match参数是字符串类型,可以设置为any或者all。如果设置为any,意思就是只要匹配到了headers表中的任何一对键值即可,all则代表需要全部匹配。 
    1.不需要依赖Key 
    2.更多的时候,像这种Key Value 的键值,可能会存储在数据库中,那么我们就可以定义一个动态规则来拼装这个Key value ,从而达到消息灵活转发到不同的队列中去 
    我们根据上面的业务和代码简单实现了由生产者到消费者的一个业务流程,我们可以总结出知道,整个消息的收发过程包含有三个角色,生产者(员工管理网站)、RabbitMQ(Broker)、消费者(微服务),在理想状态下,按照这样实现,整个流程以及系统的稳定性,可能不会发生太大的问题,但是真正在实际应用中我们要去思考可能存在的问题,主要从三个大的方面去分析,然后发散。 
    1.生产端 
    2.存储端 
    3.消费端 
    我们在给RabbitMQ发送消息时,如何去保证消息一定到达呢,我们可以使用RabbitMQ提供了2种生产端的消息确认机制 
    我们生产端给RabbitMQ发送消息成功后,如果RabbitMQ宕机了,会导致RabbitMQ中消息丢失,如何解决消息丢失问题,针对RabbitMQ消息丢失,我们可以在生产者中使用 
    1.持久化消息 
    2.集群 
     当生产者写入消息到RabbitMQ后,消费服务接收消息期间,服务器宕机,导致消息丢失了,这个时候我们就应该使用RabbitMQ的消费端消息确认机制 
    1.自动确认 
    2.手动确认 
    消费者收到消息。消费者发送确认消息给rabbitmq期间。执行业务逻辑失败了,但是消息已经确认被消费了,我们应该在我们的消费者接收消息回调执行业务逻辑后面,执行使用手动确认消息机制,保证消息不被丢失 
   原文链接:https://www.cnblogs.com/yuxl01/p/15978229.html

厉害!一文了解消息中间件-RabbitMQ

4. 消息队列 消息中间件 JMS与AMQP

  中间件 :中间件(Middleware)是处于 平台 (硬件和操作系统)和 应用程序 之间的 通用服务 。也就是说,中间件是提供普遍独立功能需求的模块。中间件屏蔽了底层操作系统的复杂性,使开发人员得以基于一个简单而统一的开发环境,集中进行业务开发,而不必考虑程序在不同系统上的兼容性问题,从而提升开发效率,且减少系统维护的工作量。    消息中间件 :也称消息队列,利用可靠的 消息传递机制 进行系统之间通信,具有接受数据、接受请求、存储数据、发送数据等功能。消息代理(message broker)和目的地(destination)是消息服务中两个重要的概念。当一个消息被发送后,会被交给消息代理,消息代理可以确保消息被发送到指定目的地,同时解放发送者,使其能够继续进行其它业务。消息代理通常有ActiveMQ、RabbitMQ...,目的地通常有队列和主题。
   常见的两个消息规范分别是JMS(Java Message Service)和AMQP(Advanced Message Queuing Protocol, 高级消息队列协议)。JMS是一个基于JVM的消息代理规范,常见实现有ActiveMQ和HornetMQ;AMQP是一个基于应用层标准的统一消息队列协议,是应用层协议的一个开放标准。基于此协议的客户端与消息中间件的消息传递,并不受客户端、中间件和不同开发语言等限制。AMQP兼容JMS,常见实现有RabbitMQ。下表列举了JMS与AMQP的区别: