Spring整合Redis分布式锁
1.导包
<spring.boot.version>2.2.6.RELEASE</spring.boot.version>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-redis</artifactId>
<version>${spring.boot.version}</version>
</dependency>
<dependency>
<groupId>org.apache.commons</groupId>
<artifactId>commons-pool2</artifactId>
<version>2.6.2</version>
</dependency>
2.工具类
@Slf4j @Component public class RedisUtils { @Autowired private StringRedisTemplate redisTemplate; /** * 上锁 将键值对设定一个指定的时间timeout. * * @param key * @param timeout 键值对缓存的时间,单位是秒 * @return 设置成功返回true,否则返回false */ public boolean tryLock(String key, String value, long timeout) { //底层原理就是Redis的setnx方法 boolean isSuccess = redisTemplate.opsForValue().setIfAbsent(key, value); if (isSuccess) { //设置分布式锁的过期时间 redisTemplate.expire(key, timeout, TimeUnit.SECONDS); } return isSuccess; } public void del(String... key) { if (key != null && key.length > 0) { if (key.length == 1) { redisTemplate.delete(key[0]); } else { redisTemplate.delete(CollectionUtils.arrayToList(key)); } } } public Object get (String key) { if (key != null) { return redisTemplate.opsForValue().get(key); } return null; } }
3.使用
@Autowired
private StringRedisTemplate stringRedisTemplate;
@Autowired
RedisUtils redisUtils;
@Scheduled(cron = "*/5 * * ? * *") public void globalStatCache (){ //-------------上分布式锁开始----------------- InetAddress addr = null; try { addr = InetAddress.getLocalHost(); } catch (UnknownHostException e) { e.printStackTrace(); } //获取本机ip String ip = addr.getHostAddress(); //默认上锁时间为五小时 //此key存放的值为任务执行的ip, // redis_default_expire_time 不能设置为永久,避免死锁 boolean lock = redisUtils.tryLock(redisKey, ip, redis_default_expire_time); log.info("============定时任务开始=============="); if (lock) { //具体代码.........
stringRedisTemplate.opsForValue().set(key, JSON.toJSONString(xxx),2, TimeUnit.HOURS);
try { Thread.sleep(1000*60); } catch (InterruptedException e) { e.printStackTrace(); } redisUtils.del(redisKey); log.info("============本次定时任务结束=============="); //三个月 }else { log.info("============获得分布式锁失败======================="); ip = (String) redisUtils.get(redisKey); log.info("============{}机器上占用分布式锁,聚类任务正在执行=======================", ip); return; } }