1. 报错信息:

在使用Seata解决分布式事务超时异常时,添加了@GlobalTransactional后,怎么也不生效

2. 原因分析:

  1. 以为 MyBatisConfig、DataSourceProxyConfig这些都是无用的,直接让自动配置类配置不就好了,结果是大意了,这里的DataSourceProxy是Seata数据源代理类…
    注意这里的数据源配置是必须的!

  2. 需要使用Seata 代理数据源 import io.seata.rm.datasource.DataSourceProxy;
    在这里插入图片描述

  3. 否则 事务回滚会一直不生效!

  4. 而且 MyBatisConfig 中 @MapperScan({“com.atguigu.springcloud.Dao”}) 也是必要的

  5. 因为 我们又新加载了 一个SqlSessionFactory组件,这个会使系统扫描不到 Dao(我看帖子说,甚至会使 MyBatis Plus 的乐观锁、分页插件都失效!https://blog.csdn.net/qq_35721287/article/details/103282589)
    在这里插入图片描述

  6. 而不去新加载了 一个SqlSessionFactory组件,又会使 seata 的数据源代理失效

  7. 所有需要对 mybatis 进行配置,让其能扫描到 Dao

3. 解决方法:

添加 MyBatisConfig、DataSourceProxyConfig两个配置类就好了

@Configuration
@MapperScan({"com.atguigu.springcloud.Dao"})
public class MyBatisConfig {
}
@Configuration
public class DataSourceProxyConfig {

    @Value("${mybatis.mapperLocations}")
    private String mapperLocations;

    @Bean
    @ConfigurationProperties(prefix = "spring.datasource")
    public DataSource druidDataSource(){
        return new DruidDataSource();
    }

    @Bean
    public DataSourceProxy dataSourceProxy(DataSource dataSource) {
        return new DataSourceProxy(dataSource);
    }

	//⭐io.seata.rm.datasource.DataSourceProxy
    @Bean
    public SqlSessionFactory sqlSessionFactoryBean(DataSourceProxy dataSourceProxy) throws Exception {
        SqlSessionFactoryBean sqlSessionFactoryBean = new SqlSessionFactoryBean();
        sqlSessionFactoryBean.setDataSource(dataSourceProxy);
        sqlSessionFactoryBean.setMapperLocations(new PathMatchingResourcePatternResolver().getResources(mapperLocations));
        sqlSessionFactoryBean.setTransactionFactory(new SpringManagedTransactionFactory());
        return sqlSessionFactoryBean.getObject();
    }
}

PS:还出现过这个异常:

org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'globalTransactionScanner' defined in class path resource [com/alibaba/cloud/seata/GlobalTransactionAutoConfiguration.class]: Bean instantiation via factory method failed; nested exception is org.springframework.beans.BeanInstantiationException: Failed to instantiate [io.seata.spring.annotation.GlobalTransactionScanner]: Factory method 'globalTransactionScanner' threw exception; nested exception is io.seata.common.exception.NotSupportYetException: not support register type: null
	at org.springframework.beans.factory.support.ConstructorResolver.instantiate(ConstructorResolver.java:656) ~[spring-beans-5.2.2.RELEASE.jar:5.2.2.RELEASE]

修改 Seata 配置文件时,将原来的配置直接注释,又新加了一句,估计是注释出现问题了,把原来的配置语句直接删除就好了

store {
  ## store mode: file、db
  #mode = "file"  # 把这行直接删除
  mode = "db"
  ## file store property
  file {
    ## store location dir
    dir = "sessionStore"
  }
Logo

华为开发者空间,是为全球开发者打造的专属开发空间,汇聚了华为优质开发资源及工具,致力于让每一位开发者拥有一台云主机,基于华为根生态开发、创新。

更多推荐