假设我们需要确保一个数据库操作序列(目前实现为A,后面跟着B,后面跟着C)要么一起执行,要么根本不执行。我们可以使用数据库事务来实现这一点--但是我们如何编写一个自动测试来验证这个原子性属性是否满足,而这个属性并不脆弱?
我们可以很容易地编写一个白盒测试:考虑到我们知道首先执行A,然后是B,然后是C,我们可以编写一个测试,注入假C并使假C抛出运行时异常,而不是发出数据库更新查询,以模拟系统崩溃。然后,我们在测试中捕获该异常,并断言自测试开始运行以来,数据库中的任何内容都没有改变。
但是,如果开发人员稍后出现并重写实现以调用C,那么我们的测试将变得无效--它只会测试“如果什么都没有发生,那么什么都不会发生”,或者换句话说,“如果系统立即崩溃,那么什么也不会写入数据库”。不是一个非常有用的测试,也不是测试我们想要测试的!这是因为它是一个白盒测试,它基于对实现中操作顺序的假设,即C是最后执行的(或者至少不是第一次)。
如果在实现中更改数据库操作的顺序,是否有可能以这种方式避免测试变成假测试?
发布于 2021-09-07 06:40:40
我真的想在代码中测试DB操作的细节,方法和往常一样:模拟接收操作的组件,并断言接收到的操作满足某些约束。
例如,您可以断言所有操作都包装到事务边界(显式或隐式)。(为了获得额外的积分,您还可以构造一个内存中的DB,它抛出一个特定的操作,然后断言如果发生这种情况,它的整个状态将保持不变。但在我看来,测试代码做X最好是直接完成,即通过一个在模块上告密的协作者观察它所做的事情。)
https://softwareengineering.stackexchange.com/questions/431692
复制相似问题