2015-06-28 22 views
1

我在我的应用程序中使用带有Dropwizard的JDBI。我已经使用dbi.open命令来获取DAO实例,然后使用它来运行各种查询。在“finally”块中,我使用dao.close()方法关闭连接。我还使用dao.inTransaction方法在单个事务中执行多个DB语句。JDBI:比使用dbi.open更适合使用dbi.onDemand吗?

虽然该应用程序已经工作了一段时间没有太多问题,但最近我们在Dev和Prod env中看到了“PoolExhausted”异常多次。我现在想知道是否使用dbi.onDemand比使用dbi.open更好,这样就可以避免每次最后都需要关闭......可能使用dbi.open是连接泄漏背后的原因?

回答

2

这取决于我们在打开和关闭连接之间所做的所有事情。

public interface UserDao { 
    @SqlQuery("select * from users") 
    public List<User> getUsers(); 

    @SqlUpdate(some query..) 
    public void insertUsers(someParam); 

} 

UserDao dao = dbi.onDemand(UserDao.class); 
dao.getUsers(); 

UserDao dao = dbi.open(UserDao.class); 
dao.getUsers(); 
dao.close(); 

这里获取连接和关闭连接没有区别。

UserDao dao = dbi.onDemand(UserDao.class); 
dao.getUsers(); 
// calling external service to get some value. 
dao.insertUsers(); 

UserDao dao = dbi.open(UserDao.class); 
dao.getUsers(); 
// calling external service to get some value. 
dao.insertUsers(); 
dao.close(); 

在此示例中,在onDemand方法中,连接在getUsers调用并在此之后关闭之前打开。 对于insertUsers也是如此。在外部服务呼叫期间,不保持连接。

在Dbi open方法中,连接在getUsers之前打开并在insertUsers之后关闭。在外部服务呼叫期间,连接也被保持。 如果这个外部通话费用很高,那么你最终会连接空闲很长时间,而不能用于其他通话。

所以最好使用onDemand来获取Dao实例。