眾所周知,保證數據庫一致性的操作,就是事務的控制。而Spring事務管理可以分為兩種:編程式(編寫代碼即xml配置文件)以及聲明式(通過切面編程即AOP注入)(具體配置可見博客)。
對於SpringBoot,推薦操作是,使用@Transactional注解來申明事務(@Transactional注解詳情可見博客https://www.cnblogs.com/pengpengdeyuan/p/12737891.html)。
下面一起使用@Transactional來添加事務控制。
1、導包
要在Spring boot中支持事務,首先要導入Spring boot提供的JDBC或JPA依賴:
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-jdbc</artifactId> <scope>test</scope> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-data-jpa</artifactId> <scope>test</scope> </dependency>
當我們導入這兩個包后,SpringBoot會自動默認注入DataSourceTransactionManager或JpaTransactionManager。
2、在啟動類上添加@EnableTransactionManagement注解
由於SpringBoot會自動配置事務,所以這個注解可加也不加,具體實現可在org.springframework.boot.autoconfigure.transaction.TransactionAutoConfiguration類中查看。
@SpringBootApplication //啟用事務管理(可省略) @EnableTransactionManagement @MapperScan("mapper路徑") public class KxlApplication { public static void main(String[] args) { SpringApplication.run(KxlApplication.class, args); } }
三、在service層添加@Transactional注解
@Transactional注解可加在類上,也可加在方法上。
若你寫代碼的風格規范的話,一般@Transactional加在Service層。
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Scope;
import org.springframework.context.annotation.ScopedProxyMode;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Isolation;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;
@Service @Transactional(isolation = Isolation.READ_COMMITTED,propagation = Propagation.REQUIRED) @Scope(proxyMode = ScopedProxyMode.TARGET_CLASS) public class TestService implements ITestService { @Autowired private TestMapper testMapper; }
@Scope(proxyMode = ScopedProxyMode.TARGET_CLASS),該注解的作用是表明此類上所有方法上的事務都是CGLib方式代理的。
具體可詳見博客https://www.cnblogs.com/pengpengdeyuan/p/12737585.html。
以上配置本人運行未報錯,但有些小伙伴在啟動項目時可能會遇到類似以下報錯,
Description: The bean 'testService' could not be injected as a 'com.pk.kxl.service.impl.TestService' because it is a JDK dynamic proxy that implements: com.pk.kxl.service.ITestService Action: Consider injecting the bean as one of its interfaces or forcing the use of CGLib-based proxies by setting proxyTargetClass=true on @EnableAsync and/or @EnableCaching.
這個原因是由jdk自動代理與CGlib代理兩種代理方式的區別造成的,如有發現可以完全按照我的配置,也可參考博客https://www.cnblogs.com/pengpengdeyuan/p/12737585.html。