一,消息队列基本概念

借用百科的一句话:消息队列就是在消息的传输过程中,保存消息的容器。

从图-1和图-2对比,可以很清晰的明白,消息队列服务器,是位于应用服务器和数据库服务器之间的一个服务器。消息队列服务器作为一个缓冲,接收应用服务器发送过来的数据库操作命令,然后按照自己的配置,依次发送给数据库服务器来执行。这种数据库执行的方式,我们称之为异步写入数据库。增加消息队列服务器有以下几点好处:

1,由于消息队列服务器的速度远远高于数据库服务器,所以能够快递处理并返回数据;

2,消息队列服务器具有更好的扩展性;

3,在高并发的情况下,延迟写入数据库,可以有效降低数据库的压力;

凡事都会有利有弊,消息队列也不例外。正所谓知己知彼,百战不怠,我们要想把消息队列用的炉火纯青,消息队列的“弊端”也要铭记于心:

1,由于消息队列是在写入消息队列服务器之后,马上返回给用户,此时数据并没有真正的写入到数据库,后续的数据库操作可能会执行失败,这显然是有问题的。我们一般的做法,是通过业务的手段来解决异步带来的不一致问题。比如我们可以稍微修改一下业务流程,在订单写入消息队列后,不立即返回订单生成成功,而是等待消息队列里的进程真正的执行完以后,再通知用户订单生成成功。

消息队列有特殊的应用场景,而作为我们程序猿或者架构师,就是要从中进行取舍,拿出一套权衡利弊之后的解决方案,解决项目中遇到的问题。

典型应用:活动期间,短时间内生成大批量的订单。如图-3

消息队列的应用场景:邮件服务、短信服务、好友动态推送服务等。我们必须要明白一点:任何需要持久化的产品,磁盘IO都是一个逃不掉的限制。消息队列只是在时间上延长了持久化的时间。

消息队列的常见应用场景:

1,流量控制和业务剥离;
由于磁盘IO的速度与内存的速度差距太大,数据库通常都会成为系统的瓶颈。并且升级硬件成本较高,所以公司通常都会采取软件的方法
来解决这类问题。还是那句话,技术是为业务服务的,没有业务,就没有技术。抢购活动、秒杀活动这一类短时间内生成大批量订单的问
题,我们通常就采用消息队列的方式来处理。
另外,从业务方面来考虑,有些用户不是很关心的业务,可以从主流程中剥离出来。比如订单系统,订单支付成功,我们一般都会发送短
信通知用户支付成功,或者返积分什么的。这个我们在平时的使用中应该也能体会到,发送短信的服务一般都是延迟发送的,少则几十
秒,多者几分钟,甚至几十分钟等等。一方面是用户不是特别关心这些问题,另一方面,短信平台的速度也是很慢的,和磁盘IO一样,都
是系统的主要瓶颈之一。并且短信的发送,受网络影响也较大,经常发生发送失败的情况。使用消息队列,一方面可以把发送短信流程从
主流程中剥离出来,降低系统的复杂性;另一方面,通过轮训消息队列的方式,可以补偿性的多发几次,直到成功为止(也就是我们经常
用到的跑批)。

2,广播(发布/订阅);
随着系统的扩大,系统的复杂性会越来越大,我们都知道,越是复杂的系统,越难维护。君不见,现在有很多老系统,维护的时间居然超
过了开发的时间。本人之前工作的老项目,是运行了五六年的老项目,大部分都是在维护,一个小功能的上线,就有可能让系统出现各种
意想不到的问题,经常通宵上线,苦不堪言。
消息队列对解决这种应用场景,也是一个不错的选择。目前国内的大公司,不管是银行、电信、还是互联网,企业内部的系统都是成百上
千,各个系统之间,通过企业总线关联成一个庞大的系统。各个系统都要调用核心接口,请求核心接口的数据,这种系统,正是通过消息
队列来实现的。企业总线不关心某个系统能否马上执行完成,而是把消息通知发送给某个系统。
消息队列的使用,还可以减少联调和开发的工作量。大公司,上线很频繁,如果每次增加新功能或者修改已有功能,都要进行接口联调的
话,那代价是很大的。

