Spring 学习笔记之事务管理
Module 介绍
Spring-Transaction-Annotaion:以注解方式配置的声明式事务
Spring-Transaction-XML:以XML方式配置的声明式事务
Spring 事务控制
事务控制分类
- 编程式事务(略)
- 声明式事务
- 以XML方式配置的声明式事务
- 以注解方式配置的声明式事务
以XML方式配置的声明式事务
pom.xml需要引入:
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-aop</artifactId> </dependency> <dependency> <groupId>org.aspectj</groupId> <artifactId>aspectjrt</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-jdbc</artifactId> </dependency>
Springboot 引入 事务控制配置文件(applicationContext-db.xml)
ApplicationContextConfig.java
package top.simba1949; import org.mybatis.spring.annotation.MapperScan; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; /** * @author simba1949@outlook.com * @date 2018/8/25 8:01 */ @SpringBootApplication @MapperScan(basePackages = "top.simba1949.mapper") public class Application { public static void main(String[] args) { SpringApplication.run(Application.class,args); } }
applicationContext.xml 和 applicationContext-db.xml融合到一个spring容器中
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" xsi:schemaLocation=" http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"> <import resource="applicationContext-db.xml"></import> </beans>
applicationContext-db.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:aop="http://www.springframework.org/schema/aop" xmlns:tx="http://www.springframework.org/schema/tx" xmlns:context="http://www.springframework.org/schema/context" xsi:schemaLocation=" http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.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="jdbc.properties"/> <aop:config> <aop:pointcut id="aopPoincut" expression="execution(* top.simba1949.service.impl.*.*(..))"></aop:pointcut> <aop:advisor advice-ref="txAdvice" pointcut-ref="aopPoincut"></aop:advisor> </aop:config> <tx:advice id="txAdvice" transaction-manager="transactionManager"> <tx:attributes> <!--tx:method表示哪些方法需要开启事务,propagation表示必须要求, isolation表示事物隔离级别,rollback-for表示发生异常回滚 --> <tx:method name="add*" propagation="REQUIRED" isolation="DEFAULT" rollback-for="java.lang.Exception"/> <tx:method name="save*" propagation="REQUIRED" isolation="DEFAULT" rollback-for="java.lang.Exception"/> <tx:method name="insert*" propagation="REQUIRED" isolation="DEFAULT" rollback-for="java.lang.Exception"/> <tx:method name="update*" propagation="REQUIRED" isolation="DEFAULT" rollback-for="java.lang.Exception"/> <tx:method name="modify*" propagation="REQUIRED" isolation="DEFAULT" rollback-for="java.lang.Exception"/> <tx:method name="delete*" propagation="REQUIRED" isolation="DEFAULT" rollback-for="java.lang.Exception"/> <tx:method name="query*" read-only="true"></tx:method> <tx:method name="select*" read-only="true"></tx:method> <tx:method name="find*" read-only="true"></tx:method> </tx:attributes> </tx:advice> <!--事务管理器--> <bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager"> <property name="dataSource" ref="dataSource"></property> </bean> <!--数据源--> <bean id="dataSource" class="com.alibaba.druid.pool.DruidDataSource"> <property name="driverClassName" value="${jdbc.driverClassName}"></property> <property name="url" value="${jdbc.url}"></property> <property name="username" value="${jdbc.username}"></property> <property name="password" value="${jdbc.password}"></property> </bean> <!--mybatis的基本配置--> <bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean"> <!--数据源配置--> <property name="dataSource" ref="dataSource"></property> <!--告诉spring,mybatis配置文件位置--> <property name="configLocation" value="classpath:mybatis-config.xml"></property> <!--告诉spring,mybatisMpapper配置文件位置--> <property name="mapperLocations"> <array> <value>classpath*:top/simba1949/mapper/*Mapper.xml</value> </array> </property> <!--给包取别名--> <property name="typeAliasesPackage" value="top.simba1949.common"></property> </bean> <!--mapper扫描配置--> <bean id="mapperScannerConfigurer" class="org.mybatis.spring.mapper.MapperScannerConfigurer"> <!--指定dao接口的路径--> <property name="basePackage" value="top.simba1949.mapper"></property> <property name="sqlSessionFactoryBeanName" value="sqlSessionFactory"></property> </bean> </beans>
mybatis-config.xml
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE configuration PUBLIC "-//mybatis.org//DTD Config 3.0//EN" "http://mybatis.org/dtd/mybatis-3-config.dtd"> <configuration> </configuration>
jdbc.properties
jdbc.driverClassName=com.mysql.jdbc.Driver jdbc.url=jdbc:mysql://localhost:3306/mybatis?characterEncoding=utf-8 jdbc.username=root jdbc.password=19491001
以注解方式配置的声明式事务
application.properteis
server.port=8083 #mysql设置 spring.datasource.driver-class-name=com.mysql.jdbc.Driver spring.datasource.url=jdbc:mysql://localhost:3306/mybatis?characterEncoding=utf-8 spring.datasource.username=root spring.datasource.password=19491001 #表示打印出sql语句 logging.level.com.shyroke.mapper=debug #mybatis配置 mybatis.mapper-locations=classpath*:top/simba1949/mapper/*Mapper.xml mybatis.type-aliases-package=top.simba1949.common
Application.java
package top.simba1949; import org.mybatis.spring.annotation.MapperScan; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; /** * @author simba1949@outlook.com * @date 2018/8/25 8:01 * @MapperScan(basePackages = "top.simba1949.mapper")扫描mapper包 */ @SpringBootApplication @MapperScan(basePackages = "top.simba1949.mapper") public class Application { public static void main(String[] args) { SpringApplication.run(Application.class,args); } }
CountryServiceImpl.java
@Transactional(rollbackFor = Exception.class)即可开启注解
package top.simba1949.service.impl; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Transactional; import top.simba1949.common.CountryCommon; import top.simba1949.mapper.CountryMapper; import top.simba1949.service.CountryService; /** * @author simba1949@outlook.com * @date 2018/8/24 23:22 */ @Service public class CountryServiceImpl implements CountryService { @Autowired private CountryMapper countryMapper; @Transactional(rollbackFor = Exception.class) @Override public int insert(CountryCommon countryCommon) { int i = countryMapper.insert(countryCommon); return i; } }
@Transactional 注解详解
@Transactional( propagation = Propagation.REQUIRED, isolation = Isolation.DEFAULT, timeout = -1, readOnly = false, rollbackFor = Exception.class, noRollbackFor = Exception.class )
编程式事务:TransactionTemplate用法
分类:
- TransactionCallback :有返回值
- TransactionCallbackWithoutResult :无返回值
TransactionCallback 使用方法
// 注入 @Autowired private TransactionTemplate transactionTemplate; // 具体执行 String result = transactionTemplate.execute((TransactionCallback) status -> { System.out.println("纳入事务的执行流程"); return "RESULT"; });
TransactionCallbackWithoutResult 使用方法
// 注入 @Autowired private TransactionTemplate transactionTemplate; // 具体执行 transactionTemplate.execute(new TransactionCallbackWithoutResult() { @Override protected void doInTransactionWithoutResult(@NotNull TransactionStatus transactionStatus) { try { // 执行业务 } catch (Exception e){ // 回滚事务 transactionStatus.setRollbackOnly(); } } });