Redis实现订单自动过期功能的示例代码

用户下单后,规定XX分钟后自动设置为“已过期”,不能再发起支付。项目类似此类"过期"的需求,笔者提供一种使用Redis的解决思路,结合Redis的订阅、发布和键空间通知机制(Keyspace Notifications)进行实现。

Posted in Redis onMay 08, 2021

配置redis.confg

notify-keyspace-events选项默认是不启用,改为notify-keyspace-events “Ex”。重启生效,索引位i的库,每当有过期的元素被删除时,向**keyspace@:expired**频道发送通知。
E表示键事件通知,所有通知以__keyevent@__:expired为前缀;
x表示过期事件,每当有过期被删除时发送。

与SpringBoot进行集成

①注册JedisConnectionFactory

import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.data.redis.connection.RedisPassword;
import org.springframework.data.redis.connection.RedisStandaloneConfiguration;
import org.springframework.data.redis.connection.jedis.JedisConnectionFactory;

import redis.clients.jedis.JedisPool;
import redis.clients.jedis.JedisPoolConfig;

@Configuration
public class RedisConfig {
 
 @Value("${redis.pool.maxTotal}")
 private Integer maxTotal;
 
 @Value("${redis.pool.minIdle}")
 private Integer minIdle;
 
 @Value("${redis.pool.maxIdle}")
 private Integer maxIdle;
 
 @Value("${redis.pool.maxWaitMillis}")
 private Integer maxWaitMillis;
 
 @Value("${redis.url}")
 private String redisUrl;
 
 @Value("${redis.port}")
 private Integer redisPort;
 
 @Value("${redis.timeout}")
 private Integer redisTimeout;
 
 @Value("${redis.password}")
 private String redisPassword;
 
 @Value("${redis.db.payment}")
 private Integer paymentDataBase;
 
 private JedisPoolConfig jedisPoolConfig() {
  JedisPoolConfig config = new JedisPoolConfig();
  config.setMaxTotal(maxTotal);
  config.setMinIdle(minIdle);
  config.setMaxIdle(maxIdle);
  config.setMaxWaitMillis(maxWaitMillis);
  return config;
 }
 
 @Bean
 public JedisPool jedisPool() {
  JedisPoolConfig config = this.jedisPoolConfig();
  JedisPool jedisPool = new JedisPool(config, redisUrl, redisPort, redisTimeout, redisPassword);
  return jedisPool;
 }
 
 @Bean(name = "jedisConnectionFactory")
 public JedisConnectionFactory jedisConnectionFactory() {
  RedisStandaloneConfiguration redisStandaloneConfiguration = new RedisStandaloneConfiguration();
  redisStandaloneConfiguration.setDatabase(paymentDataBase);
  redisStandaloneConfiguration.setHostName(redisUrl);
  redisStandaloneConfiguration.setPassword(RedisPassword.of(redisPassword));
  redisStandaloneConfiguration.setPort(redisPort);

  return new JedisConnectionFactory(redisStandaloneConfiguration);
 }
}

②注册监听器

import org.springframework.data.redis.connection.Message;
import org.springframework.data.redis.connection.MessageListener;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

@Service(value ="paymentListener")
public class PaymentListener implements MessageListener {

 @Override
 @Transactional
 public void onMessage(Message message, byte[] pattern) {
  // 过期事件处理流程
 }
}

③配置订阅对象

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.autoconfigure.AutoConfigureAfter;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.data.redis.connection.jedis.JedisConnectionFactory;
import org.springframework.data.redis.listener.PatternTopic;
import org.springframework.data.redis.listener.RedisMessageListenerContainer;
import org.springframework.data.redis.listener.adapter.MessageListenerAdapter;

@Configuration
@AutoConfigureAfter(value = RedisConfig.class)
public class PaymentListenerConfig {
 
 @Autowired
 @Qualifier(value = "paymentListener")
 private PaymentListener paymentListener;
 
 @Autowired
 @Qualifier(value = "paymentListener")
 private JedisConnectionFactory connectionFactory;
 
 @Value("${redis.db.payment}")
 private Integer paymentDataBase;
 
 @Bean
 RedisMessageListenerContainer redisMessageListenerContainer(MessageListenerAdapter listenerAdapter) {
        RedisMessageListenerContainer container = new RedisMessageListenerContainer();
        container.setConnectionFactory(connectionFactory);
        // 监听paymentDataBase 库的过期事件
        String subscribeChannel = "__keyevent@" + paymentDataBase + "__:expired";
        container.addMessageListener(listenerAdapter, new PatternTopic(subscribeChannel));
        return container;
 }
 
