C3P0 Statement.close死锁

时间:2013-05-10 15:19:38

标签: jdbc deadlock c3p0

谷歌在C3P0中返回了很多有死锁问题的人,但似乎没有一个解决方案适用(大多数人建议设置maxStatements = 0maxStatementsPerConnection = 0,我们都有。{/ p>


我使用的是来自C3P0的ComboPooledDataSource,初始化为;

cpds = new ComboPooledDataSource();
cpds.setDriverClass("org.postgresql.Driver");
cpds.setJdbcUrl("jdbc:postgresql://" + host + ":5432/" + database);
cpds.setUser(user);
cpds.setPassword(pass);

我的query函数看起来像;

public static List<Map<String, Object>> query(String q) {
    Connection c = null;
    Statement s = null;
    ResultSet r = null;
    try {
        c = cpds.getConnection();
        s = c.createStatement();
        s.executeQuery(q);
        r = s.getResultSet();
        /* parse result set into results List<Map> */
        return results;
    }
    catch(Exception e) { MyUtils.logException(e); }
    finally {
        closeQuietly(r);
        closeQuietly(s);
        closeQuietly(c);
    }
    return null;
}

尽管query()方法已到达return results;行,但仍未返回任何查询。问题是finally块正在挂起。我已经确定closeQuietly(s);是无限期悬挂的线。

有问题的closeQuietly()方法正如您所期望的那样;

public static void closeQuietly(Statement s) {
    try { if(s != null) s.close(); }
    catch(Exception e) { MyUtils.logException(e); }
}

为什么这种方法会挂在s.close()上?我想这与我使用C3P0的方式有关。


我可以在这里查看完整的C3P0配置(几乎完全默认) - &gt; http://pastebin.com/K8XDdiBg


MyUtils.logException();看起来像;

public static void logException(Exception e) {
    StackTraceElement ste[] = e.getStackTrace();
    String message = " !ERROR!: ";
    for(int i = 0; i < ste.length; i++) {
        if(ste[i].getClassName().contains("packagename")) {
            message += String.format("%s at %s:%d", e.toString(), ste[i].getFileName(), ste[i].getLineNumber());
            break;
        }
    }
    System.err.println(message);
}

如果删除closeQuietly(s);行,一切都会顺利进行。关闭ResultSetConnection对象的工作都没有问题 - 当然除了连接饥饿之外。

0 个答案:

没有答案