有没有办法验证在 Mockito 中是否在 methodTwo
之前调用了 methodOne
?
public class ServiceClassA {
public void methodOne(){}
}
public class ServiceClassB {
public void methodTwo(){}
}
public class TestClass {
public void method(){
ServiceClassA serviceA = new ServiceClassA();
ServiceClassB serviceB = new ServiceClassB();
serviceA.methodOne();
serviceB.methodTwo();
}
}
InOrder
可帮助您做到这一点。
ServiceClassA firstMock = mock(ServiceClassA.class);
ServiceClassB secondMock = mock(ServiceClassB.class);
Mockito.doNothing().when(firstMock).methodOne();
Mockito.doNothing().when(secondMock).methodTwo();
//create inOrder object passing any mocks that need to be verified in order
InOrder inOrder = inOrder(firstMock, secondMock);
//following will make sure that firstMock was called before secondMock
inOrder.verify(firstMock).methodOne();
inOrder.verify(secondMock).methodTwo();
请注意,您还可以使用 InOrder 类来验证是否在单个模拟上按顺序调用各种方法,而不仅仅是在两个或多个模拟上。
假设我有两个类 Foo
和 Bar
:
public class Foo {
public void first() {}
public void second() {}
}
public class Bar {
public void firstThenSecond(Foo foo) {
foo.first();
foo.second();
}
}
然后我可以添加一个测试类来测试 Bar
的 firstThenSecond()
方法实际调用 first()
,然后是 second()
,而不是 second()
,然后是 first()
。请看以下测试代码:
public class BarTest {
@Test
public void testFirstThenSecond() {
Bar bar = new Bar();
Foo mockFoo = Mockito.mock(Foo.class);
bar.firstThenSecond(mockFoo);
InOrder orderVerifier = Mockito.inOrder(mockFoo);
// These lines will PASS
orderVerifier.verify(mockFoo).first();
orderVerifier.verify(mockFoo).second();
// These lines will FAIL
// orderVerifier.verify(mockFoo).second();
// orderVerifier.verify(mockFoo).first();
}
}
find('foo')
,然后是 find('bar')
doNothing()
更典型的用法
是的,这在文档中有所描述。您必须使用 InOrder 类。
示例(假设已经创建了两个模拟):
InOrder inOrder = inOrder(serviceAMock, serviceBMock);
inOrder.verify(serviceAMock).methodOne();
inOrder.verify(serviceBMock).methodTwo();
对于 Kotlin 用户,您可以这样:
class MyTrackerTest {
private val trackEventUseCase: TrackEventUseCase = mock()
private val sut = MyTracker(trackEventUseCase)
@Test
fun `trackSomething SHOULD invoke tracker use case twice with correct event names WHEN called`() {
sut.trackSomething()
trackEventUseCase.inOrder {
verify().invoke("Is it August?")
verify().invoke("No!")
}
}
}
使用 BDD
@Test
public void testOrderWithBDD() {
// Given
ServiceClassA firstMock = mock(ServiceClassA.class);
ServiceClassB secondMock = mock(ServiceClassB.class);
//create inOrder object passing any mocks that need to be verified in order
InOrder inOrder = inOrder(firstMock, secondMock);
willDoNothing().given(firstMock).methodOne();
willDoNothing().given(secondMock).methodTwo();
// When
firstMock.methodOne();
secondMock.methodTwo();
// Then
then(firstMock).should(inOrder).methodOne();
then(secondMock).should(inOrder).methodTwo();
}
willDoNothing()
在那里做什么?参考在哪里?为什么在前面?
不定期副业成功案例分享
inOrder.verifyNoMoreInteractions();
以验证没有进行其他调用。inOrder(firstMock, secondMock)
和inOrder(secondMock, firstMock)
的结果是否相同?也许您可以更新答案以对此进行说明。