DANCE WITH JAVA

开发出高质量的系统

常用链接

统计

积分与排名

好友之家

最新评论

hibernate事务管理 (jdbc jta)

hibernate的两种事务管理jdbc 和jta方式。下边说说两者的区别
一、说明一下jdbc和jta方式事务管理的区别:
JDBC事务由Connnection管理,也就是说,事务管理实际上是在JDBC Connection
中实现。事务周期限于Connection的生命周期之内

JTA 事务管理则由 JTA 容器实现,JTA 容器对当前加入事务的众多Connection 进
行调度,实现其事务性要求。JTA的事务周期可横跨多个JDBC Connection生命周期。

二、在了解jdbc和jta事务的基础上,再来讨论hibernate的两种事务
对于基于JDBC Transaction的Hibernate 事务管理机制而言,事务管理在Session 所依托的JDBC Connection
中实现,事务周期限于Session的生命周期。

对于基于JTA事务的Hibernate而言,JTA事务横跨可横跨多个Session。
三、hibernate中写法的不同

jdbc的写法
public void saveUser(){
    Session session 
= sessionFactory.openSession();
    Transaction tx 
= session.beginTransaction();
    session.save(user);
    tx.commit();
    session.close();
}

必须在session.close()之前commit或者rollback

jta写法
public void saveUser(){
    Session session 
= sessionFactory.openSession();
    Transaction tx 
= session.beginTransaction();
    
    session.save(user);
    session.close();
    
    Session session1 
= sessionFactory.openSession();
    session1.save(user1);
    session.close();
    
    tx.commit();
}

commit和rollback可以在session.close()之后执行.
同时应该注意的一点是,事务是不能嵌套的,在使用jta的事务的情况下,如果要让一个事务跨越两个
session,则必须在两个session的外层开始事务和完成事务。而不能再在session内部开始事务和完成事务。




posted on 2007-07-29 01:58 dreamstone 阅读(5012) 评论(3)  编辑  收藏 所属分类: dao层框架

评论

# re: hibernate事务管理 (jdbc jta) 2007-07-29 10:18 pig

JTA事务的开始
Transaction tx = session.beginTransaction();
应该不是这样吧,应该是从容器中获得。  回复  更多评论   

# re: hibernate事务管理 (jdbc jta) 2007-07-29 12:35 slx

@pig
建议看看hibernate reference 事务处理 jta部分。

11.2.2. Using JTA
If your persistence layer runs in an application server (e.g. behind EJB session beans), every datasource connection obtained by Hibernate will automatically be part of the global JTA transaction. You can also install a standalone JTA implementation and use it without EJB. Hibernate offers two strategies for JTA integration.

If you use bean-managed transactions (BMT) Hibernate will tell the application server to start and end a BMT transaction if you use the Transaction API. So, the transaction management code is identical to the non-managed environment.

// BMT idiom
Session sess = factory.openSession();
Transaction tx = null;
try {
tx = sess.beginTransaction();

// do some work
...

tx.commit();
}
catch (RuntimeException e) {
if (tx != null) tx.rollback();
throw e; // or display error message
}
finally {
sess.close();
}
If you want to use a transaction-bound Session, that is, the getCurrentSession() functionality for easy context propagation, you will have to use the JTA UserTransaction API directly:

// BMT idiom with getCurrentSession()
try {
UserTransaction tx = (UserTransaction)new InitialContext()
.lookup("java:comp/UserTransaction");

tx.begin();

// Do some work on Session bound to transaction
factory.getCurrentSession().load(...);
factory.getCurrentSession().persist(...);

tx.commit();
}
catch (RuntimeException e) {
tx.rollback();
throw e; // or display error message
}
With CMT, transaction demarcation is done in session bean deployment descriptors, not programatically, hence, the code is reduced to:

// CMT idiom
Session sess = factory.getCurrentSession();

// do some work
...

In a CMT/EJB even rollback happens automatically, since an unhandled RuntimeException thrown by a session bean method tells the container to set the global transaction to rollback. This means you do not need to use the Hibernate Transaction API at all with BMT or CMT, and you get automatic propagation of the "current" Session bound to the transaction.

Note that you should choose org.hibernate.transaction.JTATransactionFactory if you use JTA directly (BMT), and org.hibernate.transaction.CMTTransactionFactory in a CMT session bean, when you configure Hibernate's transaction factory. Remember to also set hibernate.transaction.manager_lookup_class. Furthermore, make sure that your hibernate.current_session_context_class is either unset (backwards compatiblity), or set to "jta".

The getCurrentSession() operation has one downside in a JTA environment. There is one caveat to the use of after_statement connection release mode, which is then used by default. Due to a silly limitation of the JTA spec, it is not possible for Hibernate to automatically clean up any unclosed ScrollableResults or Iterator instances returned by scroll() or iterate(). You must release the underlying database cursor by calling ScrollableResults.close() or Hibernate.close(Iterator) explicity from a finally block. (Of course, most applications can easily avoid using scroll() or iterate() at all from the JTA or CMT code.)

  回复  更多评论   

# re: hibernate事务管理 (jdbc jta) 2007-11-03 06:17 jeadu

pig 所说的是JTA规范中定义的写法,而你所说的是经过hibernate包换的写法。  回复  更多评论   


只有注册用户登录后才能发表评论。


网站导航: