打开APP
userphoto
未登录

开通VIP,畅享免费电子书等14项超值服

开通VIP
Spring+Redis(keyspace notification)实现定时任务(订单过期自动关闭)

1.起因

最近公司项目要做订单超期未支付需自动关闭,首先想到的是用spring的定时器(@Schedule),结果领导举各种例子说会影响性能,只能作罢。后来想能不能基于redis实现,学习(baidu)之后,大概就是使用redis的Keyspace Notifications,大概就是利用该机制可以在key失效之后,提供一个回调,实际上是redis会给客户端发送一个消息。是需要redis版本2.8以上,conf配置需设置notify-keyspace-events Ex,请示领导之后也得到了同意。

2.整合实现

大致思路就是让spring做客户端订阅'__keyevent@0__:expired'频道就可以了。在这里给出两种实现方式。

1.利用MessageListenerAdapter,spring本身已经提供了的实现方式。

首先自定义一个MessageDelegate 接口并实现

 1 public interface MyMessageDelegate { 2   void handleMessage(String message); 3   void handleMessage(Map message); void handleMessage(byte[] message); 4   void handleMessage(Serializable message); 5   // pass the channel/pattern as well 6   void handleMessage(Serializable message, String channel); 7  } 8  9 public class MyRedisKeyExpiredMessageDelegate implements MessageDelegate {10   // implementation elided for clarity...11 }

xml增加相关配置

     <bean id="messageListener"          class="org.springframework.data.redis.listener.adapter.MessageListenerAdapter">        <constructor-arg>            <bean class="com.xxx.MyRedisKeyExpiredMessageDelegate" />        </constructor-arg>    </bean>    <bean id="redisContainer" class="org.springframework.data.redis.listener.RedisMessageListenerContainer">        <property name="connectionFactory" ref="connectionFactory" />        <property name="messageListeners">            <map>                <entry key-ref="messageListener">                    <list>                        <bean class="org.springframework.data.redis.listener.ChannelTopic">                            <constructor-arg value="__keyevent@0__:expired" />                        </bean>                    </list>                </entry>            </map>        </property>    </bean>    

具体可参考官方文档:http://docs.spring.io/spring-data/redis/docs/1.7.8.RELEASE/reference/html/#redis:pubsub:subscribe

2.即自定义一个OrderPubSub类继承自JedisPubSub,然后在spring启动的时候就订阅这个OrderPubSub。

 1 public class OrderSubscribe extends JedisPubSub { 2      3     public void onPSubscribe(String pattern, int subscribedChannels) {    4          5     }   6        7     public void onPMessage(String pattern, String channel, String message) {     8             if ("__keyevent@0__:expired".equals(channel)) { 9                 //do some thing10             }11     }12 }13 14 public class RedisInitSubscrib implements InitializingBean{  15     16     JedisPool pool;17 18     @Override19     public void afterPropertiesSet() throws Exception {20         pool.getResource().psubscribe(new OrderSubscribe(), "*");21         22     }23     24 } 

当key失效后,收到消息的内容(即方法中的message参数)就是key的值,这样就可以做自定义的操作了。

3.后记

欢迎大家留言交流,关于订单自动关闭如果有更好的方式,还望不吝赐教,O(∩_∩)O谢谢。

 

 

 

 

 

Keyspace Notifications

本站仅提供存储服务,所有内容均由用户发布,如发现有害或侵权内容,请点击举报
打开APP,阅读全文并永久保存 查看更多类似文章
猜你喜欢
类似文章
【热】打开小程序,算一算2024你的财运
使用Spring Data Redis操作Redis(二)
使用Spring Data Redis操作Redis(一)
redis队列定时任务 使用redis的Keyspace Notifications实现定时任务队列
Spring-data-redis:特性与实例
SpringBoot缓存技术
使用Spring
更多类似文章 >>
生活服务
热点新闻
分享 收藏 导长图 关注 下载文章
绑定账号成功
后续可登录账号畅享VIP特权!
如果VIP功能使用有故障,
可点击这里联系客服!

联系客服