Spring基础学习(五)—事务管理
一、事务基本认识
1.事务的概述
为了保证数据库中数据的一致性,数据的操作应当是离散的成组的逻辑单元。当它全部完成时,数据的一致性可以保持,而当这个单元中的一部分操作失败,整个事务应当全部视为错误,所有从起始点以后的操作应全部回退到开始状态。
事务的操作: 先定义开始一个事务,然后对数据做修改操作,这时如果提交(commit),这些数据就永久的保存下来,如果回退(rollback),数据库管理系统就放弃所有的修改而回到开始事务的状态。
2.事务的属性
(1)原子性(Atmicity)
原子性是指事务是一个不可分割的工作单位,事务的操作要么都发生,要么都不发生。
(2)一致性(Consistency)
事务必须使数据库从一个一致性状态变换到另外一个一致性的状态。
(3)隔离性(Isolation)
事务的隔离性是指一个事务的执行不能被其他事务干扰,即一个事务内部操作及使用的数据对并发的其他事务是隔离的,并发执行的各个事务之间不能互相干扰。
(4)持久性(Durability)
持久性是一个事务一旦被提交,它对数据库中的数据改变就是永久性的,接下来的其他操作和数据库故障不应该对其有任何影响。
3.数据库的隔离级别
数据库事务的隔离性: 数据库系统必须具有隔离并发运行各个事务的能力,使它不会相互影响,避免各种并发问题。
隔离级别: 一个事务与其他事务隔离的程度称为隔离级别。数据库规定了多种隔离级别,不同隔离级别对应不同的干扰程度,隔离级别越高,一致性就越好,但并发性越弱。
对于同时运行的多个事务,当这些事务访问数据库相同数据时,如果没有采用必要的隔离机制,就会导致各种并发问题。
| 脏读 | 对于两个事务T1,T2,T1读取了已经被T2修改但未提交的字段。 | 
| 不可重复读 | T1读取了一个字段,然后T2更新了该字段,之后T1再次读取同一个字段,值就不同了。 | 
| 幻读 | T1从一个表读了一个字段,T2在该表插入一些新行,T1再读,就多几行了。 | 
看到上面的,我感觉不可重复读和幻读貌似区别不大,但是上网搜了下,有人说了它俩的区别。
     不可重复读的重点是修改。同样的条件, 你读取过的数据, 再次读取出来发现值不一样了。        
     幻读的重点在于新增或者删除。同样的条件, 第1次和第2次读出来的记录数不一样。 
数据库提供了4种事务隔离级别
| 
 隔离级别  | 
 描述  | 
| 
 Read UnCommited(读未提交)  | 
 允许事务读取其他事务未提交的修改。脏读、不可重复读、幻读都会出现。  | 
| 
 Read Commited(读已提交)  | 
 只允许事务读取其他事务提交的数据。可避免脏读,不能避免不可重复读、幻读。  | 
| 
 Repeatable Read(可重复读)  | 
 确保事务可以从一个字段读相同的值,在这个事务持续期间,其他事务不能对这个字段进行更新。可避免脏读、不可重复读,不能避免幻读。  | 
| 
 Serializable(串行化)  | 
确保事务可以从一个表读取相同行。在这个事务持续期间,禁止其他事务对该表执行插入、更新、删除。所有并发问题都可以避免,但是性能十分低下。 | 
Oracle 支持的 2 种事务隔离级别: READ COMMITED, SERIALIZABLE。Oracle 默认的事务隔离级别为: READ COMMITED 。Mysql 支持 4 中事务隔离级别. Mysql 默认的事务隔离级别为: REPEATABLE READ。
二、事务的使用
AccountDao.java
public interface AccountDao{
	/*
	 * 汇款
	 */
	public void send(String sender,int money);
	/*
	 * 收款
	 */
	public void receive(String receiver,int money);
}
AccountDaoImpl.java
public class AccountDaoImpl extends JdbcDaoSupport implements AccountDao{
	@Override
	public void send(String sender,int money){
		this.getJdbcTemplate().update("update account set money = money - ? where username = ?",money,sender);
	}
	@Override
	public void receive(String receiver,int money){
		this.getJdbcTemplate().update("update account set money = money + ? where username = ?",money,receiver);
	}
}
AccountService.java
public interface AccountService{
	/*
	 * 转账
	 */
	public void transfer(String sender,String receiver,int money);
}
AccountServiceImpl.java
public class AccountServiceImpl implements AccountService{
	private AccountDao accountDao;
	public void setAccountDao(AccountDao accountDao){
		this.accountDao = accountDao;
	}
	@Override
	public void transfer(String sender,String receiver,int money){
		// 两个操作
		accountDao.send(sender,money);
		int i = 1/ 0;
		accountDao.receive(receiver,money);
	}
}
applicationContext.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context"
xmlns:util="http://www.springframework.org/schema/util" xmlns:aop="http://www.springframework.org/schema/aop"
xmlns:p="http://www.springframework.org/schema/p"
xmlns:tx="http://www.springframework.org/schema/tx"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/util http://www.springframework.org/schema/util/spring-util.xsd
http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd
http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd"> <!-- 加载属性文件 -->
<context:property-placeholder location="classpath:jdbc.properties" /> <!-- 1.数据源 -->
<bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
<property name="driverClass" value="${driverClass}" />
<property name="jdbcUrl" value="${jdbcUrl}" />
<property name="user" value="${user}" />
<property name="password" value="${password}" />
</bean> <!-- 2.dao -->
<bean id="accountDao" class="com.kiwi.dao.AccountDaoImpl">
<property name="dataSource" ref="dataSource"/>
</bean> <!-- 3.service -->
<bean id="accountService" class="com.kiwi.service.AccountServiceImpl">
<property name="accountDao" ref="accountDao"/>
</bean> <!-- 4.1 事务管理器 -->
<bean id="txManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<property name="dataSource" ref="dataSource"/>
</bean> <!-- 4.2 将事务管理器交予Spring -->
<tx:annotation-driven transaction-manager="txManager"/> </beans>
Test.app
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations="classpath:applicationContext.xml")
@Transactional
public class TestApp{ @Autowired
private AccountService accountService; @Test
public void test1(){
accountService.transfer("AAA","BBB",500);
}
}
Spring基础学习(五)—事务管理的更多相关文章
- Spring Boot 2.x基础教程:事务管理入门
		
