Макет класса в тестируемом классе
Как я могу издеваться с другими классами в моем классе, который находится под тестом?
Например:
Микласс.java
class MyClass {
public boolean performAnything() {
AnythingPerformerClass clazz = new AnythingPerformerClass();
return clazz.doSomething();
}
}
AnythingPerformerClass.java
class AnythingPerformerClass {
public boolean doSomething() {
//very very complex logic
return result;
}
}
И тест:
@Test
public void testPerformAnything() throws Exception {
MyClass clazz = new MyClass();
Assert.assertTrue(clazz.performAnything());
}
Могу ли я подделать AnythingPerformerClass для исключения ненужной логики из AnythingPerformerClass? Могу ли я переопределить метод doSomething() для простого возврата true или false?
Почему я указываю Mockito, потому что он мне нужен для тестирования Android с Robolectric.
3 ответа:
Вы можете рефакторировать
MyClassтак, чтобы он использовал инъекцию зависимостей. Вместо того, чтобы создавать экземплярAnythingPerformerClass, Вы можете передать экземпляр класса конструкторуMyClassследующим образом:class MyClass { private final AnythingPerformerClass clazz; MyClass(AnythingPerformerClass clazz) { this.clazz = clazz; } public boolean performAnything() { return clazz.doSomething(); } }Затем вы можете передать макет реализации в модульном тесте
@Test public void testPerformAnything() throws Exception { AnythingPerformerClass mockedPerformer = Mockito.mock(AnythingPerformerClass.class); MyClass clazz = new MyClass(mockedPerformer); ... }Альтернативно, если ваш
AnythingPerformerClassсодержит состояние, то вы можете передатьAnythingPerformerClassBuilderконструктору.
Как это в настоящее время (как объявление, так и создание экземпляра
AnythingPerformerClassвнутри метода, невозможно издеваться надAnythingPerformerClass, используя только Mockito.Если возможно, переместите объявление и создание экземпляра
AnythingPerformerClassна уровень класса: объявите переменную экземпляра типаAnythingPerformerClassи создайте ее экземпляр конструктором.Таким образом, вы могли бы более легко ввести Макет
AnythingPerformerClassво время теста и указать его поведение. Например:when(anythingPerformerClassMock.doSomething()).thenReturn(true);Или проверить ошибку обработка:
when(anythingPerformerClassMock.doSomething()).thenTrow(new NullPointerException());