4

前言

这周主要是项目字段增加软删除,当一个项目的字段关系变得非常复杂时,想要删除一条数据往往因为牵扯过多数据而变得难以删除,这时就用到了我们的软删除。软删除并不是真正的删除,而是将原有数据设置的deleted字段变为true。当查询数据时,忽略掉deleted字段为true的数据。也就是说,软删除并不是真正的删除,而是将其保留,当查询数据时,根据一个设置的boolean字段进行判断本条数据是否已经删除,已经删除的数据不再被各个功能查到。
在进行单元测试时,当在一个方法加入对软删除的测试时,断言预期结果与正常结果不一致。
image.png

两个对象?

1.初步检查了前面进行的软删除对仓库层方法与实体的修改,并没有问题。
2.单纯的看代码并不是有效的解决问题的方式。有效解决问题还要看执行代码过程中各字段的变化。让我们在删除后输出一下course的deleted字段到底是什么,

System.out.println(course.isDeleted());

输出false
image.png
当然false并不是我们预想中的答案。
为了验证我先在别的已通过方法上进行实验,分别看看删除前后deleted字段的变化。因为如果是delete()方法的问题,别的单元测试删除前后deleted字段就不会改变。
image.png
删除前后都为false,但是单元测试竟然过了,这让我感到了奇怪。这并不符合我的预期。带着疑惑请教了老师。老师让我在仓库层建立一个findById(Long id)方法,通过findById方法从数据库找出来,然后观察deleted字段的值。

ourse = this.courseRepository.findByIdAndDeletedIsTrue(course.getId()).get();
System.out.println(course.isDeleted());

为什么直接输出course的deleted值是false,而从数据库查询到的course的deleted值是true呢。 让我们通过debug来一探究竟。
image.png
image.png
通过对比前后两个course得知,这是两个course对象,也就是说,我们在单元测试中操作的course和数据库中的course是两个course对象,我们delete方法仅对数据库中的course进行了操作,所以造成了当前结果.
我们通过代码更能说明问题,断言两个course相等:
image.png

查无此人

弄清楚了这些,我应当修改我一开始的输出方法。当我尝试改正输出的course时,遇到了新的错误

System.out.println(this.courseRepository.findByIdAndDeletedIsTrue(course.getId()).get().isDeleted());

image.png
大概意思就是不存在。
通过输出id得知,原来我得到了一个不能用的id.
image.png
看来是这个id引起的。几乎同样的初始化数据操作,为什么上一个单元测试没有报错呢,通过debug得知,
image.png
当们在37行获取一个course时,我们的course的id值还是一个随意数,当我们在37行保存后,我们的保存的course才会有一个正常的id值,而两个测试的关键在于39行,没报错的如图所示有course = ,而报错的并没有course = 所以id还是创造出来的随机值。自然而然我们对于这个course进行delete也就无济于事,并不会对数据库中的course影响。也就产生了一开始的问题。

总结

有时候我们想象的东西,并不一定是正确的,这就需要我们一步步去验证,实践才是检验理论的唯一标准。

版权声明

本文作者:河北工业大学梦云智开发团队 - 赵凯强

小强Zzz
1.2k 声望32 粉丝