 @Bean
    MessageListenerAdapter listenerAdapter() {
        return new MessageListenerAdapter(paymentListener);
    }
}

paymentDataBase 库元素过期后就会跳入PaymentListener 的onMessage(Message message, byte[] pattern)方法。

到此这篇关于Redis实现订单自动过期功能的示例代码的文章就介绍到这了,更多相关Redis 订单自动过期内容请搜索三水点靠木以前的文章或继续浏览下面的相关文章希望大家以后多多支持三水点靠木!

Redis 相关文章推荐
详解RedisTemplate下Redis分布式锁引发的系列问题
Apr 27 Redis
Redis源码阅读:Redis字符串SDS详解
Jul 15 Redis
嵌入式Redis服务器在Spring Boot测试中的使用教程
Jul 21 Redis
在项目中使用redis做缓存的一些思路
Sep 14 Redis
Springboot/Springcloud项目集成redis进行存取的过程解析
Dec 04 Redis
解决redis批量删除key值的问题
Mar 23 Redis
基于Redis6.2.6版本部署Redis Cluster集群的问题
Apr 01 Redis
Redis中key的过期删除策略和内存淘汰机制
Apr 12 Redis
Redis 限流器
May 15 Redis
解决 redis 无法远程连接
May 15 Redis
Redis 异步机制
May 15 Redis
Redis sentinel哨兵集群的实现步骤
Jul 15 Redis
redis 限制内存使用大小的实现
使用Redis实现秒杀功能的简单方法
Redis6.0搭建集群Redis-cluster的方法
May 08 #Redis
浅谈Redis存储数据类型及存取值方法
Redis IP地址的绑定的实现
May 08 #Redis
redis通过6379端口无法连接服务器(redis-server.exe闪退)
redis 查看所有的key方式
You might like
CentOS 6.2使用yum安装LAMP以及phpMyadmin详解
2013/06/17 PHP
PHP删除HTMl标签的实现代码
2013/06/30 PHP
php用ini_get获取php.ini里变量值的方法
2015/03/04 PHP
PHP判断用户是否已经登录(跳转到不同页面或者执行不同动作)
2016/09/22 PHP
PHP实现微信提现功能(微信商城)
2019/11/21 PHP
php生成随机数/生成随机字符串的方法小结【5种方法】
2020/05/27 PHP
通过代码实例解析PHP session工作原理
2020/12/11 PHP
在iframe里的页面编写js,实现在父窗口上创建动画效果展开和收缩的div(不变动iframe父窗口代码)
2011/12/20 Javascript
微信中一些常用的js方法汇总
2015/03/12 Javascript
包含中国城市的javascript对象实例
2015/08/03 Javascript
js实现简单折叠、展开菜单的方法
2015/08/28 Javascript
手机端转盘抽奖代码分享
2015/09/10 Javascript
JS实现淡蓝色简洁竖向Tab点击切换效果
2015/10/06 Javascript
js关于getImageData跨域问题的解决方法
2016/10/14 Javascript
利用JavaScript实现拖拽改变元素大小
2016/12/14 Javascript
js/jq仿window文件夹移动/剪切/复制等操作代码
2017/03/08 Javascript
JavaScript中数组常见操作技巧
2017/09/01 Javascript
node.js中TCP Socket多进程间的消息推送示例详解
2018/07/10 Javascript
从源码角度来回答keep-alive组件的缓存原理
2021/01/18 Javascript
Vue实现摇一摇功能(兼容ios13.3以上)
2021/01/26 Vue.js
Python 40行代码实现人脸识别功能
2017/04/02 Python
python中reader的next用法
2018/07/24 Python
Python动态生成多维数组的方法示例
2018/08/09 Python
下载官网python并安装的步骤详解
2019/10/12 Python
使用python把xmind转换成excel测试用例的实现代码
2020/10/12 Python
美国最大的购物网站:Amazon.com(亚马逊美国)
2020/05/23 全球购物
几个Shell Script面试题
2014/04/18 面试题
优秀的教师个人的中文求职信
2013/09/21 职场文书
运动会广播稿200字
2014/01/15 职场文书
员工培训邀请函
2014/02/02 职场文书
高中军训第一天感言
2014/03/06 职场文书
二年级学生评语大全
2014/04/23 职场文书
村干部四风问题整改措施
2014/09/30 职场文书
新闻人物通讯稿
2014/10/09 职场文书
销售内勤岗位职责范本
2015/04/13 职场文书
少先队中队工作总结
2015/08/14 职场文书