@Transactional-单元测试中的回滚

这篇具有很好参考价值的文章主要介绍了@Transactional-单元测试中的回滚。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

1.问题1

今天在JUnit单元测试中测试接口时,突然发现idea写入数据库成功,但是数据库中没有数据

@Slf4j
@Rollback
@Transactional
class ShippingServiceImplTest extends MallApplicationTests {

    @Autowired
    private ShippingService shippingService;

    private Integer uid = 1;

    @Test
    public void add() {
        ShippingForm form = new ShippingForm();
        form.setReceiverName("Arion");
        form.setReceiverAddress("江苏南京");
        form.setReceiverCity("北京");
        form.setReceiverMobile("12212345678");
        form.setReceiverPhone("010123456");
        form.setReceiverProvince("北京");
        form.setReceiverDistrict("海淀区");
        form.setReceiverZip("000000");
        ResponseVo<Map<String, Integer>> responseVo = shippingService.add(uid, form);
        log.info("result={}", responseVo);
    }

  
}

去掉@Rollback注解后,idea中事务正常执行,mysql数据库中依然是没有数据的,查看日志发现

[main] INFO  o.s.t.c.t.TransactionContext - Rolled back transaction for test:

明显事务虽然执行成功了但是回滚了,仔细一看问题出在@Transactional,spring支持声明式事务,通过AOP实现实现用户操作和具体的事务解耦,加上该注解后,方法执行前创建一个事务,当方法结束后回滚该事务,这就是为什么idea中事务是执行成功的,最后数据库找中没有数据。

需要注意的是:
事务回滚后主键id不会随着事务的回滚而删除

2.注解失效

执行如下的test方法时,不会报错,证明方法a的注解是没有生效的。

rolled back transaction for test,Bug,单元测试,intellij-idea,java

原因在于spring中的@Transactional注解是通过AOP的机制来实现的,首先是产生一个代理对象,然而在执行父类的a方法时,是通过被代理的对象(普通对象)行的,也就是所谓的普通对象,然而普通对象在执行时不会判断方法上是否有事务的注解,因此不生效。

2.1 解决办法1-拆分类

rolled back transaction for test,Bug,单元测试,intellij-idea,java

将要执行的a方法单独拆成一个类,然后通过自动注入来调用,因为单独拆分的这个类也是有事务的,所以要进行AOP生成代理对象,最终容器中放的是代理对象,自动注入拿到的bean也是被代理后的,因此可以执行事务。

 2.2 直接通过代理对象执行a方法

rolled back transaction for test,Bug,单元测试,intellij-idea,java

 因为这个时候执行的a方法是代理对象执行的,而不是普通方法执行的文章来源地址https://www.toymoban.com/news/detail-616938.html

到了这里,关于@Transactional-单元测试中的回滚的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • @Transactional注解作用,不生效的场景,事务回滚

    声明式事务管理建立在AOP之上的。其本质是对方法前后进行拦截,然后在目标方法开始之前创建或者加入一个事务,在执行完目标方法之后根据执行情况提交或者回滚事务。 简而言之,@Transactional注解在代码执行出错的时候能够进行事务的回滚。 在启动类上添加@EnableTransac

    2024年02月10日
    浏览(50)
  • 支付宝一面:多线程事务怎么回滚?说用 @Transactional 可以回去等通知了!

    1,最近有一个大数据量插入的操作入库的业务场景,需要先做一些其他修改操作,然后在执行插入操作,由于插入数据可能会很多,用到多线程去拆分数据并行处理来提高响应时间,如果有一个线程执行失败,则全部回滚。 2,在spring中可以使用 @Transactional 注解去控制事务,

    2024年02月08日
    浏览(78)
  • C# 中的单元测试,如何使用单元测试进行程序测试和调试?

    单元测试是一种软件测试方法,用于测试单个功能或方法是否按预期工作。在 C# 中,可以使用 .NET 框架中的单元测试工具来编写和运行单元测试。 下面是使用 Visual Studio 内置的单元测试框架来创建一个简单的单元测试的步骤: 在 Visual Studio 中创建一个新的类库项目。 在新项

    2024年02月15日
    浏览(63)
  • maven中的单元测试

    单元测试:采用junit(单元测试框架) 单元:在java中就是指方法,一个方法就是一个单元,方法是测试的最小单位 采用junit去测试方法是否完成了要求,属于开发人员自测阶段 假设这种场景:一个main方法里面有好几个方法,而且方法之间彼此有关系,比如一个方法会调用另

    2023年04月22日
    浏览(47)
  • Java中的单元测试

    单元测试是指在软件开发中对软件的最小可测试单元进行测试和验证的过程。最小可测试单元通常是指函数、方法或者类,单元测试可以保证开发人员的代码正确性,同时也方便后期维护和修改。单元测试的主要目的是检测代码的正确性,确保单个函数或方法的输入和输出正

    2024年02月04日
    浏览(41)
  • 单元测试中的驱动程序和桩程序理解 单元测试中的驱动程序和桩程序理解

      运行被测单元,为了隔离单元,根据被测单元的接口,开发相应的驱动程序和桩程序,两者有什么区别呢?     驱动程序(Driver),也称驱动模块     用于模拟被测模块的上级模块,能够调用被测模块,驱模块接受测试数据,调用被测模块并把相关数据传送给被测模块。

    2024年02月15日
    浏览(45)
  • flutter中的ListView单元测试

    在 Flutter 中,你可能会希望测试 ListView 内容是否如预期那样显示,是否能够正确滚动,以及是否处理用户输入。以下是测试 ListView 的一些基本步骤: 测试 ListView 的内容 这涉及到确认 ListView 是否显示了正确数量的项,以及这些项是否包含正确的数据。 测试 ListView 的滚动行

    2024年04月10日
    浏览(50)
  • 机器人中的yaw/pitch/roll

    1、yaw(pan)/pitch(tilt)/roll 我认为,yaw/pitch/roll绕哪个轴旋转,是要看坐标系的朝向的,如果坐标系的轴如下图,则对应关系是yaw(z轴)、pitch(x轴)、roll(y轴)。 如果换个坐标系,比如下图,则是yaw(Y轴)、pitch(X轴)、roll(Z轴)。 2、yaw/pitch/roll的计算 工业上,一般的旋

    2024年02月03日
    浏览(40)
  • Python中的单元测试框架:使用unittest进行有效测试

    在软件开发中,单元测试是一种测试方法,它用于检查单个软件组件(例如函数或方法)的正确性。Python 提供了一个内置的单元测试库,名为 unittest ,可以用来编写测试代码,然后运行测试,并报告测试结果。 本文将向你介绍如何使用 unittest 来编写和运行单元测试。通过阅

    2024年03月09日
    浏览(42)
  • Java中的单元测试,反射和枚举

    2024年02月05日
    浏览(54)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包