二,消息队列的具体实现(消息队列在项目中的应用)

消息队列的实现方式有很多种,消息队列服务器broker是一个应用比较广泛的系统模型。广播关系的维护,是消息队列服务中的一个重点,一般由于消息队列本身都是集群,所以都维护在公共存储上,比如Zookeeper;

1,借助nosql数据库或者Memcached实现消息队列;

2,HornetQ、Apache 的 ActiveMQ、Beansalkd、RabitMQ、IronMQ、Tibco EMS、IBM的MQSeries等等;

3,另外,还有比较熟悉的Akka、ZeroMQ等;

首先我们来看看:Apache ActiveMQ

Apache ActiveMQ是Apache软件基金会所研发的开放源码消息中间件;由于ActiveMQ是一个纯java的,所以只要操作系统支援Java虚拟机(JVM),ActiveMQ便可运行。

说到这里,我们需要了解一下JMS与ActiveMQ的关系:

1,JMS,即Java Message Service ,也就是大名鼎鼎的java消息服务API,是一个规范;

2,ActiveMQ,是JMS规范的一种实现;

如果需要自己设计消息队列服务器,我们必须要了解RPC协议,下面是百度百科的说明:

远程过程调用协议
        RPC(Remote Procedure Call Protocol)——远程过程调用协议,它是一种通过网络从远程计算机程序上请求服务,而不需要了解底层网络技术的协议。RPC协议假定某些传输协议的存在,如TCP或UDP,为通信程序之间携带信息数据。在OSI网络通信模型中,RPC跨越了传输层和应用层。RPC使得开发包括网络分布式多程序在内的应用程序更加容易。
        RPC采用客户机/服务器模式。请求程序就是一个客户机,而服务提供程序就是一个服务器。首先,客户机调用进程发送一个有进程参数的调用信息到服务进程,然后等待应答信息。在服务器端,进程保持睡眠状态直到调用信息到达为止。当一个调用信息到达,服务器获得进程参数,计算结果,发送答复信息,然后等待下一个调用信息,最后,客户端调用进程接收答复信息,获得进程结果,然后调用执行继续进行。

有多种 RPC模式和执行。最初由 Sun 公司提出。IETF ONC 宪章重新修订了 Sun 版本,使得 ONC RPC 协议成为 IETF 标准协议。现在使用最普遍的模式和执行是开放式软件基础的分布式计算环境(DCE)。

http://blog.csdn.net/reggergdsg/article/details/51711804

