延迟交换机

延迟交换机

作用

首先,之前的消息过期时间是通过给消息或者队列加消息过期时间实现,会存在两个问题:

  1. 我们需要根据不同的业务在队列上指定不同的过期策略,这时队列的名称也不能相同,如果业务场景复杂时,维护成本过高。

  1. 因为队列先进先出的原则且串行消费,如果先进入队列的消息过期时间较长,后进入队列的过期时间较短,那么在该场景下,待先进入的消息被消费完成后后面的消息早已过期,导致本来应该很快被消费的消息等待处理的时间过长。

安装插件

  1. 在github上下载对应版本的插件并上传到rabbitmq服务器中

https://github.com/rabbitmq/rabbitmq-delayed-message-exchange/releases/tag/3.9.0

  1. 复制插件到容器的plugins目录下

docker cp rabbitmq_delayed_message_exchange-3.9.0.ez rabbitmq:/opt/rabbitmq/plugins

进入到容器内部可以看到该插件

docker exec -it rabbitmq bash

cd opt/rabbitmq/plugins

ls

进入的sbin目录中启动该插件

 cd ../sbin/
 
 rabbitmq-plugins enable rabbitmq_delayed_message_exchange

然后退出容器,并重启rabbitmq容器

 exit
 
 docker restart rabbitmq
  1. 在客户端的构建交换机这里我们就可以看到多了一个x-delayed-message类型

使用API

延迟交换机的相关配置信息

@Configuration
public class DelayedConfig {

    public static final String DELAYED_EXCHANGE = "delayed-exchange";
    public static final String DELAYED_QUEUE = "delayed-queue";
    public static final String DELAYED_ROUTING_KEY = "delayed.#";

    @Bean
    public Exchange delayedExchange(){
        Map<String, Object> arguments = new HashMap<>();
        //指定通信方式为topic
        arguments.put("x-delayed-type","topic");
        //使用CustomExchange类创建,类型要指定为“x-delayed-message”类型
        Exchange exchange = new CustomExchange(DELAYED_EXCHANGE,"x-delayed-message",true,false,arguments);
        return exchange;
    }

    @Bean
    public Queue delayedQueue(){
        return QueueBuilder.durable(DELAYED_QUEUE).build();
    }

    @Bean
    public Binding delayedBinding(Queue delayedQueue,Exchange delayedExchange){
        return BindingBuilder.bind(delayedQueue).to(delayedExchange).with(DELAYED_ROUTING_KEY).noargs();
    }
}

生产者

@SpringBootTest
public class DelayedPublisherTest {

    @Autowired
    private RabbitTemplate rabbitTemplate;

    @Test
    public void publish(){
        rabbitTemplate.convertAndSend(DelayedConfig.DELAYED_EXCHANGE, "delayed.abc", "xxxx", new MessagePostProcessor() {
            @Override
            public Message postProcessMessage(Message message) throws AmqpException {
                //设置消息延迟发送的时间
                message.getMessageProperties().setDelay(10000);
                return message;
            }
        });
    }
}

通过上述代码说明消息会在发送出去后被路由到一个特定的延迟交换机上,并在该交换机中等待指定的延迟时间。在延迟时间到达后,消息将被转发到指定的目标队列中,供消费者进行消费。

但是通过此插件实现延迟消息也会有弊端:

  1. 插件的版本一定要和RabbitMQ的版本相对应,可以看一下插件每个版本的兼容性说明,开启插件后一定重启RabbitMQ服务。

  1. 消息的可靠性问题,在极端情况下(如 RabbitMQ 节点故障或网络异常等),可能会造成消息没有正常发送或丢失的情况。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

像鸟一样菜

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值