消息中间件利用高效可靠的消息传递机制进行平台无关的数据交流,并基于数据通信来进行分布式系统的集成。通过提供消息传递和消息排队模型,它可以在分布式环境下扩展进程间的通信。对于消息中间件,常见的角色大致也就有Producer(生产者)、Consumer(消费者)
常见的消息中间件产品:
(1)ActiveMQ
ActiveMQ是Apache出品,最流行的,能力强劲的开源消息总线。ActiveMQ是一个完全支持JMS1.1和J2EE 1.4规范的JMS Provider实现。
(2)RabbitMQ
AMQP协议的领导实现,支持多种场景。淘宝的MySQL集群内部有使用它进行通讯,OpenStack开源云平台的通信组件,最先在金融行业得到运用。
(3)ZeroMQ
史上最快的消息队列系统
(4)Kafka
Apache下的一个子项目。特点:高吞吐,在一台普通的服务器上既可以达到10W/s的吞吐速率;完全的分布式系统。适合处理海量数据。
消息中间件一般使用场景有3个:
1.解耦
2.流量消锋
3.异步处理
(*)消息通讯
当一个模块的功能实现要涉及到调用其它多个service模块的方法时,模块间的耦合性较高。
拿支付订单流程举例,在没有中间件的情况下,流程大致如下:
用户支付订单,更新订单状态
调用库存服务,完成响应功能
调用积分服务,完成响应功能
调用短信服务,发送短信通知
这个过程是顺序执行的,如果库存和积分或者短信服务没有及时响应,或者短信服务处理堵塞,客户端用户收到响应的时间将会延长,体验变差。
其实我们知道对于订单流程,只有订单处理才是核心服务,其他依赖系统不是那么重要,可以通知到即可。所以可以使用消息中间件,我们在处理完毕订单之后放入中间件立刻返回,然后后续服务从中间件中拿到数据进行后续的处理。
在不使用消息队列的情况下,用户的请求数据直接写入数据库,在高并发的情况下,会对数据库造成巨大的压力,同时也使得系统响应延迟加剧。
在使用队列后,用户的请求发给队列后立即返回,
例1: 当然不能直接给用户提示订单提交成功,京东上提示:您“您提交了订单,请等待系统确认”,
再由消息队列的消费者进程从消息队列中获取数据,异步写入数据库。
例2:秒杀或团抢活动,一般会因为流量过大,导致流量暴增.一般需要在应用前端加入消息队列.在队列中实现”排队”功能:
场景说明:用户注册后,需要发注册邮件和注册短信。
传统的做法有两种: 1.串行的方式,2.并行方式。
1.串行的方式
将注册信息写入数据库成功后,发送注册邮件,再发送注册短信。以上三个任务全部完成后,返回给客户端
2.并行方式
将注册信息写入数据库成功后,发送注册邮件的同时,发送注册短信。以上三个任务完成后,返回给客户端。与串行的差别是,并行的方式可以提高处理的时间。
假设三个业务节点每个使用50毫秒钟,不考虑网络等其他开销,则串行方式的时间是150毫秒,并行的时间可能是100毫秒。
因为CPU在单位时间内处理的请求数是一定的,假设CPU1秒内吞吐量是100次。
则串行方式1秒内CPU可处理的请求量是7次(1000/150)。并行方式处理的请求量是10次(1000/100)。
用户的响应时间相当于是注册信息写入数据库的时间,也就是50毫秒。注册邮件,发送短信写入消息队列后,直接返回,因此写入消息队列的速度很快,基本可以忽略,因此用户的响应时间可能是50毫秒。所以基于此架构改变后,系统的吞吐量提高到每秒20 QPS。比串行提高了3倍,比并行提高了两倍。
消息通讯是指,消息队列一般都内置了高效的通信机制,因此也可以用在纯的消息通讯。比如实现点对点消息队列,或者聊天室等。
下载好apache-activemq-5.13.0-bin.tar.gz安装包,拷贝到Linux下
执行以下代码
mkdir /activemq
tar -zxvf apache-activemq-5.13.0-bin.tar.gz -C /activemq/
cd /activemq/apache-activemq-5.13.0/bin/linux-x86-64
验证
在非虚拟机浏览器输入虚拟机ip, 端口号8161
但在spring配置文件中消息发送的的端口号为61616
列表各列信息含义如下:
Number Of Pending Messages :等待消费的消息 这个是当前未出队列的数量。
Number Of Consumers :消费者 这个是消费者端的消费者数量
Messages Enqueued :进入队列的消息 进入队列的总数量,包括出队列的。
Messages Dequeued :出了队列的消息 可以理解为是消费这消费掉的数量。
JMS(Java Messaging Service)是Java平台上有关面向消息中间件的技术规范,它便于消息系统中的Java应用程序进行消息交换,并且通过提供标准的产生、发送、接收消息的接口简化企业应用的开发。
JMS本身只定义了一系列的接口规范,是一种与厂商无关的 API,用来访问消息收发系统。它类似于 JDBC(java Database Connectivity):这里,JDBC 是可以用来访问许多不同关系数据库的 API,而 JMS 则提供同样与厂商无关的访问方法,以访问消息收发服务。许多厂商目前都支持 JMS,包括 IBM 的 MQSeries、BEA的 Weblogic JMS service和 Progress 的 SonicMQ,这只是几个例子。 JMS 使您能够通过消息收发服务(有时称为消息中介程序或路由器)从一个 JMS 客户机向另一个 JML 客户机发送消息。消息是 JMS 中的一种类型对象,由两部分组成:报头和消息主体。报头由路由信息以及有关该消息的元数据组成。消息主体则携带着应用程序的数据或有效负载。
JMS定义了五种不同的消息正文格式,以及调用的消息类型,允许你发送并接收以一
些不同形式的数据,提供现有消息格式的一些级别的兼容性。
· TextMessage–一个字符串对象
· MapMessage–一套名称-值对
· ObjectMessage–一个序列化的 Java 对象
· BytesMessage–一个字节的数据流
·StreamMessage – Java原始值的数据流
对于消息的传递有两种类型:
一种是点对点的,即一个生产者和一个消费者一一对应;
另一种是发布/订阅模式,即一个生产者产生消息并进行发送后,可以由多个消费者进行接收。