У меня есть интерфейс (клиент) с двумя классами реализации PClient и SClient соответственно.
Interface - Client
Impl class - PCleint, SClient
У меня есть контроллер, в котором оба класса impl автоматически подключены с использованием аннотации загрузки квалификатора spring. Теперь мне нужно написать тестовый пример JUNIT mockito для контроллера.
Я не уверен, как издеваться над разными классами Impl с одинаковым интерфейсом. Я пробовал издеваться следующим образом, но он выдает исключение нулевого указателя в методе заглушки соответствующих макетов.
@Mock
private Client pclient
@Mock
private Client sclient
Как отличить имитацию разных классов impl таким образом, чтобы вызывались методы классов impl. Должен ли я сделать, как показано ниже.
@Mock
private PClient pclient
@Mock
private SClient sclient
У меня не получилось. Либо выдает исключение с нулевым указателем. Пожалуйста, порекомендуйте.




Я предполагаю, что уловки в том, что вам нужно использовать Before для заглушки возвращаемого значения и использовать @InjectMocks для контроллера.
Поскольку @Mock не возвращает «настоящий» объект, он просто возвращает «фиктивный» (или фальшивый: P) объект. Поэтому, когда вы вызываете метод этого «фиктивного» объекта, он не возвращает фактический результат вашего метода, вместо этого он возвращает null. Вот почему вам нужно заглушить возврат с помощью @Before.
См. Мой пример кода ниже:
Клиентский интерфейс
public interface Client {
String someMethod();
}
Класс реализован
public class PClient implements Client {
private static final String name = "PClient";
@Override
public String someMethod() {
return name;
}
}
public class SClient implements Client{
private static final String name = "SClient";
@Override
public String someMethod() {
return name;
}
}
Клиентский контроллер
@Controller public class ClientController {
@Autowired
private PClient pClient;
@Autowired
private SClient sClient;
public ClientController(){
}
public String executePClient(){
return this.pClient.someMethod();
}
public String executeSClient(){
return this.sClient.someMethod();
}
public String execute(Client client){
return client.someMethod();
}
}
Тестовый пример Вам нужно добавить @Before, чтобы заглушить возврат метода.
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.InjectMocks;
import org.mockito.Mock;
import org.mockito.junit.MockitoJUnitRunner;
import static org.junit.Assert.assertEquals;
import static org.mockito.Mockito.when;
@RunWith(MockitoJUnitRunner.class)
public class ClientControllerTest {
@Mock
private PClient pclient;
@Mock
private SClient sclient;
@InjectMocks
private ClientController clientController;
@Before
public void setup(){
when(pclient.someMethod()).thenReturn(new PClient().someMethod());
when(sclient.someMethod()).thenReturn(new SClient().someMethod());
}
@Test
public void testPClient(){
String result = clientController.executePClient();
assertEquals("PClient",result);
}
@Test
public void testSClient(){
String result = clientController.executeSClient();
assertEquals("SClient",result);
}
@Test
public void testExecuteWithPClient(){
String result = clientController.execute(pclient);
assertEquals("PClient",result);
}
@Test
public void testExecuteWithSClient(){
String result = clientController.execute(sclient);
assertEquals("SClient",result);
}
}
Результат: Пройдено тестов: 4 из 4 тестов - 31 мс
Вы имеете в виду передать "Клиент" в конструктор, а затем протестировать его?
У меня вопрос. Я использую метод инициализации, могу ли я вставить его в него вместо настройки