Redis分布式锁之实战

本文主要介绍了如何在实际业务中应用Redis实现分布式锁,详细阐述了pom依赖配置、MyCacheCloudRedisFactory工具类的创建以及RedisUtil.java的使用方法,并提供了具体的使用示例。
摘要由CSDN通过智能技术生成

一、pom依赖

        <dependency>
            <groupId>tf56.redis</groupId>
            <artifactId>redis-client</artifactId>
            <version>1.0.0</version>
            <exclusions>
                <exclusion>
                    <artifactId>servlet-api</artifactId>
                    <groupId>javax.servlet</groupId>
                </exclusion>
                <exclusion>
                    <artifactId>gson</artifactId>
                    <groupId>com.google.code.gson</groupId>
                </exclusion>                
            </exclusions>
        </dependency>
<!-- 其他redis依赖 -->

二、MyCacheCloudRedisFactory工具类

 

package tf56.payOnlineService.util.redis;
​
import com.sohu.tv.builder.ClientBuilder;
import com.sohu.tv.cachecloud.client.basic.enums.RedisTypeEnum;
​
import org.apache.commons.lang.StringUtils;
import org.apache.commons.pool2.impl.GenericObjectPoolConfig;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
​
import redis.clients.jedis.Jedis;
import redis.clients.jedis.JedisSentinelPool;
import redis.clients.jedis.ScanParams;
import redis.clients.jedis.ScanResult;
import redis.clients.jedis.Transaction;
import tf56.common.redis.model.CommonConfigProp;
import tf56.common.util.PropUtil;
​
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.UUID;
​
/**
 * CacheCloud Redis 云工厂
 * Created by Trying on 2017/4/10 16:46.
 */
public class MyCacheCloudRedisFactory {
​
    protected static final Logger log = LoggerFactory.getLogger(MyCacheCloudRedisFactory.class);
​
    /** 默认资源文件路径 */
    public static final String DEFAULT_PROP_FILEPATH = "config/CacheCloud.properties";
​
    /** 默认失效时间,单位:秒 */
    private static final int DEFAULT_EXPIRE_SECOND = 60;
​
    /** Jedis sentinel 连接池 */
    JedisSentinelPool jedisSentinelPool = null;
    
    private static final Long RELEASE_SUCCESS = 1L;
    
