@Transaction

来源:互联网 发布:淘宝一分钱大学生 编辑:程序博客网 时间:2024/05/17 21:59

事务是并发控制的单位,是用户定义的一个操作序列。这些操作要么都做,要么都不做,是一个不可分割的工作单位。

SpringMVC中的事务注解 @Transactional就是为了方法执行中的对数据库操作事务的完整性做的,要么方法全部执行成功,所有sql语句全部正确执行,要么全部不做,就是这样。

spring的事物管理,一般加在service类上。也可以加在service中的方法上,有参数可选择,如@Transactional(readOnly = true),这样如果这个方法中的hibernate的实体类做一些set之类的操作不会修改数据库内容

在service类前加上@Transactional,声明这个service所有方法需要事务管理。每一个业务方法开始时都会打开一个事务。 

Spring默认情况下会对运行期例外(RunTimeException)进行事务回滚。这个例外是unchecked 

如果遇到checked意外就不回滚。 

如何改变默认规则: 

1 让checked例外也回滚:在整个方法前加上 @Transactional(rollbackFor=Exception.class) 

2 让unchecked例外不回滚: @Transactional(notRollbackFor=RunTimeException.class) 

3 不需要事务管理的(只查询的)方法:@Transactional(propagation=Propagation.NOT_SUPPORTED) 

1、Spring默认Transactional事物管理机制

如果程序抛出的是运行期例外,则数据回滚 事物处理

如果是运行Exception例外,则数据不会滚。

可以通过配置修改该规则

@Transactional(noRollbackFor=RuntimeException.class)方法事物说明

@Transactional(RollbackFor=Exception.clas)

@Transactional(readyOnly=true)

@Transactional(timeout=100)默认30

@Transactional(isolation)数据库的隔离级别

{

Read Uncommited:读取未提交的数据(会出现脏读 不可重复读 幻读)

Read Commited:读已提交的数据(会出现不可重复读和幻读)

Repeatable Read:可重复读(会出现幻读)

Serializable:串行化

}


脏读:一个事务读取到另外一个事务未提交的更新的数据

不可重复读:在同一个事务中,多次读取同一个数据返回结果有所不同,就是后续的读取可以读到另外一个事务的已经提交的更新数据

可重复读:在同一个事务多次读取数据时,能够保证所读取的数据一样,也就是后读取的不能读到另外一个事务已经提交的数据

幻读: 一个事务读取到另外一个事务已经提交的更新的数据

<bean id="transactionManager" class="org.springframework.orm.hibernate3.HibernateTransactionManager">
<property name="sessionFactory" ref="sessionFactory" />
</bean>


<!-- Transaction Annotation -->
<tx:annotation-driven transaction-manager="transactionManager"/>

针对查询方法

@Transactional(propagation=Propagation.NOT_SUPPORTED)针对某个方法不开启事务

@Transactional(propagation=Propagation.REQUIRED)spring默认的事务支持


Spring可以通过注解@Transactional来为业务逻辑层的方法(调用DAO完成持久化动作)添加事务能力。

@Tranactional注解分析

  • 作用域:Transactional作用于类上表示类上所有的方法使用指定的事务管理策略,作用于方法表示该方法使用指定的事务管理策略;如果方法和类同时定义了@Tranactional注解,那么方法上定义的@Tranactional的属性覆盖类上定义的@Tranactional的属性
  • value: 用于匹配Spring中定义的tranactionManager的名字,默认是Spring中名称为transactionManager的事务管理器
  • propagation:事务传播属性,默认是Propagation.REQUIRED
  • isolation:事务隔离级别,默认是Isolation.DEFAULT,它是指数据库的默认隔离级别
  • timeout:事务超时时间,默认是TransactionDefinition.TIMEOUT_DEFAULT,它是指数据库的默认的事务超时时间
  • readOnly:设置该事务是否是只读事务;默认为false;
  • rollbackFor:用于设定需要进行回滚的异常类数组,默认只对运行时异常RuntimeException进行回滚。

PS:Spring中的用@Trancational注解标记的方法互相嵌套调用时与是否是同一个线程,同一个类没有关系。只要是Trancational方法,它就会根据propagation属性的值去决定是创建一个新的事务还是加入已存在的事务中。

  使用@Transactional的Spring配置

     为了使用基于@Transactional的事务管理,需要在Spring中进行如下的配置:

<!-- 事务管理 -->
<bean id="txManager"
class="org.springframework.jdbc.datasource.DataSourceTransactionManager"
p:dataSource-ref="dataSource" />
<tx:annotation-driven transaction-manager="txManager" />
    dataSource是在Spring配置文件中定义的数据源的对象实例,EntityManagerFactory是基于JPA使用的实体类管理器:org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean。这些都是用来配置与数据库的连接信息,本质上,@Transactional使用了JDBC的事务来进行事务控制的。

    <annotation-driven>标签的声明,则是在Spring内部启用@Transactional来进行事务管理,类似开关之类的声明。

3.  @Transactional之value

    value这里主要用来指定不同的事务管理器;主要用来满足在同一个系统中,存在不同的事务管理器。比如在Spring中,声明了两种事务管理器txManager1, txManager2.

然后,用户可以根据这个参数来根据需要指定特定的txManager.


原创粉丝点击