Jedis错误 无法从池中获取资源

3

我目前在我的Maven Web应用程序中使用的是Jedis 2.9.0版本。它包含一个循环,每五分钟检索缓存数据。为此,在整个应用程序启动执行时,我在应用程序 Scheduler 类上创建了一个 JedisPool。它仅在应用程序启动时运行一次,然后再也不运行。

@WebListener
public class appScheduler implements ServletContextListener {

    private static JedisPool jedisPool;

    private ScheduledExecutorService scheduler;


    public void contextInitialized(ServletContextEvent event) {
        logger.info("contextInitialized: " + event);
        logger.info("Creating scheduler for cache updates...");
        boolean loadStatus  = PropertiesLoader.getInstance().load();
        if(!loadStatus){
            logger.error("Error loading properties");
            System.exit(1);
        }
        scheduler = Executors.newSingleThreadScheduledExecutor();
        scheduler.scheduleAtFixedRate(new UpdateCacheJob(), 1, 5, TimeUnit.MINUTES);

        int port = 6379;
        try {
            port = Integer.parseInt(PropertiesLoader.getInstance().getCachePort());
        } catch (NumberFormatException e) {
            logger.error("Invalid port in properties file for cache.");
        }
        jedisPool = new JedisPool(PropertiesLoader.getInstance().getPoolConfig(), PropertiesLoader.getInstance().getCacheEndpoint(), port);
    }

    public static Jedis getJedisResource() {
        return jedisPool.getResource();
    }
}

我的池配置:

      final JedisPoolConfig poolConfig = new JedisPoolConfig();
        poolConfig.setMaxTotal(128);
        poolConfig.setMaxIdle(128);
        poolConfig.setMinIdle(16);
        poolConfig.setTestOnBorrow(true);
        poolConfig.setTestOnReturn(true);
        poolConfig.setTestWhileIdle(true);
        poolConfig.setMinEvictableIdleTimeMillis(60000);
        poolConfig.setTimeBetweenEvictionRunsMillis(30000);
        poolConfig.setNumTestsPerEvictionRun(3);
        poolConfig.setBlockWhenExhausted(true);
        return poolConfig;

每隔五分钟,会创建一个管道以同步不同类别中缓存的新数据:
Jedis jedis = schedulerFunction.getJedisResource(); //retrieve resource from scheduler class

Pipeline pipeline = jedis.pipelined(); //create the pipeline

for (String key : list.keySet()) {
    pipeline.setex(key, 3600, data_to_fill_cache);
}
pipeline.sync(); //sync pipeline
logger.info("Cache synched... ");

很长时间内一切正常,但突然出现以下错误:

Could not get a resource from the pool

在5分钟的循环函数中获取资源以创建 jedis 的代码行上会出现此问题。它并不总是在相同的时间发生。它可能在两个小时或十个小时后发生,没有规律可循。该管道每五分钟遵循同样的过程,并将相同的数据写入 redis 中。这不是数据完整性或意外更改导致的问题。我排除了其他任何可能原因。在突然出现此错误之前,上下文已经被多次检索。

我已经查看了所有的互联网文档,但未能找到原因或解决方案。

1个回答

3

我认为你已经检索到了所有的资源,但是没有返回它们。

在使用完资源后,你需要将其返回。(如果你使用的是足够好的Jedis版本),你可以通过调用jedis.close();或使用try-with-resources来返回资源。


此外,我建议接受一个函数/可调用对象在try-with-resources块中运行,而不是返回Jedis实例并依赖于调用方正确关闭资源。 - justis

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接