什么是事务? 我们在开发企业应用时,通常业务人员的一个操作实际上是对数据库读写的多步操作的结合.由于数据操作在顺序执行的过程中,任何一步操作都有可能发生异常,异常会导致后续操作无法完成,此时由于业务逻 ...
 - Spring学习8-Spring事务管理
		
http://blog.sina.com.cn/s/blog_7ffb8dd501014e0f.html Spring学习8-Spring事务管理(注解式声明事务管理) 标签: spring注 ...
 - 全面分析 Spring 的编程式事务管理及声明式事务管理
		
开始之前 关于本教程 本教程将深入讲解 Spring 简单而强大的事务管理功能,包括编程式事务和声明式事务.通过对本教程的学习,您将能够理解 Spring 事务管理的本质,并灵活运用之. 先决条件 本 ...
 - 全面分析 Spring 的编程式事务管理及声明式事务管理--转
		
开始之前 关于本教程 本教程将深入讲解 Spring 简单而强大的事务管理功能,包括编程式事务和声明式事务.通过对本教程的学习,您将能够理解 Spring 事务管理的本质,并灵活运用之. 先决条件 本 ...
 - Spring企业级程序设计 • 【第4章 Spring持久化层和事务管理】
		
全部章节 >>>> 本章目录 4.1 配置数据源资源 4.1.1 JdbcTemplate介绍 4.1.2通过ComboPooledDataSource创建数据源 4.1. ...
 - Spring基于AOP的事务管理
		
Spring基于AOP的事务管理 事务 事务是一系列动作,这一系列动作综合在一起组成一个完整的工作单元,如果有任何一个动作执行失败,那么事务 ...
 - spring的annotation-driven配置事务管理器详解
		
http://blog.sina.com.cn/s/blog_8f61307b0100ynfb.html ——————————————————————————————————————————————— ...
 - Spring整合hibernate4:事务管理
		
Spring整合hibernate4:事务管理 Spring和Hibernate整合后,通过Hibernate API进行数据库操作时发现每次都要opensession,close,beginTran ...
 - 使用注解实现Spring的声明式事务管理
		
使用注解实现Spring的声明式事务管理,更加简单! 步骤: 1) 必须引入Aop相关的jar文件 2) bean.xml中指定注解方式实现声明式事务管理以及应用的事务管理器类 3)在需要添加事务控制 ...
 
随机推荐
- 从CMOS到触发器(一)
			
作为一个学微电子专业的IC learner,这个学期也有一门课:<微电子器件>,今天我就来聊聊基本的器件:CMOS器件及其电路.在后面会聊聊锁存器和触发器. 今天的主要内容如下所示: ·M ...
 - Manual | BSD手册| Linux手册 | 数据库手册 | 编程开发手册 | WEB开发手册 | 软件应用手册 | 网络技术手册 | GNU手册
			
豆豆手册 □ BSD手册 □ Linux手册 □ 数据库手册 □ 编程开发手册 □ WEB开发手册 □ 软件应用手册 □ 网络技术手册 □ GNU手册 在线手册 首 页 BSD手册 ·FreeBS ...
 - 每天一个linux命令(24)--Linux文件类型与扩展名
			
linux 文件类型和Linux 文件的文件名所代表的意义是两个不同的概念.我们通过一般应用程序而创建的比如 file.txt file.tar.gz.这些文件虽然要用不同的程序来打开,但放在Lin ...
 - Hibernate一对一外键映射
			
Hibernate 一对一外键映射 ------------------------------ ----- ...
 - Maven settings.xml配置解读
			
本文对${maven.home}\conf\settings.xml的官方文档作个简单的解读,请确保自己的maven环境安装成功,具体安装流程详见Maven安装 第一步:看settings.xml的内 ...
 - 表格和echart二级联动,并通过点击echart高亮图标单元格
			
html 部分 <!DOCTYPE html><html><head lang="en"> <meta charset="UTF ...
 - ST 单元测试之maven引入junit包
			
按照上篇博客,已经完成了mavne以及eclipse的安装配置,新建好了一个maven项目. 接下来打开项目,双击打开pom.xml,可以看到如下所示, 点击下方的pom.xml,然后添加如下代码,即 ...
 - gitoschina使用入门
			
1 下载git sudo apt-get install git 2 添加公钥:terminal: ssh-keygen -t rsa -C "git.oschina.net" ...
 - PTVS在Visual Studio中的安装
			
下载链接,点这里 PTVS是VS下的python开发插件 1.下载完成后,双击运行,安装完毕 2.解释脚本:打开VS,找到文件-新建-项目,在新建项目页面的左侧树形菜单的已安装->模板-> ...
 - rsync (windows 服务端,linux客户端)将windows上的数据同步到linux服务器,反之也可
			
一:总体概述. 1.windows上面首先装CW_rsync_Server.4.1.0_installer,安装时要输入的用户名密码要记住哦!接下来就是找到rsyncd.conf进入配置细节 2.li ...