`
dreamer_0924
  • 浏览: 179925 次
  • 性别: Icon_minigender_1
  • 来自: 济南
社区版块
存档分类
最新评论

分析Hibernate的事务处理机制

阅读更多
Hibernate是对JDBC的轻量级对象封装,Hibernate本身是不具备Transaction处理功能的,Hibernate的 Transaction实际上是底层的JDBC Transaction的封装,或者是JTA Transaction的封装,下面我们详细的分析:

Hibernate可以配置为JDBCTransaction或者是JTATransaction,这取决于你在hibernate.properties中的配置:

#hibernate.transaction.factory_class
net.sf.hibernate.transaction.JTATransactionFactory
#hibernate.transaction.factory_class
net.sf.hibernate.transaction.JDBCTransactionFactory

如果你什么都不配置,默认情况下使用JDBCTransaction,如果你配置为:

hibernate.transaction.factory_class
net.sf.hibernate.transaction.JTATransactionFactory

将使用JTATransaction,不管你准备让Hibernate使用JDBCTransaction,还是JTATransaction,我的忠告就是什么都不配,将让它保持默认状态,如下:

#hibernate.transaction.factory_class
net.sf.hibernate.transaction.JTATransactionFactory
#hibernate.transaction.factory_class
net.sf.hibernate.transaction.JDBCTransactionFactory

在下面的分析中我会给出原因。

一、JDBC Transaction

看看使用JDBC Transaction的时候我们的代码例子:

Session session = sf.openSession();
Transaction tx = session.beginTransactioin();
...
session.flush();
tx.commit();
session.close();

这是默认的情况,当你在代码中使用Hibernate的Transaction的时候实际上就是JDBCTransaction。那么JDBCTransaction究竟是什么东西呢?来看看源代码就清楚了:

Hibernate2.0.3源代码中的类

net.sf.hibernate.transaction.JDBCTransaction:

public void begin() throws HibernateException {
...
if (toggleAutoCommit) session.connection().setAutoCommit(false);
...
}

这是启动Transaction的方法,看到 connection().setAutoCommit(false) 了吗?是不是很熟悉?

再来看

public void commit() throws HibernateException {
...
try {
if ( session.getFlushMode()!=FlushMode.NEVER ) session.flush();
try {
session.connection().commit();
committed = true;
}
...
toggleAutoCommit();
}

这是提交方法,看到connection().commit() 了吗?下面就不用我多说了,这个类代码非常简单易懂,通过阅读使我们明白Hibernate的Transaction都在干了些什么?我现在把用 Hibernate写的例子翻译成JDBC,大家就一目了然了:

Connection conn = ...; <--- session = sf.openSession();
conn.setAutoCommit(false); <--- tx = session.beginTransactioin();
... <--- ...
conn.commit(); <--- tx.commit(); (对应左边的两句)
conn.setAutoCommit(true);
conn.close(); <--- session.close();

看明白了吧,Hibernate的JDBCTransaction根本就是conn.commit而已,根本毫无神秘可言,只不过在Hibernate 中,Session打开的时候,就会自动conn.setAutoCommit(false),不像一般的JDBC,默认都是true,所以你最后不写 commit也没有关系,由于Hibernate已经把AutoCommit给关掉了,所以用Hibernate的时候,你在程序中不写 Transaction的话,数据库根本就没有反应。

二、JTATransaction

如果你在EJB中使用Hibernate,或者准备用JTA来管理跨Session的长事务,那么就需要使用JTATransaction,先看一个例子:

javax.transaction.UserTransaction tx = new
InitialContext().lookup("javax.transaction.UserTransaction");
Session s1 = sf.openSession();
...
s1.flush();
s1.close();
...
Session s2 = sf.openSession();
...
s2.flush();
s2.close();
tx.commit();

这是标准的使用JTA的代码片断,Transaction是跨Session的,它的生命周期比Session要长。如果你在EJB中使用 Hibernate,那么是最简单不过的了,你什么Transaction代码统统都不要写了,直接在EJB的部署描述符上配置某某方法是否使用事务就可 以了。

现在我们来分析一下JTATransaction的源代码, net.sf.hibernate.transaction.JTATransaction:

public void begin(InitialContext context, ...
...
ut = (UserTransaction) context.lookup(utName);
...

看清楚了吗? 和我上面写的代码 tx = new Initial Context?().lookup("javax.transaction.UserTransaction"); 是不是完全一样?

public void commit() ...
...
if (newTransaction) ut.commit();
...

JTATransaction的控制稍微复杂,不过仍然可以很清楚的看出来Hibernate是如何封装JTA的Transaction代码的。

但是你现在是否看到了什么问题? 仔细想一下,Hibernate Transaction是从Session中获得的,tx = session.beginTransaction(),最后要先提交tx,然后再session.close,这完全符合JDBC的 Transaction的操作顺序,但是这个顺序是和JTA的Transactioin操作顺序彻底矛盾的!!! JTA是先启动Transaction,然后启动Session,关闭Session,最后提交Transaction,因此当你使用JTA的 Transaction的时候,那么就千万不要使用Hibernate的Transaction,而是应该像我上面的JTA的代码片断那样使用才行。

总结:

1、在JDBC上使用Hibernate 必须写上Hibernate Transaction代码,否则数据库没有反应。此时Hibernate的Transaction就是Connection.commit而已

2、在JTA上使用Hibernate 写JTA的Transaction代码,不要写Hibernate的Transaction代码,否则程序会报错

3、在EJB上使用Hibernate 什么Transactioin代码都不要写,在EJB的部署描述符里面配置

|---CMT(Container Managed Transaction)
|
|---BMT(Bean Managed Transaction)
|
|----JDBC Transaction
|
|----JTA Transaction
分享到:
评论

相关推荐

    Hibernate的事务处理机制和flush方法的用法.docx

    在本文中,我们将深入探讨Hibernate的事务处理机制以及`flush`方法的用法,并分析为何在某些场景下会出现特定的异常。 首先,我们需要了解Hibernate中的事务处理。在Java应用中,事务通常与SessionFactory和Session...

    spring hibernate 事务管理学习笔记(一)

    然而,单独使用Hibernate时,事务管理往往需要手动处理,增加了复杂性。 当Spring与Hibernate整合时,Spring的事务管理可以自动地覆盖Hibernate的事务管理,实现全局的一致性。在Spring中,我们可以配置`...

    Hibernate教程26_事务并发处理

    理解并熟练运用Hibernate的事务并发处理机制,可以帮助我们设计出更高效、更可靠的数据库访问层。在实际项目中,需要根据业务需求和并发量来灵活选择悲观锁或乐观锁,或者结合两者以达到最佳效果。同时,还要注意...

    hibernate 事务管理注意事项

    ### hibernate 事务管理注意...综上所述,Hibernate事务管理的合理配置对于保证系统的稳定性和数据一致性至关重要。开发者应该充分了解Hibernate的缓存机制及其对事务管理的影响,并根据实际情况灵活调整事务管理策略。

    spring hibernate atomikos 分布式事务

    标题中的“Spring Hibernate Atomikos 分布式事务”涉及到的是在Java企业级开发中处理分布式系统中事务一致性的重要技术。Spring是一个广泛使用的轻量级框架,提供了丰富的功能,包括依赖注入、AOP(面向切面编程)...

    day36 10-Hibernate中的事务:解决丢失更新

    标题中的“day36 10-Hibernate中的事务:解决丢失更新”指的是在...通过理解并熟练运用Hibernate提供的事务控制机制、乐观锁和悲观锁等工具,开发者可以有效地避免丢失更新和其他并发问题,确保应用程序的数据完整性。

    hibernate源码分析一[启动过程]

    这些参数包括数据库连接细节、事务管理策略、缓存机制等,是Hibernate初始化和运行时必不可少的基础配置。 #### Settings类 `Settings`类负责存储由`Configuration`类解析出来的系统配置信息。它将诸如数据库连接...

    hibernate结构框架及组要实现类的深入分析

    在深入分析 Hibernate 结构框架之前,我们先来了解一下核心概念。 **1. Hibernate 配置文件** Hibernate 的配置文件通常为 `hibernate.cfg.xml`,它定义了数据库连接、缓存、事务管理和映射文件的位置。例如,你...

    Hibernate源码解析(一)

    - Transaction:事务处理,封装了数据库事务的开始、提交、回滚操作。 - Query和Criteria:提供了对数据库查询的支持,包括HQL(Hibernate查询语言)和Criteria API。 3. Hibernate工作流程 - 加载配置:程序...

    Ibatis和Hibernate的分析比较

    2. 性能:由于Ibatis允许直接编写SQL,所以在某些情况下,其性能可能优于Hibernate,尤其是在复杂的查询和事务处理上。 3. 学习曲线:Hibernate的全面性使得学习成本较高,而Ibatis的“半自动化”特性使得学习相对...

    hibernate源码分析一_启动过程_

    在启动过程中,Hibernate会根据配置确定事务管理方式,并准备好相应的事务处理机制。 7. **方言识别**:Hibernate需要知道如何与特定的数据库交互,这就涉及到方言(Dialect)。方言封装了不同数据库的SQL特性,...

    hibernate延迟机制分析

    总之,理解并合理运用Hibernate的延迟加载和Eager Loading机制,是优化Java应用性能、处理大数据量关联关系的关键。在实际开发中,还需要考虑其他因素,如事务管理、缓存策略等,以实现最佳的数据访问性能。

    hibernate-3.5.6 源码

    通过分析Hibernate 3.5.6的源码,开发者可以了解到其内部的事务处理、查询优化、缓存策略等实现细节,这对于提升Java数据库编程技能,或者进行ORM框架的二次开发具有重要意义。这个源码库是一个宝贵的教育资源,可以...

    Hibernate源码

    Hibernate源码分析有助于深入理解其内部机制,提高开发效率,优化数据库操作性能。 1. **Hibernate核心模块(hibernate-core)** Hibernate的核心模块包含了ORM框架的主要功能,如实体管理、查询语言(HQL)、事件...

    Hibernate源码解析(三)

    源码解析可能会揭示`Session`内部的事务管理、缓存机制以及如何封装JDBC操作。 其次,`SessionFactory`的创建过程也是一个重要的知识点。`SessionFactory`是Hibernate的工厂类,用于创建`Session`实例。它的创建...

    hibernate缓存机制分析共17页.pdf.zip

    《Hibernate缓存机制详解》 Hibernate,作为Java领域中广泛使用的对象关系映射(ORM)框架,极大地简化了数据库操作。其缓存机制是优化性能的关键组成部分,它减少了对数据库的直接访问,提高了数据处理效率。本文...

    hibernate-5.2.10最新jar包

    详细介绍如何在实际项目中集成Hibernate,包括配置文件设置、实体类设计、数据访问层的构建、事务处理等步骤,以及如何进行增删改查操作。 8. 性能优化: 分析并探讨Hibernate的缓存机制(一级缓存和二级缓存)、...

    Hibernate乐观锁和悲观锁分析

    Hibernate,作为Java领域广泛使用的ORM框架,提供了一种处理并发数据访问冲突的手段,那就是锁机制。主要分为两种类型:乐观锁(Optimistic Locking)和悲观锁(Pessimistic Locking)。 **悲观锁(Pessimistic ...

    ( [尚硅谷]_佟刚_Hibernate面试题分析.zip

    11. **事务处理**:Hibernate通过Session的beginTransaction()、commit()和rollback()方法进行事务管理,符合ACID原则。 12. **延迟加载(Lazy Loading)**:默认情况下,关联对象会进行延迟加载,只有在真正需要时...

    hibernate3.2.5.rar

    2. Session:它是与数据库交互的接口,提供增删查改、事务处理和事件监听等功能。 3. Query和Criteria API:提供了强大的查询功能,支持HQL(Hibernate Query Language)和Criteria API,可以编写复杂的数据库查询。...

Global site tag (gtag.js) - Google Analytics