    private static final String LOCK_SUCCESS = "OK";
​
​
    /**
     * 默认构造函数,会自动从默认配置文件 ["config/CacheCloud.properties"] 读取必要参数
     */
    public MyCacheCloudRedisFactory() throws Exception {
        this.initWithProp(null, null);
    }
​
    /**
     * 指定资源文件路径的构造函数。具体参数的key沿用默认的。
     * @param propFilepath 资源文件路径
     * @throws Exception 异常时,无法构造实例
     */
    public MyCacheCloudRedisFactory(String propFilepath) throws Exception {
        this.initWithProp(propFilepath, null);
    }
​
    /**
     * 使用默认的资源文件路径
     * @param configProp 资源文件配置
     * @throws Exception 异常时,无法构造实例
     */
    public MyCacheCloudRedisFactory(CommonConfigProp configProp) throws Exception {
        this.initWithProp(null, configProp);
    }
​
    /**
     * 指定资源文件路径、资源文件配置信息
     * @param propFilepath 资源文件路径
     * @param configProp 资源文件配置
     * @throws Exception 异常时,无法构造实例
     */
    public MyCacheCloudRedisFactory(String propFilepath, CommonConfigProp configProp) throws Exception {
        this.initWithProp(propFilepath, configProp);
    }
​
    /**
     * 个性化构造函数
     * @param redisTypeEnum Redis类型,非null
     * @param cacheCloudAppId CacheCloud应用中的appId,非null,大于0的long型数据
     */
    public MyCacheCloudRedisFactory(RedisTypeEnum redisTypeEnum, Long cacheCloudAppId, String appKey) throws Exception {
        this.init(redisTypeEnum, cacheCloudAppId, appKey, null);
    }
​
​
    private void initWithProp(String propFilepath, CommonConfigProp configProp) throws Exception {
        if (propFilepath==null || propFilepath.trim().length()==0) {
            propFilepath = DEFAULT_PROP_FILEPATH;
        }
​
        if (configProp==null) {
            configProp = new CommonConfigProp();
        }
​
        String redisTypeKey = configProp.concatPrefixAndSuffix(configProp.getRedisTypeKey());
        String redisType = PropUtil.getPropValue(propFilepath, redisTypeKey, null);
        String appIdKey = configProp.concatPrefixAndSuffix(configProp.getAppIdKey());
        String appIdStr = PropUtil.getPropValue(propFilepath, appIdKey, null);
        String appKeyKey = configProp.concatPrefixAndSuffix(configProp.getAppKeyKey());
        String appkeyStr = PropUtil.getPropValue(propFilepath, appKeyKey, null);
​
​
        RedisTypeEnum redisTypeEnum = null;
        long appId = 0;
        try {
            if (redisType==null || redisType.trim().length()==0) {
                redisTypeEnum = RedisTypeEnum.SENTINEL;
            } else {
                redisTypeEnum = RedisTypeEnum.valueOf(redisType);
            }
​
            appId = Long.parseLong(appIdStr);
        } catch (Exception e) {
            String msg = propFilepath + "{"+redisTypeKey + ":" + redisType + ", " + appIdKey + ":" + appIdStr + "}. \n";
            log.warn(msg + e.getMessage());
            throw new Exception(msg);
        }
​
        if (StringUtils.isBlank(appkeyStr)) {
            String msg = propFilepath + "{"+appKeyKey + ":" + appkeyStr +"}. \n Invalid param appKey !";
            log.warn(msg);
            throw new Exception(msg);
        }
​
​
        /* 连接池配置 */
        GenericObjectPoolConfig poolConfig = null;
        try {
            String minIdleKey = configProp.concatPrefixAndSuffix(configProp.getPoolMinIdleKey());
            String minIdleStr = PropUtil.getPropValue(propFilepath, minIdleKey, null);
            String maxIdleKey = configProp.concatPrefixAndSuffix(configProp.getPoolMaxIdleKey());
            String maxIdleStr = PropUtil.getPropValue(propFilepath, maxIdleKey, null);
            String maxTotalKey = configProp.concatPrefixAndSuffix(configProp.getPoolMaxTotalKey());
            String maxTotalStr = PropUtil.getPropValue(propFilepath, maxTotalKey, null);
​
            int minIdle = 0;
            int maxIdle = 0;
            int maxTotal = 0;
            if (minIdleStr != null)
                minIdle = Integer.parseInt(minIdleStr);
            if (maxIdleStr != null)
                maxIdle = Integer.parseInt(maxIdleStr);
            if (maxTotalStr != null)
                maxTotal = Integer.parseInt(maxTotalStr);
​
            poolConfig = new GenericObjectPoolConfig();
            if (minIdle>0) {
                poolConfig.setMinIdle(minIdle);
            }
            if (maxIdle>0 && maxIdle>minIdle) {
                poolConfig.setMaxIdle(maxIdle);
            }
            if (maxTotal>0) {
                poolConfig.setMaxTotal(maxTotal);
            }
        } catch (Exception e) {
            String msg = "Read pool config ERROR!";
            log.warn(msg, e);  // 连接池配置信息读取异常时,将只记录日志警告,并使用默认配置。而不抛异常。
        }
​
        this.init(redisTypeEnum, appId, appkeyStr, poolConfig);
    }
​
​
    /**
     * 初始化
     * @param redisTypeEnum Redis类型,非null
     * @param cacheCloudAppId CacheCloud应用中的appId,非null,大于0的long型数据
     */
    private void init(RedisTypeEnum redisTypeEnum, Long cacheCloudAppId, String appKey, GenericObjectPoolConfig poolConfig) throws Exception {
        if (redisTypeEnum==null || (cacheCloudAppId==null || cacheCloudAppId<=0)) {
            Strin
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值