分布式锁
分布式锁redisson的简单使用
1)引入依赖
<dependency>
<groupId>org.redisson</groupId>
<artifactId>redisson</artifactId>
version>3.12.0</version>
</dependency>
2)将RedissonClient注入,并编写上锁代码
代码如下(示例):
@Autowired private RedissonClient redissonClient; @ResponseBody @GetMapping("/hello") public String hello(){ //1.获取一把锁,只要锁的名字一样,就是同一把锁 RLock lock = redissonClient.getLock("my-lock"); //2.加锁 lock.lock();//阻塞式等待。默认加的锁都是30s //lock.lock(10, TimeUnit.SECONDS);省掉了整个续期操作,手动解锁 try { System.out.println("加锁成功,执行业务"+ Thread.currentThread().getId()); Thread.sleep(30000); } catch (InterruptedException e) { e.printStackTrace(); } finally { System.out.println("释放锁..."+ Thread.currentThread().getId()); lock.unlock(); } return "hello"; }
3)测试结果
测试思路:本人使用的网关,将JMeter发送的请求发到网关上,然后将服务在不端口下启动,模拟部署在多台服务器上,当有一个正在执行的时候,其他服务只能等待该服务释放锁之后才可以执行,锁的相关数据可以到redis中去查看。
————————————————
版权声明:本文为CSDN博主「Zi昂昂昂昂昂」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/A1435900388/article/details/126194125
2.简单介绍一下redisson不同类型锁的使用
1)读写锁
@ResponseBody @GetMapping("/write") public String writeValue(){ RReadWriteLock lock = redissonClient.getReadWriteLock("rw-lock"); String s = null; RLock rLock = lock.writeLock(); try { //1.改数据加写锁 rLock.lock(); System.out.println("写锁枷锁成功。。。"+Thread.currentThread().getId()); s = UUID.randomUUID().toString(); Thread.sleep(30000); redisTemplate.opsForValue().set("writeValue",s); } catch (InterruptedException e) { e.printStackTrace(); }finally { rLock.unlock(); } return s; } @ResponseBody @GetMapping("/read") public String readValue(){ RReadWriteLock lock = redissonClient.getReadWriteLock("rw-lock"); String s = null; //加读锁 RLock rLock = lock.readLock(); rLock.lock(); System.out.println("读锁枷锁成功。。。"+Thread.currentThread().getId()); try { s = redisTemplate.opsForValue().get("writeValue"); Thread.sleep(30000); } catch (Exception e) { e.printStackTrace(); }finally { rLock.unlock(); } return s; }
2)信号量
代码如下(示例):
@GetMapping("/park") @ResponseBody public String park() throws InterruptedException { RSemaphore park = redissonClient.getSemaphore("park"); park.acquire();//获取一个信号,获取一个值,占一个位置 boolean b = park.tryAcquire(); if (b){ //执行业务 }else { return "error"; } return "ok"; } @GetMapping("/go") @ResponseBody public String go() throws InterruptedException { RSemaphore park = redissonClient.getSemaphore("park"); park.release();//释放一个信号,释放一个位置 return "ok"; }
3)闭锁
代码如下(示例):
@ResponseBody @GetMapping("/lockDoor") public String lockDoor() throws InterruptedException { RCountDownLatch door = redissonClient.getCountDownLatch("door"); door.trySetCount(5); door.await();//等待闭锁都完成 return "放假了"; } @ResponseBody @GetMapping("/gogogo/{id}") public String gogogo(@PathVariable Long id){ RCountDownLatch door = redissonClient.getCountDownLatch("door"); door.countDown();//计数减一 return id+"班的人都走了..."; }
闭锁为了方便理解我们可以举个例子,小明的学校要放假锁门了,学校一共有三个班级,只有当这三个班级都走了,才能锁门,所以执行lockDoor的时候,发现闭锁中还有三个班没有走完,每当gogogo执行一次,代表有一个班级走了,当三个班级都走完的时候我们的闭锁中值为0,lockDoor开始执行。