Spring事务的⽤法及案例(注解⽅式)⼊门
Spring事务的⽤法及案例(注解⽅式)⼊门
⼀、什么是Spring事务
事务Transaction,它是⼀些列严密操作动作,要么都操作完成,要么都回滚撤销。Spring事务管理基于底层数据库本⾝的事务处理机制。数据库事务的基础,是掌握Spring事务管理的基础。
⼆、事务的四个特性ACID
2.1 原⼦性
事务最基本的操作单元,要么全部成功,要么全部失败,不会结束在中间某个环节。事务在执⾏过程中发⽣错误,会被回滚到事务开始前的状态,就像这个事务从来没有执⾏过⼀样。
2.2 ⼀致性
事务的⼀致性指的是在⼀个事务执⾏之前和执⾏之后数据库都必须处于⼀致性状态。如果事务成功地完成,那么系统中所有变化将正确地应⽤,系统处于有效状态。如果在事务中出现错误,那么系统中的所有变化将⾃动地回滚,系统返回到原始状态。
2.3 隔离性
指的是在并发环境中,当不同的事务同时操纵相同的数据时,每个事务都有各⾃的完整数据空间。由并发事务所做的修改必须与任何其他并发事务所做的修改隔离。事务查看数据更新时,数据所处的状态要么是另⼀事务修改它之前的状态,要么是另⼀事务修改它之后的状态,事务不会查看到中间状态的数据。
2.4 持久性
指的是只要事务成功结束,它对数据库所做的更新就必须永久保存下来。即使发⽣系统崩溃,重新启动数据库系统后,数据库还能恢复到事务成功结束时的状态。
三、Spring中的事务管理
Spring既⽀持编程式事务管理,也⽀持声明式的事务管理
编程式事务管理:将事务管理代码嵌⼊到业务⽅法中来控制事务的提交和回滚,在编程式事务中,必须在每个业务操作中包含额外的事务管理代码
声明式事务管理:⼤多数情况下⽐编程式事务管理更好⽤。它将事务管理代码从业务⽅法中分离出来,
以声明的⽅式来实现事务管理。事务管理作为⼀种横切关注点,可以通过AOP⽅法模块化。Spring通过Spring
AOP框架⽀持声明式事务管理。
三、Spring声明式事务管理:基于注解⽅式使⽤步骤(举个⼩栗⼦)
3.1编写数据库
SET NAMES utf8mb4;
SET FOREIGN_KEY_CHECKS =0;
-- ----------------------------
-- Table structure for account
-- ----------------------------
DROP TABLE IF EXISTS`account`;
CREATE TABLE`account`(
`username`varchar(50)CHARACTER SET utf8 COLLATE utf8_general_ci NOT NULL,
`balance`int(11)NULL DEFAULT NULL,
PRIMARY KEY(`username`)USING BTREE
)ENGINE=InnoDB CHARACTER SET= utf8 COLLATE= utf8_general_ci ROW_FORMAT = Dynamic; -- ----------------------------
-- Records of account
-- ----------------------------
INSERT INTO`account`VALUES('whd',70);
-- ----------------------------
-- Table structure for book
-- ----------------------------
DROP TABLE IF EXISTS`book`;
CREATE TABLE`book`(
`isbn`varchar(50)CHARACTER SET utf8 COLLATE utf8_general_ci NOT NULL,
`book_name`varchar(100)CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL, `price`int(11)NULL DEFAULT NULL,
PRIMARY KEY(`isbn`)USING BTREE
)ENGINE=InnoDB CHARACTER SET= utf8 COLLATE= utf8_general_ci ROW_FORMAT = Dynamic; -- ----------------------------
-- Records of book
-- ----------------------------
INSERT INTO`book`VALUES('1001','JAVA',100);
INSERT INTO`book`VALUES('1002','Oracle',70);
-- ----------------------------
-- Table structure for book_stock
-- ----------------------------
DROP TABLE IF EXISTS`book_stock`;
CREATE TABLE`book_stock`(
`isbn`varchar(50)CHARACTER SET utf8 COLLATE utf8_general_ci NOT NULL COMMENT'图书编号', `stock`int(11)NULL DEFAULT NULL COMMENT'库存',
PRIMARY KEY(`isbn`)USING BTREE
)ENGINE=InnoDB CHARACTER SET= utf8 COLLATE= utf8_general_ci ROW_FORMAT = Dynamic; -- ----------------------------
-- Records of book_stock
-- ----------------------------
INSERT INTO`book_stock`VALUES('1001',10);
INSERT INTO`book_stock`VALUES('1002',10);
SET FOREIGN_KEY_CHECKS =1;
数据库名字:book_manager 表:account
表:book
表:book_stock
l导⼊依赖
<dependencies>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>5.2.6.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-jdbc</artifactId>
<version>5.2.6.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-aspects</artifactId>
<version>5.2.6.RELEASE</version>
</dependency>
<dependency>
<groupId&batis</groupId>
<artifactId>mybatis</artifactId>
<version>3.5.4</version>
</dependency>
<dependency>
<groupId&batis</groupId>
<artifactId>mybatis-spring</artifactId>
<version>2.0.3</version>
</dependency>
<dependency>group by的用法及原理详解
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>5.1.47</version>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid</artifactId>
<version>1.1.10</version>
</dependency>
</dependencies>
3.3spring配置
3.3.1 配置事务管理器DataSourceTransactionManager(事务第⼀步)
<!--配置事务管理器 .事务类、理解为切⾯类-->
<bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager"> <property name="dataSource" ref="dataSource"/>
</bean>
3.3.2开启注解事务(事务第⼆步)
<!--2.开启事务注解-->
<annotation-driven/>
3.3.3整体的spring配置l
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="/schema/beans"
xsi="/2001/XMLSchema-instance"
context="/schema/context"
tx="/schema/tx"
schemaLocation="/schema/beans /schema/beans/spring-beans.xsd www./schema/context /schema/context/spring-context.xsd /schema/tx w /schema/tx/spring-tx.xsd">
<component-scan base-package="com.da.service"/>
<bean id="dataSource" class="com.alibaba.druid.pool.DruidDataSource">
<property name="driverClassName" value="sql.jdbc.Driver"/>
<property name="url" value="jdbc:mysql://localhost:3306/book_manager"/>
<property name="username" value="root"/>
<property name="password" value="1998"/>
</bean>
<bean id="sessionFactory" class="batis.spring.SqlSessionFactoryBean">
<property name="dataSource" ref="dataSource"/>
<property name="mapperLocations" value="classpath:mapper/*.xml"/>
</bean>
<bean class="batis.spring.mapper.MapperScannerConfigurer">
<property name="basePackage" value="com.da.dao"/>
</bean>
<!--配置事务管理器 .事务类、理解为切⾯类-->
<bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<property name="dataSource" ref="dataSource"/>
</bean>
<!--2.开启事务注解-->
<annotation-driven/>
</beans>
3.4实体类
3.4.1 Account实体类
public class Account {
private String username;
private Integer balance;
public String getUsername(){
return username;
}
public void setUsername(String username){
this.username = username == null ? null : im();
}
public Integer getBalance(){
return balance;
}
public void setBalance(Integer balance){
this.balance = balance;
}
}
3.4.2 Book实体类