redis使用中的问题

来源:互联网 发布:学编程哪里好 编辑:程序博客网 时间:2024/06/14 01:20

1、 项目中redis配置的单节点的,用jedispool访问。在项目运行一段时间后报错java.net.SocketException: Broken pipe。大家都知道,如果一个socket连接已经被远端给close掉了,但是客户端没有察觉,仍然通过这个连接读写数据,那么就会产生Broken pipe异常。最后发现错误的原因是因为我们重启了redis服务,导致有些redis被redis服务关闭了,但jedis的connection pool没有发现,还往已经被close连接发送请求。防止这个问题有两种方式
a、采用jedispool 连接连接池

    JedisPool pool=new JedisPool("172.21.20.25",8000);    Jedis jedis = null;    try {       jedis = pool.getResource();       return jedis.get("key");    } catch (Exception e) {       e.printStackTrace();    } finally {       jedis.close();    }    return null;

手动关闭jedis连接。
b、采用redis的配置文件redis.config里面有timeou这个配置项:
# Close the connection after a client is idle for N seconds (0 to disable) timeout 0
即disable timeout,同时又去查看了下jedis common pool的设置,发现minEvictableIdleTimeMillis=1000L * 60L * 60L * 5L(ms),即一个redis连接的空闲时间超过5个小时才被connection pool给回收。很明显,就是因为客户端和服务端的connection idle time设置不一样,造成了connection被一端关闭了,但是另一端没有感知,所有造成了broken pipe。解决办法就是客户端的conectionidletime要小于服务端的timeout时间

2、如果采用jediscluster访问rediscluster集群就不会出现上述的问题,因为jediscluster在每个连接访问玩之后都会释放连接,会调用releaseConnection()方法


// release current connection before recursion or renewing
private void releaseConnection(Jedis connection) {
if (connection != null) {
connection.close();
}
}

0 0