博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
RabbitMQ
阅读量:5097 次
发布时间:2019-06-13

本文共 3303 字,大约阅读时间需要 11 分钟。

1、RabbitMQ 简介

  MQ全称为Message Queue, (MQ)是一种应用程序对应用程序的通信方法。应用程序通过读写出入队列的消息(针对应用程序的数据)来通信,而无需专用连接来链接它们。

      MQ是消费-生产者模型的一个典型的代表,一端往中不断写入消息,而另一端则可以读取或者订阅队列中的消息。

  RabbitMQ 是一个消息代理。主要的原理就是通过接受和转发消息。RabbitMQ是实现AMQP(高级消息队列协议)的消息中间件的一种,消息中间件主要用于组件之间的解耦。

  RabbitMQ服务器端用Erlang语言编写,支持多种客户端,如:Python、Ruby、.NET、Java、C、PHP、ActionScript、XMPP、STOMP等,支持AJAX。

2、使用场景

     例如:应用程序A向应用程序B发送请求并期望得到响应

              发送方(应用程序A)向消息中间件(RabbitMQ) 发送请求,接受方(应用程序B)订阅请求。发送方将消息发送给消息中间件后,异步执行程序。

              发送方(应用程序B)消息中间件(RabbitMQ) 发送请求接受方(应用程序A)订阅请求。发送方将消息发送给消息中间件后,异步执行程序。

 

     在项目中,将一些无需即时返回且耗时的操作提取出来,进行了,而这种异步处理的方式大大的节省了服务器的,从而提高了系统的吞吐量。

3、RabbitMQ的优势

       高并发;负载均衡;消息持久;耦合低;响应速度快;

4、RabiitMQ术语

       Connection: 是RabbitMQ的socket链接,它封装了socket协议相关部分逻辑。

       ConnectionFactory:Connection的制造工厂。

       Channel:是我们与RabbitMQ打交道的最重要的一个接口,我们大部分的业务操作是在Channel这个接口中完成的,包括定义Queue、定义Exchange、绑定Queue与Exchange、发布消息等。

几个基本概念:

  (1)生产者:生产过程就像发送过程,发送消息的程序就是一个生产者,我们使用“P”来描述它。

          

  (2)消费者:消费过程与接收相似,一个消费者通常是一个等着接受消息的程序,我们使用"C"来描述。
         
  (3)Queue:(队列)是RabbitMQ的内部对象,用于存储消息,用下图表示。
       
  (4)Exchange:(交换机)用下图表示。
           
    
(5)Routing key:

                用于绑定交换机与队列间的key。

                生产者发送消息给交换机时,一般都会指定routing key,用于绑定交换机与队列。

                这还跟交换机类型(Exchange Type)有关:

                四种类型,fanout,direct,topic,headers 

  图解分析:

  生成者生产消息,发送消息到队列,消费者可以从队列获取消息并消费。

          

  多个消费者订阅同一个队列,消息平摊:

          
   

      实际情况:生产者投递消息永远只会先经过交换机,交换机根据交换机类型或规则路由到队列。

          

     

       如果没有路由匹配到队列,则消息会丢失。

 5、RabbitMQ交换机

      1、RabbitMQ消息模型中核心的思想是生产者从不直接将消息发送给队列。实际上,生产者常常甚至不知道是否一个消息会被传递到队列中。

      2、生产者是将消息投递给交换机,消息将被发送到一个队列中还是对个队列中亦或是被抛弃,这都是交换机的类型决定的。

     

    

    
交换机类型: direct,topic,deaders,fanout
    
    
匿名交换机

                     RabbitMQ服务器中存在一个匿名交换机,他不能被删除之前的代码中“”即为匿名交换机

                     channel.basicPublish("", "hello", null, message.getBytes());

   

    
