我一直在为我的 java 应用程序做大量工作以提高数据库连接稳定性等。有一个问题仍然困扰着用户,这似乎很常见,是我的代码而不是他们的数据库服务器的问题。
我们正在使用 jdbc-pool。
错误:
Database connection error: Connection has already been closed.
java.sql.SQLException: Connection has already been closed.
at org.apache.tomcat.jdbc.pool.ProxyConnection.invoke(ProxyConnection.java:118)
at $Proxy12.commit(Unknown Source)
at me.botsko.prism.actionlibs.ActionRecorder.insertActionsIntoDatabase(ActionRecorder.java:201)
at me.botsko.prism.actionlibs.ActionRecorder.save(ActionRecorder.java:81)
at me.botsko.prism.actionlibs.ActionRecorder.run(ActionRecorder.java:230)
at org.bukkit.craftbukkit.v1_5_R2.scheduler.CraftTask.run(CraftTask.java:53)
at org.bukkit.craftbukkit.v1_5_R2.scheduler.CraftAsyncTask.run(CraftAsyncTask.java:53)
at java.util.concurrent.ThreadPoolExecutor.runWorker(Unknown Source)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(Unknown Source)
at java.lang.Thread.run(Unknown Source)
它涉及的代码:
public void insertActionsIntoDatabase() {
PreparedStatement s = null;
Connection conn = null;
try {
if( !queue.isEmpty() ){
conn = Prism.dbc();
if(conn == null || conn.isClosed()){
// try to re-open conn
return;
}
conn.setAutoCommit(false);
s = conn.prepareStatement("QUERY HERE");
while (!queue.isEmpty()){
s.executeBatch(); // Execute every x items.
}
s.executeBatch();
conn.commit();
}
} catch (SQLException e){
plugin.handleDatabaseException( e );
} finally {
if(s != null) try { s.close(); } catch (SQLException e) {}
if(conn != null) try { conn.close(); } catch (SQLException e) {}
}
}
我长期以来一直检查连接是否关闭,但不知何故有些东西跳过了。此代码每次运行时都会抓取一个新的池连接,因此它不使用应用程序其他部分使用的连接。