JOOQ 和资源处理



我使用 JOOQ 查询我的关系数据库,我最近一直在研究连接处理,它让我有点困惑。我试过阅读JavaDoc,还有这个:调用JooQ DSLContext的.close()时,连接何时关闭?但它为我创造了更多的 FUD。

目前我的代码是这样做的:

try (final Connection cn = pool.getConnection()) {
DSLContext dsl = DSL.using(cn, MARIADB);
// query stuff
}

从本质上讲,我将 JOOQ 视为一个根本不进行连接处理的查询器。我从来没有遇到过这段代码的问题。

但是,我确实收到来自IntelliJ的警告,说DSLContext是可自动关闭的,应该由尝试资源处理。我知道在这种情况下不必这样做,但我的第一个问题是"可以吗?用这个替换上面的代码是否安全:

try (final DSLContext dsl = DSL.using(pool.getConnection(), MARIADB)) {
// query stuff
}

另一个 StackOverflow 帖子说,当你使用其中一个辅助方法创建 DSLContext 时,你需要在 DSLContext 上使用 close()。但是,如果您只是传入了连接对象怎么办?close() 还会关闭我的连接吗?

我还发现DSL还有另一个using()允许你分配整个数据源。因此,我也可以这样做:

final DSLContext dsl = DSL.using(pool, MARIADB);

然后完全省略所有尝试资源。这里的权衡是什么?有没有甚至?

IntelliJ进一步抱怨具有AutoClosable接口(继承自Query)的UpdateQuery。是否有必要关闭我的查询?我总是只是调用 execute() 并毫无问题地关闭了底层连接。

我正在寻找的是能够满足这四个要求的代码

  1. 它使用正确的资源管理
  2. 它使用JOOQ
  3. IDE 中打开了"尝试使用资源"警告
  4. 没有警告

上面的各种代码段都至少满足了其中一个要求。但最终连接处理并不重要,因为 JOOQ 中的查询类也会生成大量警告。

最好的方法确实是关闭警告,但对于JOOQ来说,特别是使用Intellij的排除规则。卢卡斯链接的页面上的评论中也提到了如何做到这一点(https://blog.jooq.org/2015/12/02/a-subtle-autocloseable-contract-change-between-java-7-and-java-8/)。

我只需要记住以正确的方式为 JOOQ 课程做事:)

目前我的代码是这样做的:

try (final Connection cn = pool.getConnection()) {
DSLContext dsl = DSL.using(cn, MARIADB);
// query stuff
}

这是正确的用法。

从本质上讲,我将 JOOQ 视为一个根本不进行连接处理的查询器。

这是一个正确的假设。

但是,我确实收到来自IntelliJ的警告,说DSLContext是可自动关闭的,应该由尝试资源处理

许多 IDE 都会执行此检查,但通常最好将其关闭。在Java 8+中,你不能合理地期望一个AutoCloseable真的需要关闭。一个这样的例子是Stream,它AutoCloseable那些确实包含资源的情况,但大多数情况下它没有。

这是 Java 8 中一个微妙的 API 更改,导致 IDE 中的此警告最好被关闭(或者您可以指定例外)。

您的问题:

这个替换上面的代码是否安全:

try (final DSLContext dsl = DSL.using(pool.getConnection(), MARIADB)) {
// query stuff
}

是的,你可以这样做。DSLContext.close()调用将仅关闭由DSLContext创建的资源。在您的情况下,它没有任何影响。

作为记录,创建了足智多谋的DSLContexts,例如通过DSL.using(url, username, password)

然后完全省略所有尝试资源。这里的权衡是什么?有没有甚至?

所有这些都与资源无关。

IntelliJ进一步抱怨具有AutoClosable接口(继承自Query)的UpdateQuery。是否有必要关闭我的查询?我总是只是调用 execute() 并毫无问题地关闭了底层连接。

  1. 关闭该警告! :-)
  2. 调用Query.keepStatement(true)时,查询可能很足智多谋

最新更新