2017-03-02 100 views
3

我有一個Android應用程序,我正在努力爲它編寫單元測試。該應用程序是用MVP架構編寫的,我試圖測試Presenter類。Android:JUnit + Mockito,測試回調?

簡化方法我想測試看起來是這樣的:

public void userPressedButton() { 
    service.loadData(new Callback<Data>{ 
     @Override 
     onResponse(Data data) { 
      view.showData(data); 
     } 
    }); 
} 

現在我想確認的是,當userPressedButton方法被調用view.showData(data)被調用。

我嘗試了幾種方法,但我似乎無法弄清楚如何測試這個。

任何想法?

編輯:爲了澄清,我想寫一個單元測試

+0

只是要確定。你想寫單元測試嗎?不是綜合測試 –

+0

Maciej Kowalski是的,這是正確的! – JesperQv

回答

1

有趣的案例。

我會做的是:

1) - 該特定回調創建一個具體類:

public class MyCallback implements Callback<Data>{ 

    private View view; 

    public MyCallback(View view){ 
     this.view = view; 
    } 

    @Override 
    onResponse(Data data) { 
     view.showData(data); 
    } 
} 

現在對於這個類,你可以寫一個單元測試,這將檢查是否onResponse方法調用view字段的showData方法。

2)已經extacted落實到一個具體的類,從包含userPressedButton方法的類的角度來看,它真的不是必要的回調類的裏面發生了什麼。 重要的是,該接口的具體實現已通過:

public void userPressedButton() { 
    service.loadData(new MyCallback(view)); 
} 

最後測試:

@InjectMocks 
MyClass myClass; 

@Mock 
Service service; 

@Captor 
ArgumentCaptor argCaptor; 

@Before 
public void init(){ 
    MockitoAnnotations.initMocks(this); 
} 

@Test 
public void shouldUseMyCallback(){ 
    // Arrange 

    // set up myClass for test 

    // Act 
    myClass.userPressedButton(); 

    Mockito.verify(service).loadData(argCaptor.capture()); 

    // Assert 
    assertTrue(argCaptor.getValue instance of MyCallback); 
} 

所以我們檢查loadData方法是否調用了適當的實現。

這就是我將如何測試你的情況。

0

你可以「儲存」的回調,並在測試期間使用測試回調

class YourClass { 

    private ??? view; 
    private Callback<Data> callback; 

    // for testing purposes 
    protected YouClass(Callback<Data> callback) { 
     this.callback = callback; 
    } 

    public YouClass() { 
     this(new Callback<Data>{ 
      @Override 
      onResponse(Data data) { 
       view.showData(data); 
      } 
     }); 
    } 

    public void userPressedButton() { 
     service.loadData(this.callback); 
    } 
} 

然後使用一些自定義的回調測試

-1

更簡單的解決方案。如果這是MVP,則可以將view實例傳遞給演示者類。然後在Mock上測試調用。

這是一個測試方法是什麼樣子:

MVPView view = mock(MVPView.class); 
Presenter presenter = new Presenter(view) 
presenter.userPressedButton(); 
verify(view, atLeastOnce()).showData(any(Data.class)); 

如果呼叫asynchronious,然後等待結果,通過修改最後聲明:

verify(view, timetout(5000).atLeastOnce()).showData(any(Data.class)); 
+0

謝謝你的回答!即使loadData方法進行網絡調用,這是否也能工作? – JesperQv

+0

然後,你也必須模擬「服務」行爲。 –