当前位置:   article > 正文

Spring数据库事务管理

Spring数据库事务管理

Spring数据库事务管理

Spring中最常用的事务管理器是DataSourceTransactionManager

配置事务管理器

<!--配置事务管理器-->
<bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
    <property name="dataSource" ref="dataSource"/>
</bean>
  • 1
  • 2
  • 3
  • 4

Java Config方式配置事务

@Configuration
@ComponentScan(basePackages = "com.spring.transaction.*")
@EnableTransactionManagement
public class JavaConfig implements TransactionManagementConfigurer {

    private DataSource dataSource = null;

    @Bean(name = "dataSource")
    public DataSource initDataSource() {
        if (dataSource != null)
            return dataSource;
        Properties props = new Properties();
        props.setProperty("driverClassName", "com.mysql.jdbc.Driver");
        props.setProperty("url", "jdbc:mysql://localhost:3306/weixin");
        props.setProperty("username", "root");
        props.setProperty("password", "root");
        props.setProperty("maxActive", "200");
        props.setProperty("maxIdle", "20");
        props.setProperty("maxWait", "30000");
        try {
            dataSource = BasicDataSourceFactory.createDataSource(props);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return dataSource;
    }

    @Bean(name = "jdbcTemplate")
    public JdbcTemplate initJdbcTemplate() {
        JdbcTemplate jdbcTemplate = new JdbcTemplate();
        jdbcTemplate.setDataSource(initDataSource());
        return jdbcTemplate;
    }

    @Override
    @Bean(name = "transactionManager")
    public PlatformTransactionManager annotationDrivenTransactionManager() {
        DataSourceTransactionManager transactionManager =
                new DataSourceTransactionManager();
        transactionManager.setDataSource(dataSource);
        return transactionManager;
    }
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43

使用注解@EnableTransactionManagement后,在Spring上下文中使用事务注解@Transactional,这样Spring就知道使用该数据库事务管理器管理事务了。

编程式事务

 public static void main(String[] args) {
    /*编程式事务(不推荐使用)*/
    ClassPathXmlApplicationContext ctx =
            new ClassPathXmlApplicationContext("applicationContext-dao.xml");
    JdbcTemplate jdbcTemplate = ctx.getBean(JdbcTemplate.class);
    TransactionDefinition def = new DefaultTransactionDefinition();
    PlatformTransactionManager transactionManager =
            ctx.getBean(PlatformTransactionManager.class);
    TransactionStatus status = transactionManager.getTransaction(def);
    try {
        jdbcTemplate.update("insert into t_lecture(lecture_name, note) " +
                "values ('Python', 'Xixi')");
        transactionManager.commit(status);
    } catch (Exception e) {
        transactionManager.rollback(status);
        e.printStackTrace();
    }
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18

声明式事务(一种约定型的事务)

<!--配置使用@Transactional配置事务-->
<tx:annotation-driven transaction-manager="transactionManager"/>
  • 1
  • 2

XML方式配置事务管理器

<!--配置事务拦截器-->
<bean id="transactionInterceptor" class="org.springframework.transaction.interceptor.TransactionInterceptor">
    <property name="transactionManager" ref="transactionManager"/>
    <!--Spring IoC启动时会解析这些内容,放到事务定义类TransactionDefinition中,运行时根据正则匹配程度决定采取的策略-->
    <property name="transactionAttributes">
        <props>
            <prop key="insert*">PROPAGATION_REQUIRED, ISOLATION_READ_UNCOMMITTED</prop>
            <prop key="save*">PROPAGATION_REQUIRED, ISOLATION_READ_UNCOMMITTED</prop>
            <prop key="add*">PROPAGATION_REQUIRED, ISOLATION_READ_UNCOMMITTED</prop>
            <prop key="select*">PROPAGATION_REQUIRED, readOnly</prop>
            <prop key="get*">PROPAGATION_REQUIRED, readOnly</prop>
            <prop key="find*">PROPAGATION_REQUIRED, readOnly</prop>
            <prop key="del*">PROPAGATION_REQUIRED, ISOLATION_READ_UNCOMMITTED</prop>
            <prop key="remove*">PROPAGATION_REQUIRED, ISOLATION_READ_UNCOMMITTED</prop>
            <prop key="update*">PROPAGATION_REQUIRED, ISOLATION_READ_UNCOMMITTED</prop>
        </props>
    </property>
</bean>

<bean class="org.springframework.aop.framework.autoproxy.BeanNameAutoProxyCreator">
    <!--指定拦截哪些类-->
    <property name="beanNames">
        <list>
            <value>*ServiceImpl</value>
        </list>
    </property>
    <!--定义事务拦截器-->
    <property name="interceptorNames">
        <list>
            <value>transactionInterceptor</value>
        </list>
    </property>
</bean>
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33

在ServiceImpl上使用注解定义事务属性

public class RoleServiceImpl implements IRoleService {

    @Override
    @Transactional(propagation = Propagation.REQUIRED, isolation = Isolation.DEFAULT
        , timeout = 3)
    public int insertRole(Role role) {
        // 执行业务逻辑...
        return 0;
    }
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10

@Transaction的底层实现是基于AOP,而AOP又是基于动态代理的,所以对于静态方法和非public方法,@Transaction是失效的。

在动态代理中,被代理对象调用了自身的其他方法,而该方法又被@Transaction标注,此时@Transaction失效。因为在方法内部调用是不会调用代理对象的。解决方法就是从Spring IoC容器中获取对象(代理对象)。

事务的使用注意:

  1. 由于Service对应的是一个事务,所以在Controller中需要注意多次操作是否是在同一个事务中。
  2. 注意不要过长时间的占用事务资源。
  3. 错误的捕捉异常,导致在约定的事务流程中捕捉不到异常,不会产生回滚。
声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/笔触狂放9/article/detail/995179
推荐阅读
相关标签
  

闽ICP备14008679号