Hibernate4、Hibernate5 和 DBCP 的兼容性问题

1 背景

周一回来发现用户中心批量更新手机号未生效,上 Nexus 看了下有没有人动了 lib-datasource(基础架构组的一个组件,简化连接池装配),最新一个版本在上周四,该版本解决了 AutoCommit 的问题,详见参考1。

2 排查过程

  1. 打断点,确认手机号在批量插入前已经脱敏。

  2. 联系DBA 输出 general_log,发现最后一步不是 commit,而是 rollback。

  3. 放开日志级别 ,发现程序有 commit。

  4. 既然 generl_log 现实有 rollback,直接在 java.sql.Connection#rollback() 上打了断点,并保留调用栈

TransactionInterceptor 是事务家的门房。
javax.transaction.TransactionManager,出身高贵,名副其实的官家。
TransactionManager 的大公子 AbstractPlatformTransactionManager 读了几年圣贤书,倒也有模有样,doCommit()、doRollback() 什么的顺手拈来,是其它小儿子的学习榜样。
狐狸精 SpringSessionSynchronization 把 AbstractPlatformTransactionManager 蛊惑了,使他在 triggerBeforeCompletion() 中还没 commit 就把自家 session 给断了(钱都败光了)。
AbstractPlatformTransactionManager 身无分文,只好把传家宝 Connection 贱卖给了包工头DBCP。
包工头DBCP 没有眼光,看这个 Connection 既不是AutoCommit,也不是只读,顺手就砸了它(回滚了 Connection)。

解决方法

  1. 直接上 HikariCP
  2. 换别的ORM实现(EBean),甚至 MyBatis、裸JDBC

Reference

[1] [排查 @Transactional 失效](https://www.cnblogs.com/mougg/p/12572773.html

相关文章