У меня есть класс, как показано ниже:
public class A {
public A(String test) {
bla bla bla
}
public String check() {
bla bla bla
}
}
Логика в конструкторе A(String test)
и check()
то, что я пытаюсь высмеять. Я хочу звонки вроде:new A($$$any string$$$).check()
возвращает фиктивную строку "test"
.
Я старался:
A a = mock(A.class);
when(a.check()).thenReturn("test");
String test = a.check(); // to this point, everything works. test shows as "tests"
whenNew(A.class).withArguments(Matchers.anyString()).thenReturn(rk);
// also tried:
//whenNew(A.class).withParameterTypes(String.class).withArguments(Matchers.anyString()).thenReturn(rk);
new A("random string").check(); // this doesn't work
Но похоже, что это не работает. new A($$$any string$$$).check()
по-прежнему выполняет логику конструктора вместо получения фиктивного объекта A
.
Ответы:
Код, который вы разместили, работает для меня с последней версией Mockito и Powermockito. Может ты не подготовил А? Попробуй это:
A.java
public class A { private final String test; public A(String test) { this.test = test; } public String check() { return "checked " + this.test; } }
MockA.java
import static org.hamcrest.MatcherAssert.assertThat; import static org.hamcrest.Matchers.equalTo; import static org.mockito.Mockito.mock; import static org.mockito.Mockito.when; import org.junit.Test; import org.junit.runner.RunWith; import org.mockito.Mockito; import org.powermock.api.mockito.PowerMockito; import org.powermock.core.classloader.annotations.PrepareForTest; import org.powermock.modules.junit4.PowerMockRunner; @RunWith(PowerMockRunner.class) @PrepareForTest(A.class) public class MockA { @Test public void test_not_mocked() throws Throwable { assertThat(new A("random string").check(), equalTo("checked random string")); } @Test public void test_mocked() throws Throwable { A a = mock(A.class); when(a.check()).thenReturn("test"); PowerMockito.whenNew(A.class).withArguments(Mockito.anyString()).thenReturn(a); assertThat(new A("random string").check(), equalTo("test")); } }
Оба теста должны пройти с mockito 1.9.0, powermockito 1.4.12 и junit 4.8.2.
источник
PrepareForTest
Насколько мне известно, вы не можете имитировать конструкторы с помощью mockito, только методы. Но согласно вики на кодовой странице Mockito google, есть способ имитировать поведение конструктора, создав метод в вашем классе, который возвращает новый экземпляр этого класса. тогда вы можете издеваться над этим методом. Ниже приведен отрывок непосредственно из вики Mockito :
Если вы просто хотите вернуть фиктивный объект своего класса, я думаю, это должно сработать для вас. В любом случае вы можете узнать больше о создании mocking-объекта здесь:
http://code.google.com/p/mockito/wiki/MockingObjectCreation
источник
Без использования Powermock ... См. Пример ниже, основанный на ответе Бена Глассера, так как мне потребовалось некоторое время, чтобы понять это ... надеюсь, что это сэкономит несколько раз ...
Исходный класс:
public class AClazz { public void updateObject(CClazz cClazzObj) { log.debug("Bundler set."); cClazzObj.setBundler(new BClazz(cClazzObj, 10)); } }
Модифицированный класс:
@Slf4j public class AClazz { public void updateObject(CClazz cClazzObj) { log.debug("Bundler set."); cClazzObj.setBundler(getBObject(cClazzObj, 10)); } protected BClazz getBObject(CClazz cClazzObj, int i) { return new BClazz(cClazzObj, 10); } }
Тестовый класс
public class AClazzTest { @InjectMocks @Spy private AClazz aClazzObj; @Mock private CClazz cClazzObj; @Mock private BClazz bClassObj; @Before public void setUp() throws Exception { Mockito.doReturn(bClassObj) .when(aClazzObj) .getBObject(Mockito.eq(cClazzObj), Mockito.anyInt()); } @Test public void testConfigStrategy() { aClazzObj.updateObject(cClazzObj); Mockito.verify(cClazzObj, Mockito.times(1)).setBundler(bClassObj); } }
источник
С mockito вы можете использовать withSettings (), например, если CounterService требовал 2 зависимости, вы можете передать их как имитацию:
UserService userService = Mockito.mock(UserService.class); SearchService searchService = Mockito.mock(SearchService.class); CounterService counterService = Mockito.mock(CounterService.class, withSettings().useConstructor(userService, searchService));
источник
Mockito имеет ограничения по тестированию final, статических и частных методов.
с библиотекой тестирования jMockit вы можете сделать несколько вещей очень простыми и понятными, как показано ниже:
Мок-конструктор класса java.io.File:
new MockUp<File>(){ @Mock public void $init(String pathname){ System.out.println(pathname); // or do whatever you want } };
Смоделируйте статический метод:
источник