临时队列:

                   当我们使用无参数调用queueDeclare()方法,我们创建一个自动产生的名字,不持久化,独占的,自动删除的队列。

                   String queueName = channel.queueDeclare().getQueue();//名字随机

     绑定:

                 

                1)funout类型的交换机

                  即为交换机与队列绑定,假设一个funout类型的交换机。

                  channel.queueBind(queueName, "logs", "");

             

                 Fanout类型发给所有它所知道的队列。

                channel.exchangeDeclare(“logs”, “fanout”);//声明fanout类型的队列

               2)direct类型的交换机

                     当我们需要对日志系统做严格过滤规则时。比如由于电脑磁盘有限,日志系统只对error级别的日志做保存。显然用Fanout类型交换机满足不了要求。

                     

              3)topic类型的交换机

                  更灵活,选择性更高。通配符式交换机。

      * (星标) 能替代任意一个单词。

      # (哈希) 能代替零个或多个单词。

                          

 6、使用流程
  
(1)客户端连接到消息队列服务器,打开一个channel。
  
(2)客户端声明一个exchange,并设置相关属性。
  
(3)客户端声明一个queue,并设置相关属性。
  
(4)客户端使用routing key,在exchange和queue之间建立好绑定关系。
  
(5)客户端投递消息到exchange。exchange接收到消息后,就根据消息的key和已经设置的binding,进行消息路由,将消息投递到一个或多个队列里。
  
      图例:
           
 

     7、代码实例

 

(1)生产者发送消息:

1 //1、创建一个服务器连接 2  ConnectionFactory factory = new ConnectionFactory(); 3  factory.setHost(“localhost”); //可连远程主机IP 4  factory.setPort(5672);//固定端口 5  factory.setUsername(“guest”);//远程必须新建用户 6  factory.setPassword(“guest”);//密码 7  Connection connection =  factory.newConnection();  8  Channel channel = connection.createChannel(); 9 //2、生产者发布消息10  channel.queueDeclare(“hello”, false, false, false, null); //声明队列11  String message = "Hello World!"; 12  channel.basicPublish("", QUEUE_NAME, null, message.getBytes()); //发布13 //3、关闭连接14  channel.close();15  connection.close();

 

(2)消费者接收消息

1 //1、首先创建连接,与生产者一样 2  channel.queueDeclare(“hello”, false, false, false, null); //声明队列 3  QueueingConsumer consumer = new QueueingConsumer(channel); 4  channel.basicConsume(QUEUE_NAME, true, consumer); 5 //2、接收消息 6 while (true) {  7 //3、线程阻塞,挂起直到队列传输消息到来 8   QueueingConsumer.Delivery delivery = consumer.nextDelivery();  9   String message = new String(delivery.getBody()); 10 }

 

转载于:https://www.cnblogs.com/mxmbk/p/5343931.html

你可能感兴趣的文章
DM8168 DVRRDK软件框架研究
查看>>
django迁移数据库错误
查看>>
epoll学习01
查看>>
yii 跳转页面
查看>>
闭包问题
查看>>
C#一个FTP操作封装类FTPHelper
查看>>
Linux运维基础入门(二):网络基础知识梳理02
查看>>
洛谷 1449——后缀表达式(线性数据结构)
查看>>
[最小割][Kruskal] Luogu P5039 最小生成树
查看>>
Data truncation: Out of range value for column 'Quality' at row 1
查看>>
Dirichlet分布深入理解
查看>>
(转)Android之发送短信的两种方式
查看>>
使用vue脚手架搭建项目
查看>>
Java基础之ArrayList与LinkedList、Vector,以及HashMap与HashTable的区别
查看>>
python第九天课程:遇到了金角大王
查看>>
字符串处理
查看>>
ECharts(Enterprise Charts 商业产品图表库)初识
查看>>
LeetCode Factorial Trailing Zeroes (阶乘后缀零)
查看>>
hdu 5402 Travelling Salesman Problem (技巧,未写完)
查看>>
[AIR] 获取U盘,打开U盘
查看>>