在JOOQ中,如果我直接使用底层连接,是否保持了我的事务状态?

时间:2018-01-31 11:59:20

标签: java postgresql transactions kotlin jooq

让我们假设我有一个JOOQ DSLContext对象,我需要下拉到JDBC Connection对象的级别来执行一些非JOOQ逻辑。 (就我而言,我想使用Postgres驱动程序的CopyManager对象)。

如果我的DSLContext是事务性的,那么直接在Connection上执行的操作是否会被同一个事务包装?我正在使用JOOQ的默认交易提供商。

e.g。 (Kotlin代码,但对Java用户应该是非常透明的)

dsl.transaction { transactionConfig ->
    val transactionalDSL = DSL.using(transactionConfig)
    transactionalDSL.connection { connection ->
        val manager = CopyManager(connection as BaseConnection)
        manager.copyInto(table, inputStream, fields)
    }
}

2 个答案:

答案 0 :(得分:2)

您的API使用方法是正确的。

最佳API使用

使用DSLContext.transaction(TransactionalRunnable)时最重要的是使用参数配置,您为事务边界内的所有数据库交互调用了transactionConfig(而不是外部dsl引用,它仍未修改并且可能会从连接池返回一个新连接。)

换句话说,transactionConfig是一个Configuration,它保证始终从事务的范围返回相同的JDBC Connection,无论您的DataSource / {{ 1}}配置。

使用线程绑定事务

以上是jOOQ的保证,但当然你也可以确保线程约束的交易也处于较低的水平,例如:

  • 使用jOOQ ConnectionProviderDSLContext.transaction(ContextTransactionRunnable),如果你的逻辑看起来像这样:

    ThreadLocalTransactionProvider
  • 使用线程绑定的事务连接池或DataSource。在这种情况下,您的dsl.transaction { () -> dsl.connection { connection -> val manager = CopyManager(connection as BaseConnection) manager.copyInto(table, inputStream, fields) } } 应该返回与dsl.configuration().connectionProvider()相同的连接,这对jOOQ来说是透明的。

答案 1 :(得分:0)

在实验上,答案似乎是肯定的。