热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

RabbitMQ延时队列怎么在SpringBoot中使用

本篇文章为大家展示了RabbitMQ延时队列怎么在SpringBoot中使用,内容简明扼要并且容易理解,绝对能使你眼前一亮,通过这篇文章的详细介绍希望你能

本篇文章为大家展示了RabbitMQ延时队列怎么在SpringBoot中使用,内容简明扼要并且容易理解,绝对能使你眼前一亮,通过这篇文章的详细介绍希望你能有所收获。

1.什么是MQ

MQ,是一种跨进程的通信机制,用于上下游传递消息。

在互联网架构中,MQ是一种非常常见的上下游“逻辑解耦+物理解耦”的消息通信服务。

使用了MQ之后,消息发送上游只需要依赖MQ,不用依赖其他服务。

为什么会产生消息列队?

  1. 不同进程(process)之间传递消息时,两个进程之间耦合程度过高,改动一个进程,引发必须修改另一个进程,为了隔离这两个进程,在两进程间抽离出一层(一个模块),所有两进程之间传递的消息,都必须通过消息队列来传递,单独修改某一个进程,不会影响另一个;

  2. 不同进程(process)之间传递消息时,为了实现标准化,将消息的格式规范化了,并且,某一个进程接受的消息太多,一下子无法处理完,并且也有先后顺序,必须对收到的消息进行排队,因此诞生了事实上的消息队列;

延时列队的使用场景?

  1. 订单业务:在淘宝或者京东购买东西,用户下单后未付款则30分钟后取消订单。

  2. 短信通知:手机用户交完话费后,几分钟之内将会收到缴费信息

2.什么是RabbitMQ(这里就做了一下简单介绍)

RabbitMQ是一种消息队列 ,用于常见的进程通信。支持点对点,请求应答和发布订阅模式 并且提供多种语言的支持。常见的java,c#,php都支持。

常被用在异步处理,应用解耦。流量消锋等复杂的业务场景中。和java的kafka一样都属于消息中间件。

下载地址:

https://www.rabbitmq.com/download.html

进入RabbitMQ官网

1.第一步

RabbitMQ延时队列怎么在SpringBoot中使用

第二步

RabbitMQ延时队列怎么在SpringBoot中使用

下载好后不要着急安装RabbitMQ,我们这里还需要安装Erlang

下载地址:http://www.erlang.org/download/otp_win64_17.3.exe

安装步骤

步骤一

RabbitMQ延时队列怎么在SpringBoot中使用

步骤二

RabbitMQ延时队列怎么在SpringBoot中使用

步骤三

RabbitMQ延时队列怎么在SpringBoot中使用

步骤四

RabbitMQ延时队列怎么在SpringBoot中使用

安装完成

现在安装RabbitMQ

步骤一

RabbitMQ延时队列怎么在SpringBoot中使用

步骤二

RabbitMQ延时队列怎么在SpringBoot中使用

步骤三

RabbitMQ延时队列怎么在SpringBoot中使用

安装完成

启动RabbitMQ管理工具

开始菜单 — 最新添加 — 展开 — 选中双击

RabbitMQ延时队列怎么在SpringBoot中使用

输入命令:rabbitmq-plugins enable rabbitmq_management

效果如果图

RabbitMQ延时队列怎么在SpringBoot中使用

在浏览器中输入地址查看:http://127.0.0.1:15672/

RabbitMQ延时队列怎么在SpringBoot中使用

出现次页面代表成功,默认用户和密码都是guest/ guest

若不出现此页面,就是安装失败了,不要慌,多半问题在系统用户名必须是中文(放心有解决办法):

Windows下安装RabbitMQ后,按正常RabbitMQ会自动注册服务并自动启动,但是如果有的道友不注意中英文目录就会出现服务启动后几秒钟自动停止,而且反反复复。

RabbitMQ延时队列怎么在SpringBoot中使用

出现这种情况一般都是由我们的用户名是中文,而导致默认的DB和log访问出现问。所以我建议以后大家在使用windows操作系统的时候尽量用英文来命名文件或目录,这样会极大的减小以后安装软件出现莫名其妙的问题的bug。

接下来我们先卸载我们的RabbitMQ,然后在我们的系统变量里设置一个RABBITMQ_BASE 的变量路径为一个不含英文的路径 比如 E:\rabbit,最后我们重新安装RabbitMQ即可,然后就会看到RabbitMQ服务自动注册了,并且不会自动停止。

SpringBoot整合RabbitMQ

