广告
返回顶部
首页 > 资讯 > 后端开发 > 其他教程 >redis实现延时队列的两种方式(小结)
  • 375
分享到

redis实现延时队列的两种方式(小结)

2024-04-02 19:04:59 375人浏览 安东尼
摘要

背景 项目中的流程监控,有几种节点,需要监控每一个节点是否超时。按传统的做法,肯定是通过定时任务,去扫描然后判断,但是定时任务有缺点:1,数据量大会慢;2,时间不好控制,太短,怕一

背景

项目中的流程监控,有几种节点,需要监控每一个节点是否超时。按传统的做法,肯定是通过定时任务,去扫描然后判断,但是定时任务有缺点:1,数据量大会慢;2,时间不好控制,太短,怕一次处理不完,太长状态就会有延迟。所以就想到用延迟队列的方式去实现。

一,Redis的过期key监控

1,开启过期key监听

在redis的配置里把这个注释去掉


notify-keyspace-events Ex

然后重启redis

2,使用redis过期监听实现延迟队列

继承KeyExpirationEventMessageListener类,实现父类的方法,就可以监听key过期时间了。当有key过期,就会执行这里。这里就把需要的key过滤出来,然后发送给kafka队列。


@Component
@Slf4j
public class RedisKeyExpirationListener extends KeyExpirationEventMessageListener {

  @Autowired
  private KafkaProducerService kafkaProducerService;

  public RedisKeyExpirationListener(RedisMessageListenerContainer listenerContainer) {
    super(listenerContainer);
  }

  
  @Override
  public void onMessage(Message message, byte[] pattern){
    if(message == null || StringUtils.isEmpty(message.toString())){
      return;
    }
    String content = message.toString();
    //key的格式为  flag:时效类型:运单号 示例如下
    try {
      if(content.startsWith(AbnConstant.EMS)){
        kafkaProducerService.sendMessageSync(TopicConstant.EMS_WAYBILL_ABN_QUEUE,content);
      }else if(content.startsWith(AbnConstant.YUNDA)){
        kafkaProducerService.sendMessageSync(TopicConstant.YUNDA_WAYBILL_ABN_QUEUE,content);
      }
    } catch (Exception e) {
      log.error("监控过期key,发送kafka异常,",e);
    }
  }
}

可以看的出来,这种方式其实是很简单的,但是有几个问题需要注意,一是,这个尽量单机运行,因为多台机器都会执行,浪费cpu,增加数据库负担。二是,机器频繁部署的时候,如果有时间间隔,会出现数据的漏处理。

二,redis的zset实现延迟队列

1,生产者实现

可以看到生产者很简单,其实就是利用zset的特性,给一个zset添加元素而已,而时间就是它的score。


public void produce(Integer taskId, long exeTime) {
  System.out.println("加入任务, taskId: " + taskId + ", exeTime: " + exeTime + ", 当前时间:" + LocalDateTime.now());
  RedisOps.getJedis().zadd(RedisOps.key, exeTime, String.valueOf(taskId));
}

2,消费者实现

消费者的代码也不难,就是把已经过期的zset中的元素给删除掉,然后处理数据。


public void consumer() {
  Executors.newSingleThreadExecutor().submit(new Runnable() {
    @Override
    public void run() {
      while (true) {
        Set<String> taskIdSet = RedisOps.getJedis().zrangeByScore(RedisOps.key, 0, System.currentTimeMillis(), 0, 1);
        if (taskIdSet == null || taskIdSet.isEmpty()) {
          System.out.println("没有任务");
 
        } else {
          taskIdSet.forEach(id -> {
            long result = RedisOps.getJedis().zrem(RedisOps.key, id);
            if (result == 1L) {
              System.out.println("从延时队列中获取到任务,taskId:" + id + " , 当前时间:" + LocalDateTime.now());
            }
          });
        }
        try {
          TimeUnit.MILLISECONDS.sleep(100);
        } catch (InterruptedException e) {
          e.printStackTrace();
        }
      }
    }
  });
}

可以看到这种方式其实是比上个方式要好的。因为,他的那两个缺点都被克服掉了。多台机器也没事儿,也不用再担心部署时间间隔长的问题。

总结

两个方式都是不错的,都能解决问题。碰到问题,多思考,多总结。

到此这篇关于redis实现延时队列的两种方式(小结)的文章就介绍到这了,更多相关redis 延时队列内容请搜索编程网以前的文章或继续浏览下面的相关文章希望大家以后多多支持编程网!

--结束END--

本文标题: redis实现延时队列的两种方式(小结)

本文链接: https://www.lsjlt.com/news/122795.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

本篇文章演示代码以及资料文档资料下载

下载Word文档到电脑,方便收藏和打印~

