2012-09-04 72 views
2

我正在使用Groovy的Sql对象在postgres数据库上执行查询。如下查询正被执行:Groovy SQL错误 - 此ResultSet已关闭

List<Map> results = sql.rows("select * from my_table") 
List<Map> result2= sql.rows("select * from my_second_table") 

我有执行两个查询,然后进行一些处理来遍历数据,以使不同的数据集常规方法,但是,在某些情况下我收到一个postgres例外"This ResultSet is closed"错误。我原本以为这可能与这里的问题有关:SQLException: This ResultSet is closed(运行多个查询并尝试从事后访问结果集中的数据) - 但是,我们似乎只是在相当程度上获得了异常高负载 - 这表明它不像第一个数据集在执行第二个查询时关闭那样简单,就好像这是我期望的一样发生的情况。

任何人都可以阐明Groovy的Sql对象如何处理这些情况或提出可能出错的建议吗?

回答

3

Groovy SQL是一种奇怪的猫。易于使用的简单的东西。如果你有更复杂的情况,你可能会更好地使用别的东西。恕我直言

我首先建议做一个查询,将结果存储到集合中,执行第二个查询并将结果存储在集合中,然后在两个集合之间而不是结果集之间执行操作。如果你的数据太大,在开始进行聚合或其他任何事情之前,先找到一些方法在本地存储数据。

如果您不喜欢那样,您可能需要检出GDK源代码以更好地了解与结果集等有关的Sql.getInstance()是如何完成的。然后您可以避开任何地方正在不经意地踩着。

0

也许

List<Map> results = sql.rows("select * from my_table") 
List<Map> result2= sql.rows("select * from my_second_table") 

甚至不会在普通的Java(如当第二个电话是在声明中所做的上次通话时专用的所有资源都被释放您所提供的答案已经说的)工作。作为mentioned by @Todd W Crone Groovy可以优化资源,例如动态释放它们或根据特定运行不释放它们。

其实我只试过一个查询。例如。我试图得到ResultSet,然后遍历它,像这样(不要介意表和字段的名称,查询是相当简单的;并且结果是由于LIMIT 1子句而包含一列的一行):

def resultSet = sql.executeQuery("SELECT age FROM person WHERE id = 12345 LIMIT 1") 
resultSet.next() 

并得到了此ResultSet被关闭错误。似乎Groovy会优化资源并立即关闭ResultSet。我没有查看Groovy SDK的源代码。我发现eachRow和其他方法与封闭式处理程序工作正常,不要抛出此ResultSet被关闭错误。

也许,封闭式处理程序的方法可以帮助你。例如,看从the article where rows() method with closure is used除外:

String query = 'select id as identifier, name as langName from languages' 
def rows = db.rows(query, { meta -> 
    assert meta.tableName == 'languages' 
    assert meta.columnCount == 2 
    // ... 
})