当前位置: 首页 > news >正文

RabbitMQ 如何使用延迟队列

RabbitMQ 如何使用延迟队列

目录

  1. 前置条件
  2. 场景描述
  3. RabbitMQ 延迟队列机制
  4. 实现步骤
    • 1. 安装 RabbitMQ 延迟队列插件
    • 2. 创建延迟队列和交换机
    • 3. 发布延迟消息
    • 4. 消费延迟消息
  5. 示例代码
    • 1. 延迟队列配置
    • 2. 发布消息的 Producer 代码
    • 3. 消费消息的 Consumer 代码
  6. 注意事项

前置条件

  • 操作系统:CentOS 7
  • RabbitMQ:版本 3.8.0+
  • Erlang:版本 21.0+
  • RabbitMQ 延迟队列插件:rabbitmq_delayed_message_exchange

场景描述

假设我们正在设计一个线上售卖电影票的系统,用户购票后有 15 分钟时间进行付款,如果用户在 15 分钟内未付款,订单将自动取消并释放电影票库存。这里,我们可以利用 RabbitMQ 的延迟队列机制,在用户购票时发送一条延迟消息到 RabbitMQ,并设定延迟时间为 15 分钟。如果用户未在 15 分钟内完成付款,延迟消息将被消费者接收并处理订单取消的逻辑。

RabbitMQ 延迟队列机制

RabbitMQ 本身不直接支持延迟队列功能,需要借助 rabbitmq_delayed_message_exchange 插件来实现。该插件为 RabbitMQ 提供了一种新的消息交换机类型——x-delayed-message,可以基于消息属性设置延迟时间,在设定的延迟时间后,将消息发送到目标队列。

实现步骤

1. 安装 RabbitMQ 延迟队列插件

# 下载插件
wget https://github.com/rabbitmq/rabbitmq-delayed-message-exchange/releases/download/v3.8.0/rabbitmq_delayed_message_exchange-3.8.0.ez# 将插件移动到 RabbitMQ 插件目录
mv rabbitmq_delayed_message_exchange-3.8.0.ez /usr/lib/rabbitmq/lib/rabbitmq_server-3.8.0/plugins/# 启用插件
rabbitmq-plugins enable rabbitmq_delayed_message_exchange

2. 创建延迟队列和交换机

我们将使用 x-delayed-message 类型的交换机,并设定延迟队列,用于处理延迟消息。

# 创建交换机
rabbitmqadmin declare exchange name=delayed_exchange type=x-delayed-message \arguments='{"x-delayed-type":"direct"}'# 创建队列
rabbitmqadmin declare queue name=delayed_queue# 绑定交换机与队列
rabbitmqadmin declare binding source=delayed_exchange destination=delayed_queue routing_key=order.payment

3. 发布延迟消息

在发布消息时,可以设置消息属性 x-delay 来指定延迟时间。

# 使用 rabbitmqadmin 发布延迟消息
rabbitmqadmin publish exchange=delayed_exchange routing_key=order.payment \payload="{'order_id': '12345', 'status': 'PENDING_PAYMENT'}" \properties='{"headers":{"x-delay":900000}}'

4. 消费延迟消息

消费者将从延迟队列中消费消息并执行订单取消逻辑。

示例代码

1. 延迟队列配置

在 Spring Boot 项目中,可以通过以下配置来创建延迟交换机和队列。

@Configuration
public class RabbitConfig {public static final String DELAYED_EXCHANGE_NAME = "delayed_exchange";public static final String DELAYED_QUEUE_NAME = "delayed_queue";public static final String ROUTING_KEY = "order.payment";// 创建延迟交换机@Beanpublic CustomExchange delayedExchange() {Map<String, Object> args = new HashMap<>();args.put("x-delayed-type", "direct");return new CustomExchange(DELAYED_EXCHANGE_NAME, "x-delayed-message", true, false, args);}// 创建延迟队列@Beanpublic Queue delayedQueue() {return new Queue(DELAYED_QUEUE_NAME);}// 绑定延迟队列与交换机@Beanpublic Binding delayedBinding(Queue delayedQueue, CustomExchange delayedExchange) {return BindingBuilder.bind(delayedQueue).to(delayedExchange).with(ROUTING_KEY).noargs();}
}

2. 发布消息的 Producer 代码

