在关于GWT的教程中,Google使用不同的方法来执行MVP,View指定Presenter或Presenter指定View。使用活动和地点时使用第一个。
这篇文章涉及这个主题:MVP: Should the View implement a Presenter's interface or vice versa?
但是,我想知道在演示者和视图的单元测试方面,您认为哪种方案最佳?或者两者同样有效?
答案 0 :(得分:4)
演示者单元测试背后的想法是模拟视图,并针对此模拟视图的状态编写几个断言,这些视图将在现实生活应用中以可视方式表示。由于这种方法,不需要运行完整的GWTTestCase
,这需要花费大量时间,而应该放在集成测试的类别中,而不是单元测试。
如果您尝试两种MVP方法,单元测试可能如下所示:
MVP 1:
@Test
public void shouldAddContactOnAddContactClicked() {
// given
ContactsPresenter.Display display = mock(ContactsPresenter.Display.class);
MockButton addButton = new MockButton();
given(display.getAddButton()).willReturn(addButton);
ContactsDisplay.Presenter presenter = new ContactsPresenter();
presenter.bindView(display);
presenter.setContacts(new ArrayList<Contact>());
// when
addButton.click();
// then
verify(display).addContact(any());
assertThat(presenter.getContacts().size(), is(1));
}
MockButton
是我在这里描述的内容:
Comprehensive Pros/Cons of Mocking Frameworks for GWT
尽管可能,以这种方式嘲笑事情并不是很方便。 MVP2方法似乎表现更好:
@Test
public void shouldAddContactOnAddContactClicked() {
// given
ContactsView view = mock(ContactsView.class);
ContactsView.Presenter presenter = new ContactsPresenter();
presenter.bindView(view); // assuming that presenter will call view.setPresenter(this)
presenter.setContacts(new ArrayList<Contact>());
// when
presenter.onAddContactClicked();
// then
verify(view).addContact(any());
assertThat(presenter.getContacts().size(), is(1));
}
使用第二种方法的另一个原因是MVP1中的问题是声明显示的元素,这会触发不同的事件(例如ClickEvent,FocusEvent)。在UiBinder
时,MVP2也使事情变得更容易。
答案 1 :(得分:3)
避免使用HasXxxHandlers
,即使用part 2文章中的方法,其中每个对等方都引用另一个。 HasXxxHandlers
过于复杂,无法模仿,特别是在使用Mockito或EasyMock等模拟库时。
为了获得最佳可测试性,您需要将视图注入演示者,然后演示者将调用视图的setPresenter
或setDelegate
方法(这样,您可以对您正确调用该方法进行单元测试,在合适的时间)。使用活动时,如果您的活动是演示者,则可能会在view.setPresenter(this)
和start
以及view.setPresenter(null)
中调用onStop
和onCancel
;通过这种方式,您可以与多个演示者共享一个单独的视图(尽管一次只有一个,但很明显)。
答案 2 :(得分:0)
单元测试,它确实没关系。如果你设计得恰到好处,那只需要注入存根(或模拟)就可以了。不应允许单元测试决定设计决策。但是,单元测试通常会指示设计是否错误(例如缺少注射等)