如何在自动提交打开或关闭的情况下注入数据源,无论方法是否在事务中 运行

How to inject a datasource with autocommit on or off whether a method is run inside a transaction or not

我有:

我想:

可能的解决方案:https://github.com/jOOQ/jOOQ/tree/master/jOOQ-examples/jOOQ-spring-guice-example i.d.:

最后,我的问题:

如何实现?

有一个简单但不优雅的方法:创建两个DataSource实例并适当地注入。

对于单个 DataSource 实例,还有一种更复杂的方法。大致:

  1. AutoCommit 是 java.sql.Connection 中的一个 属性,它有一个 setter。
  2. 实施 org.jooq.ConnectionProvider 让 JOOQ 使用您的 DataSource 实例。
  3. 这个 ConnectionProvider 实现会有一个特殊的方法,例如startTransaction() 可以使用 autocommit=false 创建连接并将其缓存在 ThreadLocal 成员中。即

    Connection conn = dataSource.createConnection();
    conn.setAutoCommit(false);
    threadLocal.set(conn);
    return conn;
    
  4. ConnectionProvider.acquire() 会像(简化版)那样做:

    return threadLocal.get() != null ? 
           threadLocal.get() : 
           dataSource.createConnection();
    
  5. 另外两个"special"方法是commit()和rollback()——它们会对缓存的连接做相应的操作,关闭连接并从threadLocal中移除。

  6. @Transactional 方法拦截器将调用 "special" 方法

    try {
      connectionProvider.startTransaction();
      interceptedMethod.invoke();
      connectionProvider.commit();
    } catch (Exception e) {
      connectionProvider.rollback();
    }
    

本质上,这是最简单的事务管理器。