下载Word文档
猜你喜欢
  • redis实现延时队列的两种方式(小结)
    背景 项目中的流程监控,有几种节点,需要监控每一个节点是否超时。按传统的做法,肯定是通过定时任务,去扫描然后判断,但是定时任务有缺点:1,数据量大会慢;2,时间不好控制,太短,怕一...
    99+
    2022-11-12
  • Springboot+rabbitmq实现延时队列的两种方式
    目录什么是延时队列,延时队列应用于什么场景利用TTL DLX实现延时队列的方式TTL DLX是什么Springboot集成rabbitmq实现第一种方式利用Rabbitmq的插件x-...
    99+
    2022-11-12
  • 基于Redis实现延时队列的优化方案小结
    目录一、延时队列的应用二、延时队列的实现三、总结一、延时队列的应用 近期在开发部门的新项目,其中有个关键功能就是智能推送,即根据用户行为在特定的时间点向用户推送相应的提醒消息,比如以下业务场景: 在用户点击充值项后,半小...
    99+
    2022-07-05
    Redis延时队列 Redis延时队列优化
  • RabbitMQ实现延迟队列的两种方式详解
    目录1. 用插件1.1 安装插件1.2 消息收发2. DLX 实现延迟队列2.1 延迟队列实现思路2.2 案例3. 小结定时任务各种各样,常见的定时任务例如日志备份,我们可能在每天凌...
    99+
    2022-11-12
  • RabbitMQ实现延迟队列的两种方式分别是什么
    这期内容当中小编将会给大家带来有关RabbitMQ实现延迟队列的两种方式分别是什么,文章内容丰富且以专业的角度为大家分析和叙述,阅读完这篇文章希望大家可以有所收获。定时任务各种各样,常见的定时任务例如日志备份,我们可能在每天凌晨 3 点去备...
    99+
    2023-06-22
  • .NETCore基于RabbitMQ实现延时队列的两方法
    目录前言实现延时队列的两种方式利用rabbitmq死信队列x-dead-letter-exchange和x-dead-letter-routing-key.NETCore实现方式ra...
    99+
    2022-11-13
  • Redis延迟队列和分布式延迟队列的简答实现
            最近,又重新学习了下Redis,Redis不仅能快还能慢,简直利器,今天就为大家介绍一下Redi...
    99+
    2022-11-12
  • 基于Java数组实现循环队列的两种方法小结
    用java实现循环队列的方法:1、添加一个属性size用来记录眼下的元素个数。目的是当head=rear的时候。通过size=0还是size=数组长度。来区分队列为空,或者队列已满。2、数组中仅仅存储数组大小-1个元素,保证rear转一圈之...
    99+
    2023-05-30
    java 数组 循环队列
  • Redis实现延迟队列的方法是什么
    这篇文章主要介绍“Redis实现延迟队列的方法是什么”,在日常操作中,相信很多人在Redis实现延迟队列的方法是什么问题上存在疑惑,小编查阅了各式资料,整理出简单好用的操作方法,希望对大家解答”Redis实现延迟队列的方法是什么”的疑惑有所...
    99+
    2023-07-05
  • mysql自动填充时间的两种实现方式小结
    目录mysql自动填充时间的两种方式方法一:数据库级别方式二:代码级别mysql自动填充时间的两种方式 mysql建表的时候有两个列,一个是createtime、另一个是updatetime 当插入一条数据,create...
    99+
    2022-11-30
    mysql自动填充时间 自动填充时间 mysql自动填充
  • redis实现队列的阻塞、延时、发布和订阅
    目录普通队列阻塞队列发布订阅模式延时队列和优先级队列应用场景Redis不仅可作为缓存服务器,还可以用作消息队列。它的列表类型天生支持用作消息队列。如下图所示: 由于Redis的列表...
    99+
    2022-11-13
  • Java 延迟队列的常用的实现方式
    目录1.  DelayQueue2.  Redis Key过期回调3.  RocketMQ延迟队列的使用场景还比较多,例如: 1、超时未收到支付回调,主...
    99+
    2022-11-12
  • Redis优雅地实现延迟队列的方法分享
    目录前言使用依赖配置配置文件demo代码执行效果原理分析队列创建生产者消费者整个流程总结思考前言 工作中常常会遇到这样的场景,如订单到期未支付取消,到期自动续费等,我们发现延迟队列非常适合在这样的场景中使用。常见的延迟队...
    99+
    2023-02-26
    Redis实现延迟队列 Redis延迟队列
  • redis如何实现队列的阻塞、延时、发布和订阅
    这篇文章主要介绍了redis如何实现队列的阻塞、延时、发布和订阅的相关知识,内容详细易懂,操作简单快捷,具有一定借鉴价值,相信大家阅读完这篇redis如何实现队列的阻塞、延时、发布和订阅文章都会有所收获,下...
    99+
    2022-10-19
  • Android实现延迟的几种方法小结
    本文实例总结了Android实现延迟的几种方法。分享给大家供大家参考,具体如下: 一、通过Thread new Thread(){ public void run(){ sl...
    99+
    2022-06-06
    小结 方法 Android
  • redis实现缓存的两种方式
    本篇文章给大家分享的是有关redis实现缓存的两种方式,小编觉得挺实用的,因此分享给大家学习,希望大家阅读完这篇文章后可以有所收获,话不多说,跟着小编一起来看看吧。redis实现缓存大致为两种措施:一、脚本...
    99+
    2022-10-18
  • java固定大小队列的几种实现方式详解
    目录前言基于Hutool中的FixedLinkedHashMap基于Guava的EvictingQueue基于Redis的list操作总结前言 最近团队有同学在开发中,遇到一个需求,...
    99+
    2022-11-12
  • 延时任务的四种实现方式
    什么是延迟任务? 顾明思议,我们把需要延迟执行的任务叫做延迟任务。 延迟任务的使用场景有以下这些: 红包 24 小时未被查收,需要延迟执退还业务; 每个月账单日,需要给用户发送当月的对账单; 订单下单之后 30 分钟后,用户如果没...
    99+
    2023-10-04
    java Powered by 金山文档
  • 基于Redis实现阻塞队列的方式
    日常需求开发过程中,不免会遇到需要通过代码进行异步处理的情况,比如批量发送邮件,批量发送短信,数据导入,为了减少用户的等待,不希望一直菊花转啊转,因此需要进行异步处理,做法就是讲要处...
    99+
    2022-11-12
  • C#实体类转换的两种方式小结
    目录C#实体类转换方式以下提供两种方式实现功能开发环境实现代码C#实体类转为JSON字符串总结C#实体类转换方式 将一个实体类的数据赋值到另一个实体类中(亦或者实现深拷贝)。 以下提...
    99+
    2023-01-28
    C#实体类 C#实体类转换 C#转换实体类
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作