应用服务器性能优化 之 消息队列(MQ:Message Queue)的更多相关文章

  1. 消息队列(Message Queue)基本概念(转)

    背景 之前做日志收集模块时,用到flume.另外也有的方案,集成kafaka来提升系统可扩展性,其中涉及到消息队列当时自己并不清楚为什么要使用消息队列.而在我自己提出的原始日志采集方案中不适用消息队列 ...

  2. Java分布式:消息队列(Message Queue)

    Java分布式:消息队列(Message Queue) 引入消息队列 消息,是服务间通信的一种数据单位,消息可以非常简单,例如只包含文本字符串:也可以更复杂,可能包含嵌入对象.队列,是一种常见的数据结 ...

  3. 消息队列(Message Queue)基本概念

    背景 之前做日志收集模块时,用到flume.另外也有的方案,集成kafaka来提升系统可扩展性,其中涉及到消息队列当时自己并不清楚为什么要使用消息队列.而在我自己提出的原始日志采集方案中不适用消息队列 ...

  4. c/c++ linux 进程间通信系列6,使用消息队列(message queue)

    linux 进程间通信系列6,使用消息队列(message queue) 概念:消息排队,先进先出(FIFO),消息一旦出队,就从队列里消失了. 1,创建消息队列(message queue) 2,写 ...

  5. 消息队列(Message Queue)简介及其使用

    消息队列(Message Queue)简介及其使用 摘要:利用 MSMQ(Microsoft Message Queue),应用程序开发人员可以通过发送和接收消息方便地与应用程序进行快速可靠的通信.消 ...

  6. 微软消息队列-MicroSoft Message Queue(MSMQ)队列的C#使用

    目录 定义的接口 接口实现 建立队列工厂 写入队列 获取消息 什么是MSMQ Message Queuing(MSMQ) 是微软开发的消息中间件,可应用于程序内部或程序之间的异步通信.主要的机制是:消 ...

  7. 消息队列(message queue)

    最近纠结于一个问题,就是horizon 在处理前台数据的时候非得等到cinder client将数据全部获取后才开始执行horizon的下一行代码,这给大量数据显示造成了很大的时延,其实对于用户体验来 ...

  8. 消息通讯之关于消息队列MQ必须了解的相关概念

    目录 系统通讯方式有哪些? 消息队列的应用场景 消息队列通讯模型 常见的消息协议 AMQP MQTT ATOMP JMS 小结 系统通讯方式有哪些? RPC调用 RPC 全称 Remote Proce ...

  9. 为什么会需要消息队列(MQ)?

    为什么会需要消息队列(MQ)? #################################################################################### ...

随机推荐

  1. Shell编程入门(第二版)(下)

    ... ... command n done #select把关键字中的每一项做成类似表单,以交互的方式执行do和done之间的命令 示例-select.sh [python] view plainc ...

  2. Xcode自定义字体不能应用的原因

    想给UILabel换一个自定义的字体,从字体册选择兰亭黑: 然后选择 在Finder中显示,找到字体文件为Lantinghei.ttc: 将其拷贝到项目中,在info.plist里添加字体支持key, ...

  3. “《编程珠玑》(第2版)第2章”:C题(查找变位词,排序)

    C题是这样子的: 给定一个英语字典,找出其中的所有变位词集合.例如,“pots”.“stop”和“tops”互为变位词,因为每一个单词都可以通过改变其他单词中字母的顺序来得到. 下段分析摘自该书(P1 ...

  4. win32多线程学习笔记

    <多核程序设计技术> 第五章--线程api,一个使用windows事件的线程应用程序,vs2008下编译调试通过. // 线程通信机制.cpp : 定义控制台应用程序的入口点. // #i ...

  5. caffe中是如何运用protobuf构建神经网络的?

    caffe这个框架设计的比较小巧精妙,它采用了protobuf来作为交互的媒介,避免了繁重的去设计各个语言的接口,开发者可以使用任意语言通过这个protobuf这个媒介,来运行这个框架. 我们这里不过 ...

  6. c#调用野狗云 rest api

    野狗云就不多介绍了,这里主要是记录一下c#调用他们提供的rest api,把数据post到野狗云存储,直接上代码 static void Main(string[] args) { string st ...

  7. valid sudoku(数独)

    Determine if a Sudoku is valid, according to: Sudoku Puzzles - The Rules. The Sudoku board could be ...

  8. 掌握 Java 泛型类型(一)

    为理解泛型类型为何如此有用,我们要将注意力转向 Java 语言中最容易引发错误的因素之一 - 需要不断地将表达式向下类型转换(downcast)为比其静态类型更为具体的数据类型(请参阅参考资料中的&q ...

  9. linux命令TOP参数load average详解[转]

    我们知道判断一个系统的负载可以使用top,uptime等命令去查看,它分别记录了一分钟.五分钟.以及十五分钟的系统平均负载……我们知道判断一个系统的负载可以使用top,uptime等命令去查看,它分别 ...

  10. Go碎碎念

    1. 时间类型转换为字符串类型 now := time.Now() fmt.Println(now.Format("2006-01-02 03:04:05 PM")) yester ...