@Component
public class OrderProducer {@Autowiredprivate RabbitTemplate rabbitTemplate;public void sendOrderMessage(String orderId) {Map<String, Object> message = new HashMap<>();message.put("order_id", orderId);message.put("status", "PENDING_PAYMENT");MessageProperties messageProperties = new MessageProperties();messageProperties.setHeader("x-delay", 15 * 60 * 1000); // 延迟 15 分钟Message msg = new Message(new ObjectMapper().writeValueAsBytes(message), messageProperties);rabbitTemplate.convertAndSend(RabbitConfig.DELAYED_EXCHANGE_NAME, RabbitConfig.ROUTING_KEY, msg);}
}

3. 消费消息的 Consumer 代码

@Component
public class OrderConsumer {@RabbitListener(queues = RabbitConfig.DELAYED_QUEUE_NAME)public void processOrderCancellation(Message message) {try {Map<String, Object> orderMessage = new ObjectMapper().readValue(message.getBody(), Map.class);String orderId = (String) orderMessage.get("order_id");// 取消订单逻辑System.out.println("Order " + orderId + " has been canceled due to non-payment.");} catch (Exception e) {e.printStackTrace();}}
}

注意事项

  1. 插件兼容性:请确保 rabbitmq_delayed_message_exchange 插件与您的 RabbitMQ 版本兼容,否则可能导致插件无法加载。
  2. Erlang 版本:RabbitMQ 依赖于 Erlang,因此确保您的 Erlang 版本满足 RabbitMQ 版本的最低要求。
  3. 延迟时间限制:合理设置延迟时间,避免消息被延迟过长时间导致系统不可预测的性能问题。

相关文章:

RabbitMQ 如何使用延迟队列

RabbitMQ 如何使用延迟队列 目录 前置条件场景描述RabbitMQ 延迟队列机制实现步骤 1. 安装 RabbitMQ 延迟队列插件2. 创建延迟队列和交换机3. 发布延迟消息4. 消费延迟消息 示例代码 1. 延迟队列配置2. 发布消息的 Producer 代码3. 消费消息的 Consumer 代码 注意事项 前置条…...

【C++】栈和队列

目录 前言 一、stack 1. 栈的定义 2. 成员函数 二、queue 1. 队列的定义 2. 成员函数 三、priority_queue 1. 优先队列的定义 2. 成员函数 前言 栈和队列是STL中很重要的两个容器&#xff0c;栈的特点是先进后出&#xff1b;队列的特点是先进先出。还有优先队列&…...

常用的预编码算法学习

一、概况 预编码算法的常用实现方式有以下几种: 1. 间隔预编码(Interval Pre-coding):该算法将原始数据分成若干个间隔,然后对每个间隔内的数据进行编码。间隔的长度可以根据具体情况进行选择,常见的间隔长度有固定长度和可变长度两种方式。 2. 迭代预编码(Iterative…...

人才培养计划大纲

构建全面而高效的人才培养规划 文章大纲&#xff1a; 引言 人才培养的重要性当前人才培养面临的挑战文章目的与结构人才培养规划的基本概念 定义与内涵人才培养规划与企业战略的关系人才培养规划的基本原则人才培养规划的现状分析 当前人才培养规划的实践情况存在的问题与不足…...

多语言环境下的正则表达式实战:校验整数、小数

在软件开发中&#xff0c;正则表达式是验证用户输入数据格式的强大工具&#xff0c;特别是在处理表单验证时。本文将通过JavaScript、Java、Python、C、Rust、Go、C六种编程语言展示如何使用正则表达式来校验输入是否为整数或小数&#xff0c;特别强调小数点后最多保留两位的场…...

过拟合和欠拟合的学习

1.什么拟合 就是说这个曲线能不能很好地描述某些样本数据&#xff0c;并且拥有较好的泛化能力。 2.什么是过拟合 过拟合就是曲线太过于贴切训练数据的特征了&#xff0c;在训练集上表现得非常优秀&#xff0c;近乎完美的预测/区分了所有得数据&#xff0c;但是在新的测试集上…...

中间件的使用

中间件是全局使用 工厂函数定义中间件 middleware.py # 工厂函数的中间件 def simple_middleware(get_response):def middleware(request):print("在视图函数处理之前执行、、、、、")response get_response(request)print("在视图函数处理之后执行。。。。…...

阿里云OSS权限开通步骤及最佳实践

在阿里云云计算平台中&#xff0c;对象存储服务&#xff08;OSS&#xff09;是一种高度可扩展的云存储服务&#xff0c;提供了安全、可靠、低成本的数据存储解决方案。在使用OSS时&#xff0c;正确配置权限是至关重要的&#xff0c;以确保数据的安全性和访问控制。本文将介绍阿…...

【Python贪吃蛇】:编码技巧与游戏设计的完美结合

文章目录 &#x1f525;一、运行效果&#x1f4a5;二、游戏教程✈1. 导入模块❤️2. 初始化游戏元素☔3. 改变蛇移动的方向&#x1f44a;4. 绘制方块&#x1f680;5. 检查蛇头是否在游戏区域内&#x1f308;6. 定义蛇的移动函数&#x1f3ac;7. 绑定键盘事件 ⭐三、完整代码 &a…...

2024.5.19 机器学习周报

引言 Abstract 文献阅读 1、题目 X-HRNET: TOWARDS LIGHTWEIGHT HUMAN POSE ESTIMATION WITH SPATIALLY UNIDIMENSIONAL SELF-ATTENTION 2、引言 高分辨率表示是人体姿态估计实现高性能所必需的&#xff0c;随之而来的问题是高计算复杂度。特别地&#xff0c;主要的姿态估…...

母亲节祝福html源码示例

创建一个完整的HTML页面&#xff0c;我可以为您提供一个简单的HTML模板&#xff0c;其中包含一些示例性的祝福语&#xff0c;并添加一些注释以帮助您理解如何扩展内容。 <!DOCTYPE html> <html lang"zh-CN"><head><meta charset"UTF-8&qu…...

微信小程序开发中的权限管理与用户身份验证:守护数据安全与用户体验

微信小程序开发中的权限管理与用户身份验证&#xff1a;守护数据安全与用户体验 引言 在微信小程序开发中&#xff0c;权限管理和用户身份验证是确保数据安全、保护用户隐私以及提供个性化服务的关键环节。本文将深入探讨微信小程序中如何实现权限管理和用户身份验证&#xf…...

Python3 笔记:二进制的转换

十进制是逢十进一&#xff0c;二进制就是逢二进一。 十进制里最大的数字是9&#xff0c;二进制里最大的数字是1。 11010010001000010000010000001000000010^0110^11010^210010^3100010^41000010^510000010^6100000010^7100000002^012^122^242^382^4162^5322^6642^7128 1、十进…...

代码审计-PHP模型开发篇动态调试反序列化变量覆盖TP框架原生POP链

知识点 1、PHP审计-动态调试-变量覆盖 2、PHP审计-动态调试-原生反序列化 3、PHP审计-动态调试-框架反序列化PHP常见漏洞关键字 SQL注入&#xff1a; select insert update delete mysql_query mysqli等 文件上传&#xff1a; $_FILES&#xff0c;type"file"&…...

前端动态旋转地球背景

效果图 贴下源码 <template><div class"map-bg"><div class"canvas" id"canvs"></div><canvas class"canvasxk" id"canv"></canvas></div> </template><script setup …...

MySQL中的子查询

子查询,在一个查询语句中又出现了查询语句 子查询可以出现在from和where后面 from 表子查询(结果一般为多行多列)把查询结果继续当一张表对待 where 标量子查询(结果集只有一行一列)查询身高最高的学生,查询到一个最高身高 列子查询(结果集只有一行多列) 对上表进行如下操作 …...

Unity打开安卓设备不同的设置面板

1&#xff0c;打开安卓设备不同的设置面板&#xff0c;我还贴心的把Android官网的链接放下面了 2&#xff0c;使用也很方便&#xff1a;unity按钮事件上拖这个脚本&#xff0c;注册MyOpenAndroidSettings方法&#xff0c;参数 填 和枚举值相应的数字 // 功能&#xff1a;打开…...

低空经济+无人机:低空物资运输技术详解

随着科技的飞速发展和航空产业的日益壮大&#xff0c;低空经济已成为全球经济的重要组成部分。无人机作为低空经济的重要载体&#xff0c;其在低空物资运输领域的应用逐渐凸显&#xff0c;为物流、救援等多个领域带来了革命性的变革。 一、低空经济概述 低空经济是指在垂直高度…...

全场景智能终端RK3288主板在智能垃圾回收项目的应用,支持鸿蒙,支持全国产化

全场景智能终端主板AIoT-3588A推出的智能化垃圾回收项目&#xff0c;旨在解决城市化进程中日益突出的垃圾处理问题。智能垃圾分类箱具备触屏操作、自动称重、分类投放以及电子语音播报提示等多项功能&#xff0c;居民能够经过分类积分卡、手机扫码、人脸识别等多种途径进行投放…...

QT设计模式:建造者模式

基本概念 建造者模式是一种创建型设计模式&#xff0c;它允许你创建复杂对象的过程独立于该对象的组成部分以及它们的组装方式。这样可以构造出不同的对象表示。 在建造者模式中&#xff0c;将创建对象的过程和对象的表示分离&#xff0c;通过一步步的构建&#xff0c;可以得…...

LBE-LEX系列工业语音播放器|预警播报器|喇叭蜂鸣器的上位机配置操作说明

LBE-LEX系列工业语音播放器|预警播报器|喇叭蜂鸣器专为工业环境精心打造&#xff0c;完美适配AGV和无人叉车。同时&#xff0c;集成以太网与语音合成技术&#xff0c;为各类高级系统&#xff08;如MES、调度系统、库位管理、立库等&#xff09;提供高效便捷的语音交互体验。 L…...

装饰模式(Decorator Pattern)重构java邮件发奖系统实战

前言 现在我们有个如下的需求&#xff0c;设计一个邮件发奖的小系统&#xff0c; 需求 1.数据验证 → 2. 敏感信息加密 → 3. 日志记录 → 4. 实际发送邮件 装饰器模式&#xff08;Decorator Pattern&#xff09;允许向一个现有的对象添加新的功能&#xff0c;同时又不改变其…...

CVPR 2025 MIMO: 支持视觉指代和像素grounding 的医学视觉语言模型

CVPR 2025 | MIMO&#xff1a;支持视觉指代和像素对齐的医学视觉语言模型 论文信息 标题&#xff1a;MIMO: A medical vision language model with visual referring multimodal input and pixel grounding multimodal output作者&#xff1a;Yanyuan Chen, Dexuan Xu, Yu Hu…...

P3 QT项目----记事本(3.8)

3.8 记事本项目总结 项目源码 1.main.cpp #include "widget.h" #include <QApplication> int main(int argc, char *argv[]) {QApplication a(argc, argv);Widget w;w.show();return a.exec(); } 2.widget.cpp #include "widget.h" #include &q…...

【2025年】解决Burpsuite抓不到https包的问题

环境&#xff1a;windows11 burpsuite:2025.5 在抓取https网站时&#xff0c;burpsuite抓取不到https数据包&#xff0c;只显示&#xff1a; 解决该问题只需如下三个步骤&#xff1a; 1、浏览器中访问 http://burp 2、下载 CA certificate 证书 3、在设置--隐私与安全--…...

pikachu靶场通关笔记22-1 SQL注入05-1-insert注入(报错法)

目录 一、SQL注入 二、insert注入 三、报错型注入 四、updatexml函数 五、源码审计 六、insert渗透实战 1、渗透准备 2、获取数据库名database 3、获取表名table 4、获取列名column 5、获取字段 本系列为通过《pikachu靶场通关笔记》的SQL注入关卡(共10关&#xff0…...

如何在最短时间内提升打ctf(web)的水平?

刚刚刷完2遍 bugku 的 web 题&#xff0c;前来答题。 每个人对刷题理解是不同&#xff0c;有的人是看了writeup就等于刷了&#xff0c;有的人是收藏了writeup就等于刷了&#xff0c;有的人是跟着writeup做了一遍就等于刷了&#xff0c;还有的人是独立思考做了一遍就等于刷了。…...

【碎碎念】宝可梦 Mesh GO : 基于MESH网络的口袋妖怪 宝可梦GO游戏自组网系统

目录 游戏说明《宝可梦 Mesh GO》 —— 局域宝可梦探索Pokmon GO 类游戏核心理念应用场景Mesh 特性 宝可梦玩法融合设计游戏构想要素1. 地图探索&#xff08;基于物理空间 广播范围&#xff09;2. 野生宝可梦生成与广播3. 对战系统4. 道具与通信5. 延伸玩法 安全性设计 技术选…...

C++使用 new 来创建动态数组

问题&#xff1a; 不能使用变量定义数组大小 原因&#xff1a; 这是因为数组在内存中是连续存储的&#xff0c;编译器需要在编译阶段就确定数组的大小&#xff0c;以便正确地分配内存空间。如果允许使用变量来定义数组的大小&#xff0c;那么编译器就无法在编译时确定数组的大…...

排序算法总结(C++)

目录 一、稳定性二、排序算法选择、冒泡、插入排序归并排序随机快速排序堆排序基数排序计数排序 三、总结 一、稳定性 排序算法的稳定性是指&#xff1a;同样大小的样本 **&#xff08;同样大小的数据&#xff09;**在排序之后不会改变原始的相对次序。 稳定性对基础类型对象…...