Nó không phức tạp chút nào.
-
Trước tiên, bạn cần hiểu rằng trình quản lý giao dịch Spring chỉ là một phần tóm tắt quản lý giao dịch. Trong trường hợp của bạn, các giao dịch thực tế xảy ra ở cấp độ Kết nối JDBC.
-
Tất cả
@Transactional
các cuộc gọi phương thức dịch vụ bị chặn bởiTransactionInterceptor
Khía cạnh. -
TransactionIntreceptor
ủy quyền quản lý giao dịch cho cấu hình hiện tạiAbstractPlatformTransactionManager
triển khai (JpaTransactionManager
trong trường hợp của bạn). -
JpaTransactionManager
sẽ ràng buộc giao dịch Spring đang chạy hiện tại với một EntityManager, vì vậy tất cả các DAO tham gia vào giao dịch hiện tại đều có chung một Ngữ cảnh bền vững. -
JpaTransactionManager
chỉ cần sử dụngEntityManager
API giao dịch để kiểm soát các giao dịch:EntityTransaction tx = txObject.getEntityManagerHolder().getEntityManager().getTransaction(); tx.commit();
API giao dịch JPA chỉ cần ủy quyền cuộc gọi đến các phương thức cam kết / khôi phục kết nối JDBC cơ bản.
-
Khi giao dịch được thực hiện (commit / rollback),
org.hibernate.engine.transaction.internal.jdbc.JdbcTransaction
cuộc gọi:transactionCoordinator().getTransactionContext().managedClose();
kích hoạt Phiên ngủ đông (Trình quản lý thực thể) đóng.
-
Do đó, kết nối JDBC cơ bản cũng được kích hoạt để đóng:
jdbcCoordinator.close();
-
Hibernate có một trình xử lý kết nối JDBC hợp lý:
@Override public Connection close() { LOG.tracev( "Closing JDBC container [{0}]", this ); if ( currentBatch != null ) { LOG.closingUnreleasedBatch(); currentBatch.release(); } cleanup(); return logicalConnection.close(); }
-
Kết nối logic ủy quyền cuộc gọi đóng tới nhà cung cấp kết nối hiện được định cấu hình (
DataSourceConnectionProvider
trong trường hợp của bạn), chỉ gọi phương thức đóng trên kết nối JDBC:@Override public void closeConnection(Connection connection) throws SQLException { connection.close(); }
-
Giống như bất kỳ kết nối nào khác gộp chung DataSource, kết nối JDBC đóng chỉ đơn giản là trả kết nối về nhóm và không đóng kết nối cơ sở dữ liệu vật lý. Đó là bởi vì DataSource gộp kết nối trả về proxy Kết nối JDBC chặn tất cả các cuộc gọi và ủy quyền đóng cho logic xử lý nhóm kết nối.
Lưu ý rằng đối với các giao dịch RESOURCE_LOCAL, bạn cũng nên đặt hibernate.connection.provider_disables_autocommit
thuộc tính nếu autocommit
kiểm tra đã bị vô hiệu hóa bởi nhóm kết nối. Bằng cách này, các kết nối cơ sở dữ liệu sẽ được thu thập một cách lười biếng trước khi thực hiện truy vấn SQL hoặc xóa bối cảnh Persistence.