SpringMVC+MyBatis 事务管理(实例)

发布时间 - 2026-01-11 02:37:09    点击率:

前言

        spring事务管理包含两种情况,编程式事务、声明式事务。而声明式事务又包括基于注解@Transactional和tx+aop的方式。那么本文先分析编程式注解事务和基于注解的声明式事务。 编程式事务管理使用TransactionTemplate或者PlatformTransactionManager。对于编程式事务spring推荐使用TransactionTemplate。

一、编程式事务

     spring事务特性

     spring中所有的事务策略类都继承自org.springframework.transaction.PlatformTransactionManager接口

public interface PlatformTransactionManager {
 TransactionStatus getTransaction(TransactionDefinition definition) throws TransactionException;
 void commit(TransactionStatus status) throws TransactionException;
 void rollback(TransactionStatus status) throws TransactionException;
}

     编程式事务TransactionTemplate需要手动在代码中处理事务,一般不推荐使用,也不符合spring的思想,因为它直接耦合代码,但各有利弊。先看下TransactionTemplate的源码。

public class TransactionTemplate extends DefaultTransactionDefinition
  implements TransactionOperations, InitializingBean {
 protected final Log logger = LogFactory.getLog(getClass());
 private PlatformTransactionManager transactionManager;
 public TransactionTemplate() {
 }
 public TransactionTemplate(PlatformTransactionManager transactionManager) {
  this.transactionManager = transactionManager;
 }
 public TransactionTemplate(PlatformTransactionManager transactionManager, TransactionDefinition transactionDefinition) {
  super(transactionDefinition);
  this.transactionManager = transactionManager;
 }
 public void setTransactionManager(PlatformTransactionManager transactionManager) {
  this.transactionManager = transactionManager;
 }
 public PlatformTransactionManager getTransactionManager() {
  return this.transactionManager;
 }
 @Override
 public void afterPropertiesSet() {
  if (this.transactionManager == null) {
   throw new IllegalArgumentException("Property 'transactionManager' is required");
  }
 }
 @Override
 public <T> T execute(TransactionCallback<T> action) throws TransactionException {
  if (this.transactionManager instanceof CallbackPreferringPlatformTransactionManager) {
   return ((CallbackPreferringPlatformTransactionManager) this.transactionManager).execute(this, action);
  }
  else {
   TransactionStatus status = this.transactionManager.getTransaction(this);
   T result;
   try {
    result = action.doInTransaction(status);
   }
   catch (RuntimeException ex) {
    // Transactional code threw application exception -> rollback
    rollbackOnException(status, ex);
    throw ex;
   }
   catch (Error err) {
    // Transactional code threw error -> rollback
    rollbackOnException(status, err);
    throw err;
   }
   catch (Throwable ex) {
    // Transactional code threw unexpected exception -> rollback
    rollbackOnException(status, ex);
    throw new UndeclaredThrowableException(ex, "TransactionCallback threw undeclared checked exception");
   }
   this.transactionManager.commit(status);
   return result;
  }
 }
 private void rollbackOnException(TransactionStatus status, Throwable ex) throws TransactionException {
  logger.debug("Initiating transaction rollback on application exception", ex);
  try {
   this.transactionManager.rollback(status);
  }
  catch (TransactionSystemException ex2) {
   logger.error("Application exception overridden by rollback exception", ex);
   ex2.initApplicationException(ex);
   throw ex2;
  }
  catch (RuntimeException ex2) {
   logger.error("Application exception overridden by rollback exception", ex);
   throw ex2;
  }
  catch (Error err) {
   logger.error("Application exception overridden by rollback error", ex);
   throw err;
  }
 }
}

  从上面的代码可以看到核心方法是execute,该方法入参TransactionCallback<T>。查看TransactionCallback源码:

public interface TransactionCallback<T> {
 T doInTransaction(TransactionStatus status);
}

 那么以上两个源码可以确定我们使用编程式事务管理的方式也就是自己需要重写doInTransaction()。OK,那么我们手动使用TransactionTemplate处理下。

1、先配置transactionmanager

 <!--事务管理器 -->
 <bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
  <property name="dataSource" ref="dataSource"/>
 </bean>

2、配置transactionTemplate

 <!--编程式事务,推荐使用TransactionTemplate-->
 <bean id="transactionTemplate"
   class="org.springframework.transaction.support.TransactionTemplate">
  <property name="transactionManager" ref="transactionManager"/>
 </bean>

3、业务代码处理

@Autowired
 private TransactionTemplate transactionTemplate;
 public int insertUser2(final User user) {
  Integer i= (Integer) this.transactionTemplate.execute(new TransactionCallback() {
   public Object doInTransaction(TransactionStatus transactionStatus) {
    int i = userMapper.insertUser(user);
    if (i > 0) {
     System.out.println("success");
    }
    int j = 10 / 0;
    return i;
   }
  });
  return i;
 }

  业务代码中我们使用by zero的异常故意抛出,你会发现能继续打印success,当你断点debug时,你会发现数据库一直是锁定状态,直到你程序执行完。如下图:

