RabbitMQ-简单队列

场景化工具架构

  消息队列(MQ)是一种应用程序对应用程序的通信方法。应用程序通过写和检索出入列队的针对应用程序的数据(消息)来通信,而无需专用连接来链接它们。消息传递指的是程序之间通过在消息中发送数据进行通信,而不是通过直接调用彼此来通信,直接调用通常是用于诸如远程过程调用的技术。排队指的是应用程序通过队列来通信。队列的使用除去了接收和发送应用程序同时执行的要求。

  来自百度百科。


  在项目中使用MQ的主要原因,在选课还有在线考试提交答案模块都有用到MQ,这些模块都有一个共性,就是“秒杀”,在高并发环境下,由于来不及同步处理,请求往往会发生堵塞,比如,有大量的insert,updata之类的请求同时到达Mysql,直接导致请求会堆积过多,从而触发很多错误,最明显的可能就是会变慢吧,所以要通过使用消息队列,可以异步处理请求,从而缓解系统压力。

RabbitMQ页面

RabbitMQ-简单队列

RabbitMQ-简单队列


简单队列

模型

RabbitMQ-简单队列
  P:消息的生产者
红色的部分为消息队列
C:消费者

  简单队列的不足:耦合性高,生产者一一对应消费者,如果想消费多个消费者队列中消息,就不可以,队列名变更,消费者也就要同时变更,这时就要用work queues工作队列。


Work queues 工作队列

模型

RabbitMQ-简单队列

  工作队列出现的原因:simple队列是一一对应的,而且我们实际开发,生产者发送消息是毫不费力的,而消费者一般是要跟业务相结合的,消费者接受到消息之后就需要处理,可能需要花费时间,这时候就会积压很多消息,工作队列可以解决这个问题。

  消费者c1和消费者c2处理消息是一样的,这种方式是轮询分发,结果都是不管是不是空闲或者什么,都是均分。

  如图,C1就会繁忙,所以轮询是不合理的,就会有公平分发,这样就会能者多劳,但是前提是必须要关闭自动应答Ack,改成手动,使用basicQos(perfetch=1),意思是说当C1处理完,并给MQ发消息说我处理完了,消息队列才会分发下一个消息。


消息应答与消息持久化

消息应答

   boolean autoAck= false;为消息应答。Ack(Message acknowkedgment),消息应答默认是打开的,为false
   channel.basicConsume(QUEUE_NEME,autoAck,consumer);
  =true时为自动确认模式,意思是说MQ发送消息给C中任何一个之后就是自动删除,但是如果杀死正在消费的,就会丢失正在处理的消息,不想丢失就可以用=false的方式手动模式。
  =false时为手动模式,如果有一个消费者死掉,因为没有收到回执,就会交付给其他消费者,就可以保证不丢失。rabbitmq支持消息应答,消费者发送一个消息应答,告诉mq说我已经完成了你可以删除了,mq才会删除对应的消息。
  

消息持久化

  如果mq死掉,消息依旧会丢失,所有这就体现了mq持久化的特性:
   channel.queueDeclar(QUEUE_NEME,false,false,false,null);

RabbitMQ-简单队列