博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
redis setnx解决定时任务多节点部署并发问题(分布式锁)
阅读量:2065 次
发布时间:2019-04-29

本文共 1915 字,大约阅读时间需要 6 分钟。

在一些大的互联网平台,通常都会使用定时任务处理一些周期性的业务,而为了保障系统的高可用性,定时任务也会多节点部署,而解决多节点并发问题(分布式锁),大家通常会想到使用缓存,如redis,但是如果使用set / get是无法解决问题的,同样会出现并发问题,redis有专门的解决分布式并发问题的方法,就是setnx命令,很好用,下面介绍一下java实现redis分布式锁的方法。

1. Redis SETNX命令语法:

SETNX 是『SET if Not eXists』(如果不存在,则 SET)的简写,其操作为:将 key 的值设为 value ,当且仅当 key 不存在。若给定的 key 已经存在,则 SETNX 不做任何动作。

返回值:
  设置成功,返回 1 。
  设置失败,返回 0 。

 SetNX 不具备设置过期时间的功能,所以我们需要借助  来设置,否则可能会出现死锁问题。

2. 环境说明

是基于 spring boot的项目,这是一个项目中多节点定时扣费任务的实现。

3. 配置实现

3.1. 定时任务

@Component@EnableSchedulingpublic class QuartzCharge {	Logger logger = LogManager.getLogger("quartzCharge");	@Autowired	RedisComponent redisComponent;			 //每每小时0分0秒执行一次     @Scheduled(cron = "0 0 * * * *")	 public void quartzCharge(){		 //需要先查询redis的计费标记,如果有,就不计费,如果没有就计费,整点计费		 logger.info(" 定时计费开始: ");		 //redis分布式锁,尽量要设置过期时间,防止死锁		 if(!redisComponent.setNX("quartzChargeTag", "1", 10, TimeUnit.SECONDS)){			 logger.info("已有执行中定时扣费任务,本次不执行!");			 return;		 }		 		 //计费		 try{			 //to_do 定时业务实现             		 }catch(Exception e){			 logger.error("定时扣费异常结束: " + e);		 }finally{			//任务执行完,一定要清空缓存,防止意外终止死锁			 redisComponent.del("quartzChargeTag");		 }		 		 logger.info("定时计费结束!");	 }}

3.2.redis操作工具类

@Componentpublic class RedisComponent {	@Autowired	//操作字符串的template,StringRedisTemplate是RedisTemplate的一个子集	private StringRedisTemplate stringRedisTemplate;	@Autowired	// RedisTemplate,可以进行所有的操作  	private RedisTemplate
redisTemplate; /* * redis分布式锁实现,同时利用expire设置过期时间 * 返回true就是设置成功 * */ public Boolean setNX(String key, String value,long timeout, TimeUnit unit){ Boolean isExit = this.redisTemplate.getConnectionFactory().getConnection().setNX(key.getBytes(), value.getBytes()); //如果设置成功,要设置其过期时间 if(isExit){ redisTemplate.expire(key, timeout, unit); } return isExit; } }

3.3 双节点执行效果

节点一日志:

节点二日志:

 

看两个节点的日志,可以清楚的看到,两个节点相互执行定时任务,执行时间就在毫厘之间,谁快谁就抢到锁,一个节点挂了还有另外一个,这样就保障了系统的高可用,是不是挺酸爽的,O(∩_∩)O哈哈~

----------over--------------

 

转载地址:http://gcwmf.baihongyu.com/

你可能感兴趣的文章
Leetcode C++《热题 Hot 100-29》22.括号生成
查看>>
Leetcode C++《热题 Hot 100-40》64.最小路径和
查看>>
Leetcode C++《热题 Hot 100-41》75.颜色分类
查看>>
Leetcode C++《热题 Hot 100-42》78.子集
查看>>
Leetcode C++《热题 Hot 100-43》94.二叉树的中序遍历
查看>>
Leetcode C++ 《第175场周赛-1 》5332.检查整数及其两倍数是否存在
查看>>
Leetcode C++ 《第175场周赛-2 》5333.制造字母异位词的最小步骤数
查看>>
Leetcode C++ 《第175场周赛-3》1348. 推文计数
查看>>
Leetcode C++《热题 Hot 100-44》102.二叉树的层次遍历
查看>>
Leetcode C++《热题 Hot 100-45》338.比特位计数
查看>>
读书摘要系列之《kubernetes权威指南·第四版》第一章:kubernetes入门
查看>>
Leetcode C++《热题 Hot 100-46》739.每日温度
查看>>
Leetcode C++《热题 Hot 100-47》236.二叉树的最近公共祖先
查看>>
Leetcode C++《热题 Hot 100-48》406.根据身高重建队列
查看>>
《kubernetes权威指南·第四版》第二章:kubernetes安装配置指南
查看>>
Leetcode C++《热题 Hot 100-49》399.除法求值
查看>>
Leetcode C++《热题 Hot 100-51》152. 乘积最大子序列
查看>>
[Kick Start 2020] Round A 1.Allocation
查看>>
[Kick Start 2020] Round A 2.Plates
查看>>
Leetcode C++ 《第181场周赛-1》 5364. 按既定顺序创建目标数组
查看>>