一、Spring事务管理实现方式

  按是否通过编程分为声明式事务和编程式事务

  • 声明式事务:

  声明式事务:通过AOP(面向切面)方式在方法前使用编程式事务的方法开启事务,在方法后提交或回滚。用配置文件的方法或@(如:@Transactional)控制事务。

  通过XML配置或者注解实现。

  • 编程式事务:

  手动开启、提交、回滚事务。

  通过编程代码在业务逻辑时需要时自行实现,粒度更小。

二、声明式事务

  本例通过@Transactional注解的方式实现声明式事务

1、ITargetService接口

1 public interface ITargetService {2 3     void update();4 5 }

2、TargetService实现类

【Spring】Spring事务管理实现方式_Spring

 1 @Service 2 public class TargetService implements ITargetService { 3  4     @Autowired 5     JdbcTemplate jdbcTemplate; 6  7     @Transactional 8     @Override 9     public void update(){10         11         String sql="update user set name = '王四' where id = 3";12         int update = jdbcTemplate.update(sql);13     }14 }

【Spring】Spring事务管理实现方式_Spring

3、配置类,主要是注入了数据源、JDBCTemplate 和 事务管理器

【Spring】Spring事务管理实现方式_Spring

 1 @Configuration 2 // 开启事务管理 3 @EnableTransactionManagement 4 @ComponentScan("com.test.tx.service") 5 public class MainConfig { 6  7     // 数据源 8     @Bean("druidDataSource") 9     public DataSource druidDataSource(){10         System.out.println("初始化数据源 DruidDataSource ");11 12         String url="jdbc:mysql://192.168.0.1:3306/test?allowPublicKeyRetrieval=true&useSSL=true";13         String username = "root";14         String password = "123456";15         String driverClassName = "com.mysql.cj.jdbc.Driver";16 17         DruidDataSource druidDataSource = new DruidDataSource();18         druidDataSource.setUsername(username);19         druidDataSource.setPassword(password);20         druidDataSource.setUrl(url);21         druidDataSource.setDriverClassName(driverClassName);22 23         return druidDataSource;24     }25 26     // jdbcTemplate27     @Bean28     public JdbcTemplate jdbcTemplate(){29         System.out.println("初始化 JdbcTemplate ");30 31         JdbcTemplate jdbcTemplate = new JdbcTemplate(druidDataSource());32         return jdbcTemplate;33     }34 35     // 事物管理器36     @Bean37     public TransactionManager transactionManager(){38         return new DataSourceTransactionManager(druidDataSource());39     }40 }

【Spring】Spring事务管理实现方式_Spring

4、主方法调用

【Spring】Spring事务管理实现方式_Spring_05

1 public class MainStarter {2     public static void main(String[] args) {3         AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(MainConfig.class);4 5         ITargetService targetService = context.getBean(ITargetService.class);6         targetService.update();7     }8 }

【Spring】Spring事务管理实现方式_Spring_05

三、编程式事务

1、方法一:使用DefaultTransactionDefinition,定义一个事务,获取事务状态TransactionStatus,使用 PlatformTransactionManager 平台事务对象来管理

  新建一个TestService

【Spring】Spring事务管理实现方式_Spring_05

 1 @Service 2 public class TestService { 3  4     @Autowired 5     private TransactionManager transactionManager; 6  7     @Autowired 8     private JdbcTemplate jdbcTemplate; 9 10     public void test1() {11         PlatformTransactionManager txManager = (PlatformTransactionManager) this.transactionManager;12         // 定义事务隔离级别,传播行为,13         DefaultTransactionDefinition def = new DefaultTransactionDefinition();14         def.setIsolationLevel(TransactionDefinition.ISOLATION_REPEATABLE_READ);15         def.setPropagationBehavior(TransactionDefinition.PROPAGATION_REQUIRED);16         // 事务状态类,通过PlatformTransactionManager的getTransaction方法根据事务定义获取;17         // 获取事务状态后,Spring根据传播行为来决定如何开启事务18         TransactionStatus status = txManager.getTransaction(def);19         try {20             jdbcTemplate.update("update user set name = '王五' where id = 3");21             int n = 1/0;22             // 提交status中绑定的事务23             txManager.commit(status);24         } catch (RuntimeException e) {25             // 回滚status中绑定的事务26             txManager.rollback(status);27         }28     }29 }

【Spring】Spring事务管理实现方式_Spring

2、方式二:使用TransactionTemplate,该类继承了接口DefaultTransactionDefinition,用于简化事务管理,事务管理由模板类定义,主要是通过TransactionCallback回调接口或TransactionCallbackWithoutResult回调接口指定,通过调用模板类的参数类型为TransactionCallback或TransactionCallbackWithoutResult的execute方法来自动享受事务管理。

TransactionTemplate模板类使用的回调接口:

  • TransactionCallback:通过实现该接口的“T doInTransaction(TransactionStatus status) ”方法来定义需要事务管理的操作代码;

  • TransactionCallbackWithoutResult:继承TransactionCallback接口,提供“void doInTransactionWithoutResult(TransactionStatus status)”便利接口用于方便那些不需要返回值的事务操作代码。

  1)配置类中添加TransactionTemplate 事务模版的注册

【Spring】Spring事务管理实现方式_Spring

 1 // 事务模版 2 @Bean 3 public TransactionTemplate transactionTemplate(){ 4     // DataSourceTransactionManager 实现了 PlatformTransactionManager 接口 5     TransactionTemplate template = new TransactionTemplate((PlatformTransactionManager)transactionManager() ); 6     // 设置隔离级别,重复读取 7     template.setIsolationLevel(TransactionDefinition.ISOLATION_REPEATABLE_READ); 8     // 设置传播行为,重复读取 9     template.setPropagationBehavior(TransactionDefinition.PROPAGATION_REQUIRED);10     return template;11 }

【Spring】Spring事务管理实现方式_Spring

  2)使用事务模版 transactionTemplate

【Spring】Spring事务管理实现方式_Spring

 1 public void test2() { 2  3         transactionTemplate.execute(new TransactionCallbackWithoutResult() { 4                              // 在事务中执行,且没有结果返回 5                              @Override 6                              protected void doInTransactionWithoutResult(TransactionStatus status) { 7                                  // 报异常,自动回滚,TransactionTemplate自动管理事务 8                                  jdbcTemplate.update("update user set name = '王五' where id = 3"); 9                                  throw new RuntimeException();10                              }11                          }12         );13 14         // 有结果返回的执行15 //        Object result = transactionTemplate.execute(new TransactionCallback<Object>() {16 //            // 在事务中执行17 //            @Override18 //            public Object doInTransaction(TransactionStatus status) {19 //                return null;20 //            }21 //        });22     }

【Spring】Spring事务管理实现方式_Spring_05