• RabbitMQ 延时消息实现方式


    rabbitmq实现延时消息主要有两种方式:

    • 死信消息(队列ttl+死信exchange)
    • 延时插件 (rabbitmq-delayed-message-exchange)

    rabbitmq 实现方式一:队列ttl+死信exchange

    简述:使用两个队列,一个队列接收消息不消费,等待指定时间后消息死亡,再由该队列绑定的死信exchange再次将其路由到另一个队列提供业务消费。

    ttl 和 死信exchange 相关知识

    ttl

    先贴两个个rabbitmq官方文档:

    • Time-To-Live and Expiration:https://www.rabbitmq.com/ttl.html
    • Dead Letter Exchangeshttps:https://www.rabbitmq.com/dlx.html

    我这里也简单介绍下:
    rabbitmq 可以给 消息 和 队列 设置 ttl(生存时间)

    • 队列设置:x-message-ttl=60000 (队列中所有消息都只有60s存活时间)
    • 指定消息设置:expire=60000 指定消息只有60s存活时间

    如果队列和消息同时设置了ttl,则取较小的那个作为ttl。消息死亡后不会被消费者消费。

    死信exchange

    死信(死亡的消息):

    • 消费者使用 basic.rejectbasic.nack 并将requeue参数设置为 false 来否定的消息
    • ttl到期的消息
    • 队列超过长度限制被丢弃的消息

    当一个队列设置了死信exchange 后,这个队列的死信都会被投递到死信exchange中,然后可以再次路由到其他队列中(如果指定了死信routing key 则死信消息routing key 变为设置的routing key,未设置则为原始 routing key)。

    使用介绍

    1. 先声明一个消费队列 queue_dlx,用来接收死信消息,并提供消费;
    2. 然后声明一个死信exchange_dlx, 绑定 queue_dlx,接收消息后路由至queue_dlx;
    3. 声明一个延迟队列,queue_delay, 用来接收业务消息,但不提供消费,等待消息死亡后转至死信exchange。(即延迟)
    4. 声明一个exchange,由业务发送消息到exchange,然后转至queue_delay.

    一个消息的流程大概是:

    具体使用推荐另一篇文章:
    RabbitMQ 实现固定延时等级的延时消息
    , 直接实现一套不同延时等级的消息,就不用每次都配置各种exchange和queue绑定关系了。

    简单分析

    缺点:

    • 只能支持固定延迟等级的消息
    • 使用较复杂,得声明一堆队列&exchange

    优点:

    • 支持镜像队列复制,实现高可用
    • 支持大量消息(成千上万)

    适用场景: 使用固定延迟时间的场景。

    备注:对于高版本(3.6及以上)的rabbitmq建议使用lazy-mode作为延迟队列,防止大量延时消息堆积而占用大量内存,从而触发rabbitmq换页阻塞队列。 (如果使用spring的话,即使低版本rabbitmq也不用太担心:spring-amqp默认发送持久化消息,即使触发换页,也只是把消息从内存中逐出而已。)

    rabbitmq 实现方式二:rabbitmq延时插件

    简述:延时消息不直接投递到队列中,而是先转储到本地Mnesia数据库中,然后定时器在消息到期后再将其投递到队列中。

    延时插件使用

    关于用法可以直接看这个文档或者网上搜一搜,这里就不介绍了。
    github地址:https://github.com/rabbitmq/rabbitmq-delayed-message-exchange

    其大概原理就是:指定了延时的消息,会被先保存在 Mnesia (erlang编写的数据库管理系统)中,然后有一个定时器去查询最近需要被投递的消息,将其投递到目标队列中。

    在这里插入图片描述

    简单分析

    优点:

    • 基本支持任意延迟时间(不能超过1个月)

    缺点:

    • 延时不可靠,存在消息数量较大或使用很久后延迟不准确(会推迟), 见 issues#72
    • 无备份机制,延时消息存在单个节点磁盘中
    • 不支持ram类型的节点 (数据得存磁盘里面)
    • 增加大量内存的占用 (经测试发现,发送大量延时消息后,rabbitmq内存占用明显增高,比普通消息还要高很多那种。)
    • 安装插件需要重启

    适用场景::如果不是无关紧要的小业务,不建议使用。

    先自我介绍一下,小编13年上师交大毕业,曾经在小公司待过,去过华为OPPO等大厂,18年进入阿里,直到现在。深知大多数初中级java工程师,想要升技能,往往是需要自己摸索成长或是报班学习,但对于培训机构动则近万元的学费,着实压力不小。自己不成体系的自学效率很低又漫长,而且容易碰到天花板技术停止不前。因此我收集了一份《java开发全套学习资料》送给大家,初衷也很简单,就是希望帮助到想自学又不知道该从何学起的朋友,同时减轻大家的负担。添加下方名片,即可获取全套学习资料哦

  • 相关阅读:
    设计模式之代理模式(Proxy Pattern)
    用CHAT写APP的权限需求
    【PAT甲级】1043 Is It a Binary Search Tree
    Sql依赖注入-架构案例(五十五)
    计算机视觉:人脸识别与检测
    Redis数据库管理工具Redis Desktop Manager最新中文
    21天python学习计划
    python-opencv划痕检测-续
    pdb restore in ADG database
    OCR让点读笔如虎添翼
  • 原文地址:https://blog.csdn.net/web18484626332/article/details/126113958