zoukankan      html  css  js  c++  java
  • Redis 分布式锁 解决集群环境下多次定时任务执行

    1、设置分布式锁

        /**
         * 设置redis 分布式锁
         * @param lockName
         * @param acquireTimeout
         * @param lockTimeout
         * @return
         */
        public String acquireDistributedLockWithTimeout(String lockName, long acquireTimeout, int lockTimeout) {
            String lockValue = UUID.randomUUID().toString();
            String lockKey = "lock:" + lockName;
            long acquireTime = System.currentTimeMillis() + acquireTimeout;
            ValueOperations ops = this.redisTemplate.opsForValue();
    
            while(acquireTime > System.currentTimeMillis()) {
                boolean locked = ops.setIfAbsent(lockKey, lockValue);
                if (locked) {
                    this.redisTemplate.expire(lockKey, (long)lockTimeout, TimeUnit.SECONDS);
                    return lockValue;
                }
    
                try {
                    TimeUnit.MILLISECONDS.sleep(1L);
                } catch (InterruptedException var12) {
                    Thread.currentThread().interrupt();
                }
            }
    
            return null;
        }

    2、释放redis分布式锁

        /**
         * 释放redis锁
         * @param lockName
         * @param lockValue
         * @return
         */
        public boolean releaseDistributedLock(String lockName, String lockValue) {
            String lockKey = "lock:" + lockName;
            List<Object> result = null;
            ValueOperations ops = this.redisTemplate.opsForValue();
    
            do {
                this.redisTemplate.watch(lockKey);
                if (!Objects.equal(lockValue, ops.get(lockKey))) {
                    break;
                }
    
                this.redisTemplate.delete(lockKey);
            } while(result == null);
    
            this.redisTemplate.unwatch();
            return true;
        }

    3、定时逻辑

         //集群环境 定时任务加锁,保证执行一次 异常情况6个小时 释放锁
            String lock = redisService.acquireDistributedLockWithTimeout("incomeStatistics", 10, 60*60*6);
            //判断是否获得锁
            if(StringUtils.isNotBlank(lock)){
                logger.info("定时任务 开始执行");
                try{
                    //业务逻辑
                    
                    
                }catch (Exception e){
                   //异常处理
                }
                finally {
                    //释放锁
                    redisService.releaseDistributedLock("incomeStatistics",lock);
                }
            }
  • 相关阅读:
    Redis 字符串(String)
    Redis 哈希(Hash)
    Redis 键(key)
    Redis 命令
    Redis 数据类型
    Redis 配置
    Log4j 2X 日志文件路径问题
    shiro项目从 log4j1X 迁移到 log4j2X
    shiro+SpringMVC 项目 配置404页面
    邮件发送-》http://service.mail.qq.com/cgi-bin/help?subtype=1&&id=28&&no=1001256
  • 原文地址:https://www.cnblogs.com/yi1036943655/p/11512869.html
Copyright © 2011-2022 走看看