一、事务概述
1、在 JavaEE 企业级开发的应用领域,为了保证数据的完整性和一致性,必须引入数据库事务的概念,所以事务管理是企业级应用程序开发中必不可少的技术;
2、事务就是一组由于逻辑上紧密关联而合并成一个整体(工作单元)的多个数据库操作,这些操作要么都执行,要么都不执行;
3、事务的四个关键属性(ACID)
① 原子性(atomicity):"原子性" 的本意是“不可再分”,事务的原子性表现为一个事务中涉及到的多个操作在逻辑上缺一不可。事务的原子性要求事务中的所有操作要么都执行,要么都不执行;
② 一致性(consistency):“一致”指的是数据的一致,具体是指:所有数据都处于满足业务规则的一致性状态。一致性原则要求:一个事务中不管涉及到多少个操作,都必须保证事务执行之前数据是正确的,事务执行之后数据仍然是正确的。如果一个事务在执行的过程中,其中某一个或几个操作失败了,则必须将其他所有操作撤销,将数据恢复到事务执行之前的状态,这就是回滚;
③ 隔离性(isolation):在应用程序实际运行过程中,事务往往是并发执行的,所以很有可能有许多事务同时处理相同的数据,因此每个事物都应该与其他事务隔离开来,防止数据损坏。隔离性原则要求多个事务在并发执行过程中不会互相干扰。
④ 持久性(durability):持久性原则要求事务执行完成后,对数据的修改永久的保存下来,不会因各种系统错误或其他意外而受到影响。通常情况下,事务对数据的修改应该被写入到持久化存储器中。
二、Spring 事务管理
1、编程式事务管理
使用原生的 JDBC API 进行事务管理
TransactionFilter{
try{
//获取连接
//设置非自动提交
chain.doFilter();
//提交
} catch(Exception e){
//回滚
}finally{
//关闭连接释放资源
}
}
评价:
使用原生的JDBC API实现事务管理是所有事务管理方式的基石,同时也是最典型的编程式事务管理。编程式事务管理需要将事务管理代码嵌入到业务方法中来控制事务的提交和回滚。在使用编程的方式管理事务时,必须在每个事务操作中包含额外的事务管理代码。相对于核心业务而言,事务管理的代码显然属于非核心业务,如果多个模块都使用同样模式的代码进行事务管理,显然会造成较大程度的代码冗余。
2、声明式事务管理
大多数情况下声明式事务比编程式事务管理更好:它将事务管理代码从业务方法中分离出来,以声明的方式来实现事务管理。
事务管理代码的固定模式作为一种横切关注点,可以通过 AOP 方法模块化,进而借助 Spring AOP 框架实现声明式事务管理。
Spring 在不同的事务管理 API 之上定义了一个抽象层,通过配置的方式使其生效,从而让应用程序开发人员不必了解事务管理 API 的底层实现细节,就可以使用 Spring 的事务管理机制。
Spring 即支持编程式事务管理,也支持声明式的事务管理。
AOP:环绕通知
//获取连接//设置非自动提交目标代码执行//正常提交//异常回滚//最终关闭
三、Spring提供的事务管理器
Spring 从不同的事务管理 API 中抽象出了一整套事务管理机制,让事务管理代码从特定的事务技术中独立出来。开发人员通过配置的方式进行事务管理,而不必了解其底层是如何实现的。
Spring 的核心事务管理抽象是它为事务管理封装了一组独立于技术的方法。无论使用 Spring 的哪种事务管理策略(编程式或声明式),事务管理器都是必须的。
事务管理器可以以普通的 bean 的形式声明在 Spring IOC 容器中。
四、事务管理器的主要实现
(1)DataSourceTransactionManager:在应用程序中只需要处理一个数据源,而且通过 JDBC 存取。
(2)JtaTransactionManager:在 JavaEE 应用服务器上用 JTA(Java Transaction API)进行事务管理;
(3)HibernateTransactionManager:用 Hibernate 框架存取数据库;
这个事务管理器就可以在目标方法运行前后进行事务控制(事务切面)