【SSH】SSH之Hibernate框架:事务管理与线程绑定Session

事务

1、事务:操作数据库中各种数据项的一个程序执行单元。

2、事务的特性

  • 原子性:事务是执行数据库一系列操作的最小单位,不可再分;
  • 一致性:一个事务中的各项操作要么同时成功,要么同时失败;
  • 隔离性:一个事务的操作不受其他事务的干扰;
  • 持久性:事务一旦提交,不可回滚。

3、事务的并发操作可能出现的问题

  • 脏读:一个事务读取到了另一个事务已经更新但没有提交的数据;
  • 不可重复读:一个事务在另一个事务的两次读取操作中间更新了数据;
  • 幻读:一个事务在另一个事务的两次读取操作中间插入了数据。

4、事务隔离级别

  • Read uncommitted(读未提交):可能出现脏读、不可重复读和幻读。
  • Read committed(读提交):可以避免脏读,但可能出现不可重复读和幻读。
  • Repeatable read(重复读):可以避免脏读和不可重复读,但可能出现幻读。
  • Serializable(序列化):可以避免脏读、不可重复读和幻读,但是并发性极低,一般很少使用。

Hibernate的事务管理

1、开启事务:Transaction ts = session.beginTransaction();
2、回滚事务:ts.rollBack();
3、提交事物:ts.commit();
4、事务隔离级别的配置:在hibernate.cfg.xml文件中配置

  • 1:Read uncommitted isolation
  • 2:Read committed isolation
  • 4:Repeatable read isolation
  • 8:Serializable isolation
<!--例:设置隔离级别为:Repeatable read isolation-->
<property name="hibernate.connection.isolation">4</property>

线程绑定Session

1、原因:事务通常是设置在service层的,因为dao层处理的都是一个一个的具体的对数据库的操作,如果为每一个操作都加一个事务管理是没有意义的,因为事务就是要保证多个操作的同时成功或失败。但是一个事务的每个操作都必须在同一个session 中,这就需要事务中dao层的每个方法获得的都是同一个session对象。
2、解决:使一个事务中dao层的每个方法获得同一个session对象,做法有两种:

  • 1、将service层创建的session对象传递给事务中dao层的每个方法;
  • 2、将service层的session对象绑定到ThreadLocal中,在dao层的每个方法中都从ThreadLocal获取session对象。由于事务中的每个操作都在同一个线程中,因此在该线程的任何地方获取的session对象都会是同一个。

3、Hibernate的的解决:Hibernate解决以上问题采用的是第二种方法,但是Hibernate是一个很完善的框架,它底层已经为我们绑定好了session对象,只需要调用SessionFactory的getCurrentSession()方法就能获得绑定好的session对象。但是,这么做还需要一个前提,就是在hibernate.cfg.xml文件中进行配置。
在Hibernate的配置文件中,用hibernate.current_session_context_class属性来指定管理session的方式,管理方式有以下几种:

  • thread:Session对象的生命周期与本地线程绑定;
  • jta:Session的生命周期与JTA事务绑定,用于跨数据库的事务管理;
  • managed:Hibernate委托程序来管理Session对象的生命周期。
<!--例:Session对象的生命周期与本地线程绑定-->
<property name="hibernate.current_session_context_class">thread</property>
发布了128 篇原创文章 · 获赞 17 · 访问量 2725

猜你喜欢

转载自blog.csdn.net/qq_43705275/article/details/104234070
今日推荐