二、基于Transactional注解的事务管理

    当前应该是使用最清爽的事务管理方式了,也符合spring的理念,非入侵代码的方式。

1、配置

 <!--事务管理器 -->
 <bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
  <property name="dataSource" ref="dataSource"/>
 </bean>
 <!-- 使用注解事务,需要添加Transactional注解属性 -->
 <tx:annotation-driven transaction-manager="transactionManager"/>
 <!--启用最新的注解器、映射器-->
 <mvc:annotation-driven/>

2、配置后只需要在要处理的地方加上Transactional注解,而且Transactional注解的方式可以应用在类上,也可以应用在方法上,当然只针对public方法。

3、业务代码处理

 @Transactional
 public int insertUser(User user) {
  int i = userMapper.insertUser(user);
  if (i > 0) {
   System.out.println("success");
  }
  int j = 10 / 0;
  return i;
 }

总结

以上所述是小编给大家介绍的SpringMVC+MyBatis 事务管理,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对网站的支持!


# springmvc  # mybatis  # 事务管理  # SpringMVC中事务是否可以加在Controller层的问题  # Spring SpringMVC  # Spring整合MyBatis 事务配置的详细流程  # Spring+SpringMVC配置事务管理无效原因及解决办法详解  # SpringMVC与Mybatis集合实现调用存储过程、事务控制实例  # SpringMVC+MyBatis声明式事务管理  # springmvc多事务提交和回滚问题  # 推荐使用  # 管理器  # 用在  # 你会发现  # 小编  # 也不  # 在此  # 两种  # 当你  # 只需  # 要在  # 给大家  # 到你  # 可以看到  # 重写  # 各有  # 因为它  # 所述  # 抛出  # 先看 


相关栏目: 【 网站优化151355 】 【 网络推广146373 】 【 网络技术251813 】 【 AI营销90571


相关推荐: 如何快速生成凡客建站的专业级图册?  儿童网站界面设计图片,中国少年儿童教育网站-怎么去注册?  如何在建站之星绑定自定义域名?  如何批量查询域名的建站时间记录?  如何用搬瓦工VPS快速搭建个人网站?  如何用AWS免费套餐快速搭建高效网站?  利用JavaScript实现拖拽改变元素大小  怎么制作一个起泡网,水泡粪全漏粪育肥舍冬季氨气超过25ppm,可以有哪些措施降低舍内氨气水平?  网站制作软件有哪些,制图软件有哪些?  详解一款开源免费的.NET文档操作组件DocX(.NET组件介绍之一)  EditPlus中的正则表达式实战(6)  香港网站服务器数量如何影响SEO优化效果?  如何用5美元大硬盘VPS安全高效搭建个人网站?  如何用IIS7快速搭建并优化网站站点?  如何在万网利用已有域名快速建站?  详解Android中Activity的四大启动模式实验简述  Laravel怎么配置S3云存储驱动_Laravel集成阿里云OSS或AWS S3存储桶【教程】  如何用西部建站助手快速创建专业网站?  个人网站制作流程图片大全,个人网站如何注销?  网站建设要注意的标准 促进网站用户好感度!  活动邀请函制作网站有哪些,活动邀请函文案?  动图在线制作网站有哪些,滑动动图图集怎么做?  java ZXing生成二维码及条码实例分享  BootStrap整体框架之基础布局组件  黑客入侵网站服务器的常见手法有哪些?  Laravel如何记录日志_Laravel Logging系统配置与自定义日志通道  Laravel如何生成API文档?(Swagger/OpenAPI教程)  如何破解联通资金短缺导致的基站建设难题?  微博html5版本怎么弄发语音微博_语音录制入口及时长限制操作【教程】  如何在沈阳梯子盘古建站优化SEO排名与功能模块?  Laravel 419 page expired怎么解决_Laravel CSRF令牌过期处理  标准网站视频模板制作软件,现在有哪个网站的视频编辑素材最齐全的,背景音乐、音效等?  iOS正则表达式验证手机号、邮箱、身份证号等  如何安全更换建站之星模板并保留数据?  html5怎么画眼睛_HT5用Canvas或SVG画眼球瞳孔加JS控制动态【绘制】  详解Nginx + Tomcat 反向代理 负载均衡 集群 部署指南  如何在腾讯云服务器快速搭建个人网站?  Java Adapter 适配器模式(类适配器,对象适配器)优缺点对比  Laravel如何处理CORS跨域问题_Laravel项目CORS配置与解决方案  Android中Textview和图片同行显示(文字超出用省略号,图片自动靠右边)  标题:Vue + Vuex 项目中正确使用 JWT 进行身份认证的实践指南  JavaScript常见的五种数组去重的方式  如何在自有机房高效搭建专业网站?  Laravel如何处理JSON字段_Eloquent原生JSON字段类型操作教程  如何快速查询域名建站关键信息?  Laravel如何使用Contracts(契约)进行编程_Laravel契约接口与依赖反转  Linux后台任务运行方法_nohup与&使用技巧【技巧】  Laravel怎么防止CSRF攻击_Laravel CSRF保护中间件原理与实践  如何在橙子建站中快速调整背景颜色?  如何用PHP工具快速搭建高效网站?