1.添加依赖

pom.xml中添加 spring-boot-starter-amqp的依赖

 
      
   org.springframework.boot
        spring-boot-starter-amqp
 

其他依赖


        org.springframework.boot
        spring-boot-starter-web
      
  
      
        org.projectlombok
        lombok
        true
      
  
      
        org.springframework.boot
        spring-boot-starter-test
        test
        
          
            org.junit.vintage
            junit-vintage-engine
          
        
      
      
      
        junit
        junit
        4.12
        test
      

application.yml文件中配置rabbitmq相关内容

spring:
  rabbitmq:
   host: localhost
   port: 5672
   username: guest
   password: guest

这里我们环境就搭建起来了

2.具体编码实现

配置列队

 package com.example.spring_boot_rabbitmq;
  
  
  
  import lombok.extern.slf4j.Slf4j;
  import org.springframework.amqp.core.*;
  import org.springframework.context.annotation.Bean;
  import org.springframework.context.annotation.Configuration;
  
  import java.util.HashMap;
  import java.util.Map;
  
  /**
   * @author:zq
   * @date: Greated in 2019/12/19 11:46
   * 配置队列
   */
  
  @Configuration
  @Slf4j
  public class DelayRabbitConfig {
  
    /**
     * 延迟队列 TTL 名称
     */
    private static final String ORDER_DELAY_QUEUE = "user.order.delay.queue";
    /**
     * DLX,dead letter发送到的 exchange
     * 延时消息就是发送到该交换机的
     */
    public static final String ORDER_DELAY_EXCHANGE = "user.order.delay.exchange";
    /**
     * routing key 名称
     * 具体消息发送在该 routingKey 的
     */
    public static final String ORDER_DELAY_ROUTING_KEY = "order_delay";
  
    public static final String ORDER_QUEUE_NAME = "user.order.queue";
    public static final String ORDER_EXCHANGE_NAME = "user.order.exchange";
    public static final String ORDER_ROUTING_KEY = "order";
  
    /**
     * 延迟队列配置
     * 

     * 1、params.put("x-message-ttl", 5 * 1000);      * 第一种方式是直接设置 Queue 延迟时间 但如果直接给队列设置过期时间,这种做法不是很灵活,(当然二者是兼容的,默认是时间小的优先)      * 2、rabbitTemplate.convertAndSend(book, message -> {      * message.getMessageProperties().setExpiration(2 * 1000 + "");      * return message;      * });      * 第二种就是每次发送消息动态设置延迟时间,这样我们可以灵活控制      **/     @Bean     public Queue delayOrderQueue() {       Map params = new HashMap<>();       // x-dead-letter-exchange 声明了队列里的死信转发到的DLX名称,       params.put("x-dead-letter-exchange", ORDER_EXCHANGE_NAME);       // x-dead-letter-routing-key 声明了这些死信在转发时携带的 routing-key 名称。       params.put("x-dead-letter-routing-key", ORDER_ROUTING_KEY);       return new Queue(ORDER_DELAY_QUEUE, true, false, false, params);     }     /**      * 需要将一个队列绑定到交换机上,要求该消息与一个特定的路由键完全匹配。      * 这是一个完整的匹配。如果一个队列绑定到该交换机上要求路由键 “dog”,则只有被标记为“dog”的消息才被转发,      * 不会转发dog.puppy,也不会转发dog.guard,只会转发dog。      * @return DirectExchange      */     @Bean     public DirectExchange orderDelayExchange() {       return new DirectExchange(ORDER_DELAY_EXCHANGE);     }     @Bean     public Binding dlxBinding() {       return BindingBuilder.bind(delayOrderQueue()).to(orderDelayExchange()).with(ORDER_DELAY_ROUTING_KEY);     }        @Bean     public Queue orderQueue() {       return new Queue(ORDER_QUEUE_NAME, true);     }     /**      * 将路由键和某模式进行匹配。此时队列需要绑定要一个模式上。      * 符号“#”匹配一个或多个词,符号“*”匹配不多不少一个词。因此“audit.#”能够匹配到“audit.irs.corporate”,但是“audit.*” 只会匹配到“audit.irs”。      **/     @Bean     public TopicExchange orderTopicExchange() {       return new TopicExchange(ORDER_EXCHANGE_NAME);     }        @Bean     public Binding orderBinding() {       // TODO 如果要让延迟队列之间有关联,这里的 routingKey 和 绑定的交换机很关键       return BindingBuilder.bind(orderQueue()).to(orderTopicExchange()).with(ORDER_ROUTING_KEY);     }      }

创建一个Order实体类

package com.example.spring_boot_rabbitmq.pojo;
 
 import lombok.Data;
 
 import java.io.Serializable;
 
 /**
  * @author:zq
  * @date: Greated in 2019/12/19 11:49
  */
 @Data
 public class Order implements Serializable {
   private static final long serialVersionUID = -2221214252163879885L;
 
   private String orderId; // 订单id
 
   private Integer orderStatus; // 订单状态 0:未支付,1:已支付,2:订单已取消
 
   private String orderName; // 订单名字
 
 }

接收者

package com.example.spring_boot_rabbitmq;
 
 import com.example.spring_boot_rabbitmq.pojo.Order;
 import com.rabbitmq.client.Channel;
 import lombok.extern.slf4j.Slf4j;
 import org.springframework.amqp.core.Message;
 import org.springframework.amqp.rabbit.annotation.RabbitListener;
 import org.springframework.stereotype.Component;
 
 import java.util.Date;
 
 /**
  * @author:zq
  * @date: Greated in 2019/12/19 11:53
  * 接收者
  */
 
 @Component
 @Slf4j
 public class DelayReceiver {
   @RabbitListener(queues = {DelayRabbitConfig.ORDER_QUEUE_NAME})
   public void orderDelayQueue(Order order, Message message, Channel channel) {
     log.info("###########################################");
     log.info("【orderDelayQueue 监听的消息】 - 【消费时间】 - [{}]- 【订单内容】 - [{}]", new Date(), order.toString());
     if(order.getOrderStatus() == 0) {
       order.setOrderStatus(2);
       log.info("【该订单未支付,取消订单】" + order.toString());
     } else if(order.getOrderStatus() == 1) {
       log.info("【该订单已完成支付】");
     } else if(order.getOrderStatus() == 2) {
       log.info("【该订单已取消】");
     }
     log.info("###########################################");
   }
 
 }

发送者

 package com.example.spring_boot_rabbitmq;
 
 
 import com.example.spring_boot_rabbitmq.pojo.Order;
 import lombok.extern.slf4j.Slf4j;
 import org.springframework.amqp.core.AmqpTemplate;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Component;
 
 import java.util.Date;
 
 /**
 * @author:zq
 * @date: Greated in 2019/12/19 11:55
 * 发送者
 */
 @Component
 @Slf4j
 public class DelaySender {
   @Autowired
   private AmqpTemplate amqpTemplate;
 
   public void sendDelay(Order order) {
     log.info("【订单生成时间】" + new Date().toString() +"【1分钟后检查订单是否已经支付】" + order.toString() );
     this.amqpTemplate.convertAndSend(DelayRabbitConfig.ORDER_DELAY_EXCHANGE, DelayRabbitConfig.ORDER_DELAY_ROUTING_KEY, order, message -> {
       // 如果配置了 params.put("x-message-ttl", 5 * 1000); 那么这一句也可以省略,具体根据业务需要是声明 Queue 的时候就指定好延迟时间还是在发送自己控制时间
       message.getMessageProperties().setExpiration(1 * 1000 * 60 + "");
       return message;
     });
   }
 
 }

测试,访问http://localhost:8080/sendDelay查看日志输出

package com.example.spring_boot_rabbitmq;

import com.example.spring_boot_rabbitmq.pojo.Order;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;


/**
 * @author:zq
 * @date: Greated in 2019/12/19 11:57
 * 测试
 */

@RestController
public class TestController {
  @Autowired
  private DelaySender delaySender;

  @GetMapping("/sendDelay")
  public Object sendDelay() {
    Order order1 = new Order();
    order1.setOrderStatus(0);
    order1.setOrderId("123456");
    order1.setOrderName("小米6");

    Order order2 = new Order();
    order2.setOrderStatus(1);
    order2.setOrderId("456789");
    order2.setOrderName("小米8");

    delaySender.sendDelay(order1);
    delaySender.sendDelay(order2);
    return "ok";
  }

}

输出

RabbitMQ延时队列怎么在SpringBoot中使用

上述内容就是RabbitMQ延时队列怎么在SpringBoot中使用,你们学到知识或技能了吗?如果还想学到更多技能或者丰富自己的知识储备,欢迎关注编程笔记行业资讯频道。


推荐阅读
  • 本文深入探讨了如何利用Maven高效管理项目中的外部依赖库。通过介绍Maven的官方依赖搜索地址(),详细讲解了依赖库的添加、版本管理和冲突解决等关键操作。此外,还提供了实用的配置示例和最佳实践,帮助开发者优化项目构建流程,提高开发效率。 ... [详细]
  • 本文将深入探讨 iOS 中的 Grand Central Dispatch (GCD),并介绍如何利用 GCD 进行高效多线程编程。如果你对线程的基本概念还不熟悉,建议先阅读相关基础资料。 ... [详细]
  • Windows环境下RabbitMQ安装详尽指南
    Windows环境下RabbitMQ安装详尽指南 ... [详细]
  • 本文探讨了 Kafka 集群的高效部署与优化策略。首先介绍了 Kafka 的下载与安装步骤,包括从官方网站获取最新版本的压缩包并进行解压。随后详细讨论了集群配置的最佳实践,涵盖节点选择、网络优化和性能调优等方面,旨在提升系统的稳定性和处理能力。此外,还提供了常见的故障排查方法和监控方案,帮助运维人员更好地管理和维护 Kafka 集群。 ... [详细]
  • SQLmap自动化注入工具命令详解(第28-29天 实战演练)
    SQL注入工具如SQLMap等在网络安全测试中广泛应用。SQLMap是一款开源的自动化SQL注入工具,支持12种不同的数据库,具体支持的数据库类型可在其插件目录中查看。作为当前最强大的注入工具之一,SQLMap在实际应用中具有极高的效率和准确性。 ... [详细]
  • 本文介绍了如何使用Postman构建和发送HTTP请求,包括四个主要部分:方法(Method)、URL、头部(Headers)和主体(Body)。特别强调了Body部分的重要性,并详细说明了不同类型的请求体。 ... [详细]
  • 本文介绍了如何查看PHP网站及其源码的方法,包括环境搭建、本地测试、源码查看和在线查找等步骤。 ... [详细]
  • 本文介绍了如何使用Python爬取妙笔阁小说网仙侠系列中所有小说的信息,并将其保存为TXT和CSV格式。主要内容包括如何构造请求头以避免被网站封禁,以及如何利用XPath解析HTML并提取所需信息。 ... [详细]
  • 本文详细介绍了Java代码分层的基本概念和常见分层模式,特别是MVC模式。同时探讨了不同项目需求下的分层策略,帮助读者更好地理解和应用Java分层思想。 ... [详细]
  • IOS Run loop详解
    为什么80%的码农都做不了架构师?转自http:blog.csdn.netztp800201articledetails9240913感谢作者分享Objecti ... [详细]
  • 本文详细介绍了 InfluxDB、collectd 和 Grafana 的安装与配置流程。首先,按照启动顺序依次安装并配置 InfluxDB、collectd 和 Grafana。InfluxDB 作为时序数据库,用于存储时间序列数据;collectd 负责数据的采集与传输;Grafana 则用于数据的可视化展示。文中提供了 collectd 的官方文档链接,便于用户参考和进一步了解其配置选项。通过本指南,读者可以轻松搭建一个高效的数据监控系统。 ... [详细]
  • 在对WordPress Duplicator插件0.4.4版本的安全评估中,发现其存在跨站脚本(XSS)攻击漏洞。此漏洞可能被利用进行恶意操作,建议用户及时更新至最新版本以确保系统安全。测试方法仅限于安全研究和教学目的,使用时需自行承担风险。漏洞编号:HTB23162。 ... [详细]
  • Python多线程编程技巧与实战应用详解 ... [详细]
  • 为了在Hadoop 2.7.2中实现对Snappy压缩和解压功能的原生支持,本文详细介绍了如何重新编译Hadoop源代码,并优化其Native编译过程。通过这一优化,可以显著提升数据处理的效率和性能。此外,还探讨了编译过程中可能遇到的问题及其解决方案,为用户提供了一套完整的操作指南。 ... [详细]
  • QT框架中事件循环机制及事件分发类详解
    在QT框架中,QCoreApplication类作为事件循环的核心组件,为应用程序提供了基础的事件处理机制。该类继承自QObject,负责管理和调度各种事件,确保程序能够响应用户操作和其他系统事件。通过事件循环,QCoreApplication实现了高效的事件分发和处理,使得应用程序能够保持流畅的运行状态。此外,QCoreApplication还提供了多种方法和信号槽机制,方便开发者进行事件的定制和扩展。 ... [详细]
author-avatar
xuxiao
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有