zoukankan      html  css  js  c++  java
  • Redis分布式锁之redisson

    Redis分布式锁之redisson

    常用的redis解决方案:

    [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-pHt6m1O6-1601000482896)(C:\Users\VIolet\AppData\Roaming\Typora\typora-user-images\image-20200925095652120.png)]

    redisson官网,官方讲解可以点击这里

    redisson实现分布式锁原理:
    • 线程首先会尝试获取锁,如果获取锁成功,会执行加锁操作并执行业务代码,如果没有成功会使用自旋锁方式不断尝试获取锁
    • redisson为防止死锁方式默认加锁时间为30s,看门狗过30秒查看是否依然持有锁,如果持有会延长时间,当业务执行完毕释放锁

    [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-c9VoOX50-1601000482899)(C:\Users\VIolet\AppData\Roaming\Typora\typora-user-images\image-20200925095835130.png)]

    1.maven依赖
     <dependency>
                <groupId>org.redisson</groupId>
                <artifactId>redisson</artifactId>
                <version>3.8.0</version>
            </dependency>
    2.spring注入客户端
    package com.violet.sys.configuration;
    
    
    import org.redisson.Redisson;
    import org.redisson.api.RedissonClient;
    import org.redisson.config.Config;
    import org.springframework.beans.factory.annotation.Value;
    import org.springframework.context.annotation.Bean;
    import org.springframework.context.annotation.Configuration;
    
    /**
     * @Description //TODO
     * @Date 2020/3/19 22:32
     * @Author huangwb
     **/
    @Configuration
    public class RedissonAutoConfiguration {
     
        @Value("${redisson.addres}")
        private String addressUrl;
        @Value("${redisson.password}")
        private String password;
     
        /**
         * @return org.redisson.api.RedissonClient
         * @Author huangwb
         * @Description //TODO 单机模式配置
         * @Date 2020/3/19 22:54
         * @Param []
         **/
        @Bean
        public RedissonClient getRedisson() {
            Config config = new Config();
            config.useSingleServer()
                    .setAddress(addressUrl).setPassword(password)
                    .setRetryInterval(50000)
                    .setTimeout(100000)
                    .setConnectTimeout(100000);
            return Redisson.create(config);
        }
    }
    3对应的yml配置
    redisson:
      addres: redis://127.0.0.1:6379
      password:  你的reids密码 
    4.业务逻辑代码
    4.1看门狗自动检测锁

    这样的代码会出现一个看门狗,它的作用是在Redisson实例被关闭前,不断的延长锁的有效期,没过10s检测一遍,通过config.setLockWatchdogTimeout(“时间”)可以设置超时时间

    package com.violet.sys.controller;
    
    import com.github.xiaoymin.knife4j.annotations.ApiOperationSupport;
    import io.swagger.annotations.Api;
    import io.swagger.annotations.ApiOperation;
    import org.redisson.api.RLock;
    import org.redisson.api.RedissonClient;
    import org.slf4j.Logger;
    import org.slf4j.LoggerFactory;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.web.bind.annotation.PostMapping;
    import org.springframework.web.bind.annotation.RequestMapping;
    import org.springframework.web.bind.annotation.RequestMethod;
    import org.springframework.web.bind.annotation.RestController;
    
    /**
     * TODO(描述)
     *
     * @author violet
     * @Title ReidsLock
     * @Description:
     * @date 2020/7/8 15:17
     */
    @RestController
    @Api(tags={"分布式锁"})
    public class ReidsLock {
        private Logger logger = LoggerFactory.getLogger(ReidsLock.class);
        @Autowired
        RedissonClient redissonClient;
    
        @RequestMapping(value = "redislock", method = RequestMethod.POST)
        @ApiOperation(value = "测试分布式锁", notes = "接口描述", httpMethod = "POST")
        @ApiOperationSupport(author = "violet")
        public void redislock(){
            //你锁的id
            String key = "dec_store_lock" ;
            //1、获取一把锁,只要锁的名字一样,就是同一把锁
            RLock lock = redissonClient.getLock(key);
            lock.lock();
            int i =0;
            logger.info(i+":  获取锁");
            try {
                logger.info(i+":  打印锁");
                logger.info(String.valueOf(i));
                i++;
            } catch (Exception e) {
                System.out.println(e.getMessage());
            } finally {
            //解锁
                lock.unlock();
            }
        }
    }
    4.2 自行设置锁超时时间
    // 加锁以后10秒钟自动解锁,不会续期
    // 无需调用unlock方法手动解锁
    //10秒自动解锁,自动解锁时间一定要大于业务的执行时间。
    lock.lock(10, TimeUnit.SECONDS);
    
    // 尝试加锁,最多等待100秒,超出不等,上锁以后10秒自动解锁
    boolean res = lock.tryLock(100, 10, TimeUnit.SECONDS);
    if (res) {
       try {
         ...
       } finally {
           lock.unlock();
       }
    }
    4.3设置公平锁
    RLock fairLock = redisson.getFairLock("dec_store_lock");
    // 最常见的使用方法
    fairLock.lock();
    
    // 10秒钟以后自动解锁
    // 无需调用unlock方法手动解锁
    fairLock.lock(10, TimeUnit.SECONDS);
    
    // 尝试加锁,最多等待100秒,上锁以后10秒自动解锁
    boolean res = fairLock.tryLock(100, 10, TimeUnit.SECONDS);
    ...
    fairLock.unlock();
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12

    ``
    接下来就可以用jmeter压测了,我这里就不贴图了

     
     
  • 相关阅读:
    Ubuntu 更换软件源
    Ubuntu 配置 SOCKS5
    Ubuntu 配置 Sha-dow-socks
    frp(内网穿透)
    solr 远程代码执行(CVE-2019-12409)
    多线程处理爬虫
    python实现文件自动排序
    python 实现根据文件名自动分类移动至不同的文件夹
    Centos7如何开启任意端口服务
    centos7默认安装没有连接网络
  • 原文地址:https://www.cnblogs.com/javalinux/p/14265383.html
Copyright © 2011-2022 走看看