一、概述

来自队列的消息可以是“死信”;即,在发生以下任何事件时重新发布到交易所:

  • 使用者使用basic.ject或basic.nack对消息进行否定确认,重新排队参数设置为false。

  • 由于每条消息的TTL,消息过期;

  • 消息已被丢弃,因为其队列超过了长度限制

请注意,队列的过期不会使其中的消息成为死信。

死信交换(DLX)是正常的交换。它们可以是任何常见的类型,并按常规进行声明。

对于任何给定的队列,DLX可以由客户端使用队列的参数来定义,也可以在服务器中使用策略来定义。在策略和参数都指定DLX的情况下,参数中指定的DLX将替代策略中指定的。

建议使用策略进行配置,因为它允许不涉及应用程序重新部署的DLX重新配置。

二、使用策略进行配置

要使用策略指定 DLX,请添加密钥“死信交换” 到策略定义。例如:

Rabbitmqctl

rabbitmqctl set_policy DLX ".*"'{"dead-letter-exchange":"my-dlx"}' --apply-to queues

rabbitmqctl (Windows)

rabbitmqctl set_policy DLX ".*""{""dead-letter-exchange"":""my-dlx""}" --apply-to queues

上述策略将 DLX“my-dlx”应用于所有队列。这只是一个例子,在实践中 不同的队列集可能会使用不同的死信设置(或根本不使用)

同样,可以通过添加 策略的密钥“死信路由密钥”。

三、使用可选队列参数进行配置

要设置队列的死信交换,请在声明队列时指定可选的x-dead-letter-exchange参数。该值必须是同一虚拟主机中的交换机名称:

channel.exchangeDeclare("some.exchange.name", "direct");Map<String, Object> args = new HashMap<String, Object>();
args.put("x-dead-letter-exchange", "some.exchange.name");
channel.queueDeclare("myqueue", false, false, false, args);

上面的代码声明了一个名为some.exchange.name的新交换,并将此新交换设置为新建队列的死信交换。请注意,在声明队列时不必声明交换,但在消息需要使用死信时,它应该已经存在;如果它丢失了,那么消息将被静默地丢弃。

您还可以指定一个路由密钥,以便在死字消息时使用。如果未设置此项,则将使用消息自己的路由密钥。

args.put("x-dead-letter-routing-key", "some-routing-key");

指定死信交换后,除了对声明的队列具有通常的配置权限外,用户还需要对该队列具有读取权限,对死信交换具有写入权限。在队列声明时验证权限。

四、路由死信消息

死信消息被路由到其以下任一死信队列:

  • 使用为他们所在的队列指定的路由密钥;或者如果没有设置,

  • 使用与最初相同的路由密钥 发布者

例如,如果您将一条消息发布到具有路由关键字foo的交换机,并且该消息是死信的,则它将被发布到其具有路由关键字foo的死信交换机。如果消息最初到达的队列已声明为x-dead-letter-routing-key设置为bar,则消息将发布到具有路由密钥bar的死信交换机。

请注意,如果未为 队列,其上的消息是死信的,具有所有原始路由密钥。这包括路由密钥 由 CC 和密件抄送标头添加 (有关这两个标头的详细信息,请参阅发件人选择的分发)。

有可能形成消息死信的循环。为 实例,当队列死信时,可能会发生这种情况 发送到默认交换的消息,而不指定 死信路由密钥。此类循环中的消息(即 两次到达同一队列的邮件)将是 如果整个周期中没有拒绝,则丢弃。

五、安全

默认情况下,死信消息会在内部未启用发布者确认的情况下重新发布。因此,在集群中使用 DLX RabbitMQ 环境不保证安全。邮件将从 发布到 DLX 目标队列后立即启动原始队列。这确保了 没有可能耗尽代理的过度消息积累的可能性 资源,但如果目标队列不可用于接受消息,则消息可能会丢失。

由于 RabbitMQ 3.10 仲裁队列支持至少一次死信,其中消息在内部打开发布者确认的情况下重新发布。

六、对消息的死信影响

消息的死信会修改其标头:

  • 交易所名称将替换为最新的死信交易所名称,

  • 路由密钥可以替换为执行死信的队列中指定的密钥,

  • 如果发生上述情况,CC 标头也将被删除,并且

  • 密件抄送标头将根据发件人选择的分发删除

死信进程将数组添加到 每条死信消息都命名为X-Death。 此数组包含每个死信事件的条目, 由一对 {队列, 原因} 标识。 每个这样的条目都是一个包含 的几个字段:

  • 队列:消息在变为死信之前所在的队列的名称

  • 原因:死字的原因,见下文

  • time:消息作为 64 位 AMQP 0-9-1 时间戳的死信日期和时间

  • Exchange - 消息发布到的 Exchange (请注意,这将是一个死信 如果消息多次为死信,则交换)

  • 路由密钥:发布消息时使用的路由密钥(包括 CC 密钥,但不包括密件抄送密钥)

  • 计数:由于此原因,此消息在此队列中被死信的次数

  • 原始过期(如果消息由于每条消息的 TTL 而成为死信): 消息的原始过期属性。过期属性将从 关于死信的消息,以防止它在路由到的任何队列中再次过期。

新条目将附加到 x-death 数组的开头。如果 x-death 已经包含带有 相同的队列和死字原因,其计数字段将是 递增,它将被移动到数组的开头。

