事务管理
事务是一组原子操作(一组SQL执行)的工作单元,这个工作单元中的所有原子操作在进行期间,与其它事务隔离,免于数据源的交相更新而发生混乱,事务中的所有原子操作,要嘛全部执行成功,要嘛全部失败(即使只有一个失败,所有的原子操作也要全部撤消)。 在JDBC中,可以用Connection来管理事务,可以将Connection的AutoCommit设定为false,在下达一连串的SQL语句后,自行呼叫Connection的commit()来送出变更,如果中间发生错误,则撤消所有的执行,例如: try { ..... connection.setAutoCommit(false); ..... // 一连串SQL操作 connection.commit(); } catch(Exception) { // 发生错误,撤消所有变更 connection.rollback(); } Hibernate本身没有事务管理功能,它依赖于JDBC或JTA的事务管理功能,预设是使用JDBC事务管理,事实上,下面的程序只是对JDBC事务管理作了个简单的封装: try { session = sessionFactory.openSession(); Transaction tx = session.beginTransaction(); .... tx.commit(); } catch(Exception e) { tx.rollback(); } 在执行openSession()时,实际上Hibernate是在开启一个Connection,而执行beginTransaction()时,实际上会执行Connection的setAutoCommit(false)方法,最后的tx.commit()就是呼叫Connection的 commit()方法,有兴趣的话,可以研究net.sf.hibernate.transaction.JDBCTransaction中的begin ()与commit()方法,可以找到对应的JDBC代码。 session = sessionFactory.openSession(); <-- Connection connection = ....; tx = session.beginTransactioin(); <-- connection.setAutoCommit(false); tx.commit(); <-- connection.commit(); session.close(); <-- connection.close(); 所以使用JDBC事务管理,最后一定要执行Transaction的commit(),如果没有,则之前对session所下的所有指令并不会有效果。 Hibernate可以透过配置文件来使用基于JTA的事务管理,JTA事务管理可以跨越数个Session,而不是像JDBC事务管理只能在一个Session中进行,我们在hibernate.cfg.xml中如下撰写: <hibernate-configuration> <session-factory> .... <property name="hibernate.transaction.factory_class"> net.sf.hibernate.transaction.JTATransactionFactory </property> .... </session-factory> </hibernate-configuration> 或者是在hibernate.properties中撰写: hibernate.transaction.factory_class=net.sf.hibernate.transaction.JTATransactionFactory JTA的事务是由JTA容器管理,而不是像JDBC事务管理一样由Connection来管理事务,所以我们不是由Session来开始事务,而是如下进行: javax.transaction.UserTransaction tx = new InitialContext().lookup("javax.transaction.UserTransaction"); Session s1 = sessionFactory.openSession(); .... // 一些save、update等 s1.flush(); s1.close(); ... Session s2 = sf.openSession(); ... s2.flush(); s2.close(); .... tx.commit(); 同样的,如果您有兴趣,可以看net.sf.hibernate.transaction.JTATransaction中的begin()与commit()方法代码,看看Hibernate如何封装JTA的事务管理代码的。 |
|
来自: WindySky > 《Hibernate入门》