分布式锁
分布式锁redisson的简单使用
1)引入依赖
<dependency>
<groupId>org.redisson</groupId>
<artifactId>redisson</artifactId>
version>3.12.0</version>
</dependency>
2)将RedissonClient注入,并编写上锁代码
代码如下(示例):
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 | @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)读写锁
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 | @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)信号量
代码如下(示例):
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 | @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)闭锁
代码如下(示例):
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 | @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开始执行。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 震惊!C++程序真的从main开始吗?99%的程序员都答错了
· 【硬核科普】Trae如何「偷看」你的代码?零基础破解AI编程运行原理
· 单元测试从入门到精通
· 上周热点回顾(3.3-3.9)
· winform 绘制太阳,地球,月球 运作规律
2017-08-17 Sqlserver时间函数用法(二)