Here's what I've finally settled on. We must use @SpringBootTest
to load in the test properties (application-test.yaml
) and get the @Value(..)
, but that unfortunately causes the whole application to run. To block out the real objects being used, and substitute mock objects instead, we can use @SpringBootTest
with @Import(SomeConfiguration.class)
as follows. This will make the mock object get picked up on running the @SpringBootTest
test:
@SpringBootTest
@Import(value = {MockAppServiceConfiguration.class,
MockEmailServiceConfiguration.class}) // etc. any other mocked objects
public class MyTest {
}
example of a Mock Service Configuration:
public class MockEmailServiceConfiguration {
// Replace with mock EmailService when running full-application @SpringBootTest tests
@Bean
public EmailService emailService(){
return new EmailService() {
//... Override any service methods with a mock result (no real processing)
}
Now you can run the test without getting real objects wired. But since we still need to unit-test the actual service class, I manually create my own Service object and do Mockito's testing on it with openMocks / @Mock / @InjectMocks)
. Here's Part 2 for testing the actual Service class:
@SpringBootTest
@Import(value = {MockAr11ApplicationServiceConfiguration.class, /* Prevent the loading of the real Ar11ApplicationService during @SpringBootTest's full-application launch */
MockEmailServiceConfiguration.class}) /* Prevent the loading of the real EmailService during @SpringBootTest's full-application launch */
@ExtendWith(MockitoExtension.class)
public class Ar11ApplicationServiceTest {
// Custom object to be constructed for unit testing, includes DAO sub-object via InjectMocks
@InjectMocks
Ar11ApplicationServiceImpl ar11ApplicationServiceImpl;
// Custom DAO sub-object to be constructed for this unit test via Mock
@Mock
private Ar11ApplicationDAO ar11ApplicationDAO;
@BeforeEach
void setUp() throws Exception {
// Manually construct/wire my own custom objects for unit testing
ar11ApplicationServiceImpl = new Ar11ApplicationServiceImpl();
ar11ApplicationDAO = new Ar11ApplicationDAO();
ar11ApplicationServiceImpl.setAr11ApplicationDAO(ar11ApplicationDAO);
MockitoAnnotations.openMocks(this);
// Set up mock behaviors for the DAO sub-object with when/then
when(ar11ApplicationDAO.method(filename)).thenReturn(..)
doNothing().when(ar11ApplicationDAO).voidMethod(params);