彻底解决 Jedis 连接池 获取不到连接,连接放回连接池错误的问题

public class CacheKit {
    private static Logger logger = LoggerFactory.getLogger(CacheKit.class);
    private List<JSONObject> resultList;
    private static JedisPool pool;

    /**
     * 初始化Redis连接池
     */
    private static void initializePool() {
		//redisURL 与 redisPort 的配置文件
        String configFile = "production.properties";
        if (PropKit.getBoolean("devMode")) {
            configFile = "dev.properties";
        }

        JedisPoolConfig config = new JedisPoolConfig();
		//设置最大连接数(100个足够用了,没必要设置太大)
		config.setMaxTotal(100);
		//最大空闲连接数
		config.setMaxIdle(10);
		//获取Jedis连接的最大等待时间(50秒) 
		config.setMaxWaitMillis(50 * 1000);
		//在获取Jedis连接时,自动检验连接是否可用
		config.setTestOnBorrow(true);
		//在将连接放回池中前,自动检验连接是否有效
		config.setTestOnReturn(true);
		//自动测试池中的空闲连接是否都是可用连接
		config.setTestWhileIdle(true);
		//创建连接池
		pool = new JedisPool(config, PropKit.use(configFile).get("redisURL"),
					PropKit.use(configFile).getInt("redisPort"));
    }

    /**
     * 多线程环境同步初始化(保证项目中有且仅有一个连接池)
     */
    private static synchronized void poolInit() {
        if (null == pool) {
            initializePool();
        }
    }

    /**
     * 获取Jedis实例
     */
    private static Jedis getJedis() {
        if (null == pool) {
            poolInit();
        }

        int timeoutCount = 0;
        while (true) {
            try {
                if (null != pool) {
                    return pool.getResource();
                }
            } catch (Exception e) {
                if (e instanceof JedisConnectionException) {
                    timeoutCount++;
                    logger.warn("getJedis timeoutCount={}", timeoutCount);
                    if (timeoutCount > 3) {
                        break;
                    }
                } else {
                    logger.warn("jedisInfo ... NumActive=" + pool.getNumActive()
                            + ", NumIdle=" + pool.getNumIdle()
                            + ", NumWaiters=" + pool.getNumWaiters()
                            + ", isClosed=" + pool.isClosed());
                    logger.error("GetJedis error,", e);
                    break;
                }
            }
            break;
        }
        return null;
    }

    /**
     * 释放Jedis资源
     *
     * @param jedis
     */
    public static void returnResource(Jedis jedis) {
        if (null != jedis) {
            pool.returnResourceObject(jedis);
        }
    }

    /**
     * 绝对获取方法(保证一定能够使用可用的连接获取到 目标数据)
     * Jedis连接使用后放回 
     * @param key
     * @return
     */
    private String safeGet(String key) {
        Jedis jedis = getJedis();
        while (true) {
            if (null != jedis) {
                break;
            } else {
                jedis = getJedis();
            }
        }
        String value = jedis.get(key);
        returnResource(jedis);
        return value;
    }

    /**
     * 绝对设置方法(保证一定能够使用可用的链接设置 数据)
     * Jedis连接使用后返回连接池
     * @param key
     * @param time
     * @param value
     */
    private void safeSet(String key, int time, String value) {
        Jedis jedis = getJedis();
        while (true) {
            if (null != jedis) {
                break;
            } else {
                jedis = getJedis();
            }
        }
        jedis.setex(key, time, value);
        returnResource(jedis);
    }

    /**
     * 绝对删除方法(保证删除绝对有效)
     * Jedis连接使用后返回连接池</span>
     * @param key
     */
    private void safeDel(String key) {
        Jedis jedis = getJedis();
        while (true) {
            if (null != jedis) {
                break;
            } else {
                jedis = getJedis();
            }
        }
        jedis.del(key);
        returnResource(jedis);
    }

    /**自定义的一些 get set del 方法,方便使用**/
    public JSONObject getByCache(String key) {
        String result = safeGet(key);
        if (result != null) {
            return (JSONObject) JSONObject.parse(result);
        }
        return null;

    }

    public String getByCacheToString(String key) {
        String result = safeGet(key);
        if (result != null) {
            return result;
        }
        return null;

    }

    public List<JSONObject> getArrayByCache(String key) {
        String result = safeGet(key);
        if (result != null) {
            resultList = JSONArray.parseArray(result, JSONObject.class);
            return resultList;
        }
        return null;
    }

    public JSONArray getJSONArrayByCache(String key) {
        String result = safeGet(key);
        if (result != null) {
            return JSONArray.parseArray(result);
        }
        return null;
    }

    public void setByCache(String key, String s) {
        safeSet(key, 86400, s);
    }

    public void setByCacheOneHour(String key, String s) {
        safeSet(key, 3600, s);
    }

    public void setByCacheOneHour(String key, List<JSONObject> json) {
        safeSet(key, 86400, JSONObject.toJSONString(json));
        resultList = json;
    }

    public void setByCache(String key, JSONObject json) {
        safeSet(key, 86400, JSONObject.toJSONString(json));
    }

    public void setByCache(String key, List<JSONObject> list) {
        safeSet(key, 86400, JSONObject.toJSONString(list));
        resultList = list;
    }

    public void setByCache(String key, JSONArray array) {
        safeSet(key, 86400, JSONArray.toJSONString(array));
    }

    public void setByCacheCusTime(String key, String s, int time) {
        safeSet(key, time, s);
    }


    public void delByCache(String key) {
        if (null != safeGet(key)) {
            safeDel(key);
        }
    }

    public JSONObject toJSON(DBObject db) {
        return (JSONObject) JSONObject.toJSON(db);
    }

    public List<JSONObject> toJSON(List<DBObject> list) {
        List<JSONObject> json = new ArrayList<>();
        for (DBObject aList : list) {
            json.add((JSONObject) JSONObject.toJSON(aList));
        }
        return json;
    }

    public boolean notNull() {
        return resultList != null && resultList.size() > 0;
    }

    public List<JSONObject> getResult() {
        return resultList;
    }

}


  • 8
    点赞
  • 19
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值