2010-06-04 116 views
0

我有一个场景,问题如下Java JDBC连接和Oracle

应用程序服务器有两个到DB的连接池。 AB

A点 - >DatabaseA - >已128 connections

A已经存储了访问表驻留在DatabaseBDB link

B点用程序 - >DatabaseB - >具有36 connections

现在让我们说通过使用连接poo,Java代码调用DatabaseA中的Stored Proc l A。该存储过程是从DatabaseB

问题获取数据在DB链接:

基于这种方案如果我们在前端connection closed错误。是否可行的说,尽管java正在从池A(128)调用SP(在DatabaseA中),但由于SP正在从DatabaseB中提取数据,它的连接数量较少(36)。

基本上我想知道什么时候数据通过数据库链接,像这样...是否从分配给池B pointint的36个连接带到DatabaseB?

精确异常 精确例外,我得到的是:--- Cause: java.sql.SQLException: Closed Connection

一些堆栈跟踪:

产生的原因:java.sql.SQLException中:在 com.ibatis.sqlmap 关闭连接。 engine.mapping.statement.GeneralStatement.executeQueryWithCallback(GeneralStatement.java:185) at com.ibatis.sqlmap.engine.mapping.statement.GeneralStatement.executeQueryForList(GeneralStateme nt.java:123) 在 com.ibatis.sqlmap.engine.impl.SqlMapExecutorDelegate.queryForList(SqlMapExecutorDelegate.java:614) 在 com.ibatis.sqlmap.engine.impl.SqlMapExecutorDelegate.queryForList(SqlMapExecutorDelegate.java: 588) 在 com.ibatis.sqlmap.engine.impl.SqlMapSessionImpl.queryForList(SqlMapSessionImpl.java:118) 在 org.springframework.orm.ibatis.SqlMapClientTemplate $ 3.doInSqlMapClient(SqlMapClientTemplate.java:268) 在 org.springframework.orm.ibatis.SqlMapClientTemplate.execute(SqlMapClientTemplate.java:193) at org.springframework.orm.ibatis.SqlMapClientTemplate.executeWithListResult(SqlMapClientTemplate.java :219) 在 org.springframework.orm.ibatis.SqlMapClientTemplate.queryForList(SqlMapClientTemplate.java:266)

而且,我使用iBatis的...所以没有try..catch..finally

+1

它不应该。请更新您的问题以包含确切的异常和数据源配置。 – BalusC 2010-06-04 22:56:06

回答

0

这个异常表明资源泄漏,即JDBC代码没有正确地关闭finally块中的连接(以确保它即使在发生异常时也会关闭),或者连接已在多个线程之间共享。如果两个线程共享来自池的同一连接并且一个线程关闭它,那么当其他线程使用连接时会发生此异常。

应编写JDBC代码,以便在同一个方法块中获取并关闭(以相反顺序)连接(以及语句和结果集)。例如。

Connection connection = null; 
// ... 
try { 
    connection = database.getConnection(); 
    // ... 
} finally { 
    // ... 
    if (connection != null) try { connection.close(); } catch (SQLException logOrIgnore) {} 
} 

另一个可能的原因是池正在保持连接太长时间闲置,而不是在释放前测试/验证它们。这可以在一个体面的连接池中进行配置。请查阅其文档。

0

“基本上我想知道什么时候数据通过数据库链接传入,就像这样......是否从连接池B分配的36个连接带到DatabaseB?”

否。数据库服务器将与其他数据库服务器建立独立连接,而不考虑任何连接池。

我不得不忍受一段时间不活动后连接断开的防火墙,所以我发现这个错误非常多。查看dbms_session.close_database_link,因为数据库链接连接通常会在会话期间保持不变(因为您有连接池,该会话可能会持续很长时间)。

+0

我也有类似的东西。如果它们长时间运行(9秒),它会杀死会话,但这个杀手级作业只运行在数据库A中。当发生这种情况时,我实际上看到“您的会话已被杀害”而不是“关闭连接” – john 2010-06-05 04:18:33

+0

您是否建议在存储过程结束时,我应该有dbms_session.close_database_link?或者在我不使用数据库链接的表之后关闭数据库链接? – john 2010-06-05 04:22:20

+0

我建议你在我的存储过程中关闭数据库链接,在事务 – 2010-06-06 01:49:52

2

存储过程运行的数据库中;当它连接到另一个数据库时,它将建立直接连接,但不会通过应用程序服务器的池。实际上,它可以连接到链接到A的任何数据库,而不管是否有应用程序服务器维护的数据库的连接池。