[英]Test if another method was called
所以我確定那里有類似的東西,但我一直在尋找一個小時,並沒有找到我正在尋找的東西。 說我有一個看起來像這樣的課:
public class MyClass
{
public void myMethod(boolean shouldCallOtherMethod)
{
if(shouldCallOtherMethod)
{
otherMethod();
}
}
public void otherMethod()
{
System.out.println("Called");
}
}
我如何制作這樣的作品呢?
@Test
public void shouldCallMethod()
{
MyClass myClass = new MyClass();
myClass.myMethod(true)
// verify myClass.otherMethod method was called
}
假設MokeysClass
有一個像這樣聲明的構造函數,其中Foo
是其他類。
public MokeysClass(String name, int counter, Foo myFoo)
我會像這樣寫我的測試。
@RunWith(MockitoJUnitRunner.class)
public class TestArray {
@Mock
private Foo mockMyFoo;
private String nameToInject = "Mokey";
private int counterToInject = 42;
@Spy
private MokeysClass toTest = new MokeysClass(nameToInject, counterToInject, mockMyFoo);
@Test
public void shouldCallMethod() {
toTest.myMethod(true);
verify(toTest).otherMethod();
}
}
所以我明確說明在創建測試對象時要調用哪個構造函數,以及傳遞給它的參數。
有一些原因不依賴@InjectMocks
為我執行此步驟,特別是如果被測試的類更復雜並且具有多個構造函數。 Mockito選擇具有最多參數的構造函數,但如果有多個構造函數具有相同數量的參數,Mockito可以選擇任何構造函數; 也就是說,行為是未定義的。
一旦Mockito選擇了構造函數,它就會檢查該構造函數是否實際上可以用於構造函數注入。 如果,將不使用構造函數注入
如果這些條件中的任何一個成立,對於Mockito選擇的構造函數,則不會使用構造函數注入。 在這種情況下,類必須具有默認構造函數,否則Mockito將拋出異常。
選擇是否應用構造函數注入時Mockito使用的標准的復雜性意味着添加或刪除構造函數,或更改構造函數的參數,可以使Mockito從使用構造函數注入切換到使用setter和field注入; 或者使用setter和field injection來使用構造函數注入。 即使更改的構造函數不是將用於構造函數注入的構造函數,也會發生這種情況。
因此,任何使用構造函數注入的測試都會自動變得非常脆弱; 從某種意義上說,與測試本身沒有直接關系的變化會導致測試失敗。 這樣的故障可能很難排除故障。
@InjectMocks
注釋旨在用於執行依賴注入的Spring等框架; 對於使用Spring的類的測試,它可能是非常寶貴的。 但是如果依賴注入不屬於你的類,我強烈建議避免使用@InjectMocks
它的脆弱性。 您確實希望您的測試代碼像生產代碼一樣易於維護和排除故障。
這不推薦 ,但你可以窺探真實的對象:)
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Spy;
import org.mockito.runners.MockitoJUnitRunner;
import static org.mockito.BDDMockito.verify;
@RunWith(MockitoJUnitRunner.class)
public class MyClassTest {
@Spy
private MyClass sut; // System Under Test
@Test
public void shouldCallMethod() {
// when
sut.myMethod(true);
// then
verify(sut).otherMethod();
}
}
結果:
Tests Passed: 1 passed in 0,203 s
更改代碼后: sut.myMethod(false);
Wanted but not invoked:
sut.otherMethod();
-> at my.custom.MyClassTest.shouldCallMethod(MyClassTest.java:23)
來源: 對真實物體進行間諜活動
@Mock
private LexAnalyzer lexAnalyzer;
@Spy
@InjectMocks
private SyntaxAnalyzer sut; // System Under Test
@Test
public void shouldCallMethod() {
// when
sut.myMethod(true);
// then
verify(sut).otherMethod();
}
SyntaxAnalyzer.java
public class SyntaxAnalyzer {
private final LexAnalyzer lexAnalyzer;
public SyntaxAnalyzer(LexAnalyzer lexAnalyzer) {
this.lexAnalyzer = lexAnalyzer;
}
...
經過測試,有效;)
我想你想看看Mock對象。 您可以創建MyClass的模擬,然后設置在調用myMethod時調用otherMethod()的期望,如果未調用則調整失敗。
以下是對java的非常好的概述 - http://www.scalatest.org/user_guide/testing_with_mock_objects
使用Mocks的另一個主要好處是,您可以避免在測試中產生副作用,例如記錄到NSLog或訪問Web服務器或打印。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.