(非maven項目,可到中央仓库下载http://mvnrepository.com)
org.springframework.boot
spring-boot-starter-data-redis
package com.jxnx.service;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Component;
import org.springframework.util.StringUtils;
/**
* Created by ledy
* 2018-02-22 19:05
*/
@Component
@Slf4j
public class RedisLock {
@Autowired
private StringRedisTemplate redisTemplate;
/**
* 加锁
* @param key
* @param value 当前时间+超时时间
* @return
*/
public boolean lock(String key, String value) {
if(redisTemplate.opsForValue().setIfAbsent(key, value)) {
return true;
}
//currentValue=A 这两个线程的value都是B 其中一个线程拿到锁
String currentValue = redisTemplate.opsForValue().get(key);
//如果锁过期(由于业务逻辑处理是死锁或其他异常,导致没有释放锁的处理逻辑)
if (!StringUtils.isEmpty(currentValue)
&& Long.parseLong(currentValue) < System.currentTimeMillis()) {
//获取上一个锁的时间
String oldValue = redisTemplate.opsForValue().getAndSet(key, value);
if (!StringUtils.isEmpty(oldValue) && oldValue.equals(currentValue)) {
return true;
}
}
return false;
}
/**
* 解锁
* @param key
* @param value
*/
public void unlock(String key, String value) {
try {
String currentValue = redisTemplate.opsForValue().get(key);
if (!StringUtils.isEmpty(currentValue) && currentValue.equals(value)) {
redisTemplate.opsForValue().getOperations().delete(key);
}
}catch (Exception e) {
log.error("【redis分布式锁】解锁异常, {}", e);
}
}
}
public static void main(String[] args) {
//key由实际业务传参
String key ="lockKey";
//加锁,超時时间设置为10秒,实际项目设置为常量
long time = System.currentTimeMillis() + 10*1000;
if(!redisLock.lock(key, String.valueOf(time))) {
throw new RuntimeException("哎哟喂,加锁失败了!");
}
/**
* 业务逻辑处理...
*/
//解锁
redisLock.unlock(key, String.valueOf(time));
}
如果觉得我的文章对您有用,请点赞。您的支持将鼓励我继续创作!
赞1
添加新评论0 条评论