如何验证Mockito是否满足许多条件?是否可以验证是否调用了一个或另一个方法?

时间:2019-04-07 15:34:07

标签: java android junit mockito

在单元测试中,我想检查是否调用了一个或另一个方法。由于Mockito,我可以轻松地验证一些方法被调用了多少次,但是verify没有像“ OR”这样的验证模式。任何解决方法?

在我的情况下,我想检查SharedPreferences.Editor上的名称是.apply()还是.commit(),因为这两种可能性使我满意并保存了数据。不幸的是,如果我致电verify(mEditor).apply(),但由于即时保存的要求,有人将实施方式更改为.commit(),则测试将失败,但不应这样做,因为我只想从这种角度进行测试,如果数据是否保存。这是单元测试,应该独立于此类更改,并且仅检查内部测试的范围。

2 个答案:

答案 0 :(得分:1)

我不知道这样做的好方法,说实话,我认为真正的答案是:。是的,另一个答案显示了一种实现您所要求的方法,但是然后:

您知道生产代码应该做什么。意思是:与其编写允许“ this or that”的 single 验证代码,不如编写两个独立的测试,一个用于“ this”,一个用于“ that” “。

换句话说,您可以控制测试内容。因此,编写一个应导致apply()的测试,并编写一个应导致commit()的测试。然后verify()那个一个案例,预计每个测试都会看到该案例!

单元测试应该简单明了。当某件事失败时,您可以快速查看单元测试,并且您已经知道在生产代码中可以查找到根本原因的位置。任何会增加测试复杂性的事情都可能使之变得更加困难。最好有两个遵循清晰的“何时验证”路径的测试,而不是具有一个(或多个)“然后验证或验证”的测试。

答案 1 :(得分:1)

您要求的解决方法是捕获基础的MockitoAssertionError(或仅捕获AssertionError):

try {
  verify(mEditor).apply();
} catch (MockitoAssertionError mae) {
  // apply was not called. Let's verify commit instead.
  verify(mEditor).commit();
}

或者,如果applycommit都调用某些(内部)save方法,则您也可以尝试验证(假设它是公开的,基于模拟的测试可能会不一致)隐藏信息)。或者,如果您可以控制要测试的代码,则可以按照以下说明进行重构。

但是,更好的建议是,完全避免这种情况的发生,如answer by @GhostCat所述。