赞
踩
看门线程: 用于给当前key延长时间,保证也是线程的正常执行的过程中,锁不会过期
基于Redis+看门狗机制的分布式锁框架
Redisson在基于NIO的Netty框架上,充分的利⽤了Redis键值数据库提供的⼀系列优势,在Java实⽤⼯具包中常⽤接⼝的基础上,为使⽤者提供了⼀系列具有分布式特性的常⽤⼯具类。使得原本作为协调单机多线程并发程序的⼯具包获得了协调分布式多机多线程并发系统的能⼒,⼤⼤降低了设计和研发⼤规模分布式系统的难度。同时结合各富特⾊的分布式服务,更进⼀步简化了分布式环境中程序相互之间的协作
添加依赖
<dependency>
<groupId>org.redisson</groupId>
<artifactId>redisson</artifactId>
<version>3.12.0</version>
</dependency>
配置yml
redisson:
addr:
singleAddr:
host: redis://ajie.jimo.fun:6379
password: 12345
database: 0
配置RedissonClient
@Configuration public class RedissonConfig { @Value("${redisson.addr.singleAddr.host}") private String host; @Value("${redisson.addr.singleAddr.password}") private String password; @Value("${redisson.addr.singleAddr.database}") private int database; @Bean public RedissonClient redissonClient() { Config config = new Config(); config.useSingleServer().setAddress(host).setPassword(password).setDatabase(database); return Redisson.create(config); } }
在秒杀业务实现中注⼊RedissonClient对象
@Autowired
private RedissonClient redissonClient;
Redisson的工作原理图
application.yml
redisson:
addr:
cluster:
hosts: redis://47.96.11.185:6370,...,redis://47.96.11.185:6373
password: 12345678
RedissonConfig——RedissonClient对象
@Configuration public class RedissonConfig { @Value("${redisson.addr.cluster.hosts}") private String hosts; @Value("${redisson.addr.cluster.password}") private String password; /** * 集群模式 * @return */ @Bean public RedissonClient redissonClient(){ Config config = new Config(); config.useClusterServers().addNodeAddress(hosts.split("[,]")) .setPassword(password) .setScanInterval(2000) .setMasterConnectionPoolSize(10000) .setSlaveConnectionPoolSize(10000); return Redisson.create(config); } }
application.yml
redisson:
addr:
masterAndSlave:
masterhost: redis://47.96.11.185:6370
slavehosts: redis://47.96.11.185:6371,redis://47.96.11.185:6372
password: 12345678
database: 0
RedissonConfig——RedissonClient对象
@Configuration public class RedissonConfig3 { @Value("${redisson.addr.masterAndSlave.masterhost}") private String masterhost; @Value("${redisson.addr.masterAndSlave.slavehosts}") private String slavehosts; @Value("${redisson.addr.masterAndSlave.password}") private String password; @Value("${redisson.addr.masterAndSlave.database}") private int database; /** * 主从模式 * @return */ @Bean public RedissonClient redissonClient(){ Config config = new Config(); config.useMasterSlaveServers() .setMasterAddress(masterhost) .addSlaveAddress(slavehosts.split("[,]")) .setPassword(password) .setDatabase(database) .setMasterConnectionPoolSize(10000) .setSlaveConnectionPoolSize(10000); return Redisson.create(config); } }
1、互斥性
和我们本地锁⼀样互斥性是最基本,但是分布式锁需要保证在不同节点的不同线程的互斥。
2、可重⼊性
同⼀个节点上的同⼀个线程如果获取了锁之后那么也可以再次获取这个锁。
3、锁超时
和本地锁⼀样⽀持锁超时,加锁成功之后设置超时时间,以防⽌线程故障导致不释放锁,防
⽌死锁。
4、⾼效,⾼可⽤
加锁和解锁需要⾼效,同时也需要保证⾼可⽤防⽌分布式锁失效,可以增加降级。redission是基于redis的,redis的故障就会导致redission锁的故障,因此redission⽀持单节点redis、reids主从、reids集群
5、⽀持阻塞和⾮阻塞
和 ReentrantLock ⼀样⽀持 lock 和 trylock 以及 tryLock(long timeOut)。
1、乐观锁与悲观锁
2、可重⼊锁和⾮可重⼊锁
3、公平锁和⾮公平锁
4、阻塞锁和⾮阻塞锁
1、获取锁——公平锁和⾮公平锁
//获取公平锁
RLock lock = redissonClient.getFairLock(skuId);
//获取⾮公平锁
RLock lock = redissonClient.getLock(skuId);
2、加锁——阻塞锁和⾮阻塞锁
//阻塞锁(如果加锁成功之后,超时时间为30s;加锁成功开启看⻔狗,剩5s延⻓过期时间)
lock.lock();
//阻塞锁(如果加锁成功之后,设置⾃定义20s的超时时间)
lock.lock(20,TimeUnit.SECONDS);
//⾮阻塞锁(设置等待时间为3s;如果加锁成功默认超时间为30s)
boolean b = lock.tryLock(3,TimeUnit.SECONDS);
//⾮阻塞锁(设置等待时间为3s;如果加锁成功设置⾃定义超时间为20s)
boolean b = lock.tryLock(3,20,TimeUnit.SECONDS);
3、释放锁
lock.unlock();
4、应⽤示例
//公平⾮阻塞锁
RLock lock = redissonClient.getFairLock(skuId);
boolean b = lock.tryLock(3,20,TimeUnit.SECONDS);
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。