原因是描述为什么 消息是死信的,并且是以下之一:

  • 已拒绝:邮件被拒绝,重新排队参数设置为 false

  • 已过期:消息 TTL 已过期

  • maxlen:已超出允许的最大队列长度

  • delivery_limit:消息返回的次数超过了限制(由仲裁队列的策略参数传递限制设置)。

为第一个死信事件添加了三个顶级标题。他们是

  • X-第一死亡原因

  • X-第一死亡队列

  • X-第一次死亡交换

它们与原始死信事件的原因、队列和交换字段具有相同的值。一旦添加,这些标头就永远不会被修改。

RabbitMq死信队列及其处理方案相关推荐

  1. Rabbitmq死信队列

    目录 1.什么是死信队列 2.产生死信队列的原因 3.代码实现---直连交换机 3.1.导入依赖 3.2.配置rabbitmq连接信息 3.3.编写配置类 3.4.编写生产者 3.5.编写消费者 3. ...

  2. Java秒杀系统实战系列~RabbitMQ死信队列处理超时未支付的订单(转)

    转自: https://juejin.cn/post/6844903903130042376 文末有源代码,非常棒 摘要: 本篇博文是"Java秒杀系统实战系列文章"的第十篇,本篇 ...

  3. RabbitMQ - 死信队列(DLX)

    RabbitMQ - 死信队列(DLX) 配置死信队列 方式1 - RabbitMQ 管理后台配置死信队列 方式2 - 代码创建死信队列 验证 满足死信队列的条件 死信队列只是一个概念,本质就是普通的 ...

  4. 【分布式】Rabbitmq死信队列模型、实战场景---订单延迟30min支付处理

    分布式 内容管理 死信队列 死信队列demo 死信队列消息模型 平台订单支付超时 --- 演示 业务分析 代码实现 RabbitMQ 死信队列/ 延迟队列 - 延迟业务逻辑 最近可能分布式进入Redi ...

  5. RabbitMQ死信队列应用

    目录 1.什么是死信队列 2.死信队列应用场景 3.延迟消息概念 3.1 消息的TTL(Time To Live) 3.2 死信交换器 3.3 延时队列 4.死信队列使用流程图 5.死信队列应用(管理 ...

  6. RabbitMQ死信队列,延时队列

    死信队列 消息被消费方否定确认,使用channel.basicNack或channel.basicReject, 并且此时requeue属性被设置为false. 消息在队列的存活时间超过设置的TTL时 ...

  7. 消息队列控制灯代码_代码实现RabbitMQ死信队列的创建

    ‍ ‍前言:‍ ‍ 之前有写过死信队列的使用场景以及通过管控台创建死信.这次就通过代码实现死信队列的创建,同时也分享一下RabbitMQ封装的类. 准备: 1. 先准备一个死信队列(最后用来消费)的参 ...

  8. 消息中间件--RabbitMQ --死信队列

    https://blog.csdn.net/u012211603/article/details/85707760 介绍一些概念 1.首先是任何的MQ中,都有死信队列的存在 2.RabbitMQ的死信 ...

  9. Spring Cloud Stream与RabbitMQ 死信队列

    RabbitMQ的TTL全称为Time-To-Live,表示的是消息的有效期.消息如果在队列中一直没有被消费并且存在时间超过了TTL,消息就会变成"死信" (Dead Messag ...

最新文章

  1. 一文了解点特征直方图
  2. Qt for Android (Alpha) 发布
  3. myeclipse集成jad
  4. 八十六、从拓扑排序探究有向图
  5. SpringBoot新版
  6. 海量数据持久层解决方案_爱数AnyBackup重磅发布海量非结构化数据超可用解决方案...
  7. postgresql模糊匹配正则表达式性能问题
  8. Web开发如何实现Tomcat等服务器热部署不用重启
  9. android sqlite 添加多个表,Android的 - 导入多个.CSV文件在SQLite数据库的多个表(Android - Impo...
  10. 微软亚研院 | 智能信息检索综述
  11. sublime text_Sublime Text Editor赠品报告和获胜者
  12. 单片机引脚与端口,引脚和GPIO的区别
  13. dimens文件生成器使用方法
  14. 关于ip、pv、uv的概念
  15. 机器学习(ML)、深度学习(DL)和图像处理(opencv)专用英语词典
  16. [附源码]计算机毕业设计springboot基于微信小程序的网络办公系统
  17. 规格书搜索网站分享和体验
  18. Win10电脑怎么恢复出厂设置
  19. 【烧录问题】flymcu下载出现从08000000开始运行失败
  20. 小米盒子访问计算机硬盘,无需电脑教你手机数据传到小米盒子外置硬盘的教程...

热门文章

  1. 使用迭代器和增强版for循环遍历Map集合(keySet)
  2. Threejs使用白底贴图时,显示出来的图片为灰底
  3. 简书凭什么绑定微信号
  4. Android 旗舰机标配的高帧屏(120Hz),对各位 App 开发者有什么影响?
  5. Silverlight MMORPG WebGame游戏设计(六)-----Server和Client的婚后协议[附上完整15M游戏DEMO]...
  6. 汇报工作是技术活,其中艺术你可知道?
  7. curl 发送 POST 请求的四种方式
  8. 通过光盘重置administrator账号密码
  9. Python 小贴士(2)列表与字典
  10. 无重复字符的最长子串