Skip to the content.

What type of tests typically use Spring?

The Spring Framework provides first-class support for integration testing in the spring-test module.

How can you create a shared application context in a JUnit integration test?

The Spring TestContext Framework provides consistent loading of Spring ApplicationContext instances and WebApplicationContext instances as well as caching of those contexts. Support for the caching of loaded contexts is important, because startup time can become an issue.By default, once loaded, the configured ApplicationContext is reused for each test. Thus, the setup cost is incurred only once per test suite, and subsequent test execution is much faster. To create shared application context you have to annotate a JUnit 4 based test class with @RunWith(SpringJUnit4ClassRunner.class) or @RunWith(SpringRunner.class). However, @RunWith will try to initialize default @ContextConfiguration:

When and where do you use @Transactional in testing?

Annotating a test method with @Transactional causes the test to be run within a transaction that is, by default, automatically rolled back after completion of the test. If a test class is annotated with @Transactional, each test method within that class hierarchy runs within a transaction. Test methods that are not annotated with @Transactional (at the class or method level) are not run within a transaction. Furthermore, tests that are annotated with @Transactional but have the propagation type set to NOT_SUPPORTED are not run within a transaction.Also, you can create custom annotations to include more than one spring test annotation:

@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
@Transactional
@Tag("integration-test") // org.junit.jupiter.api.Tag
@Test // org.junit.jupiter.api.Test
public @interface TransactionalIntegrationTest {}

How are mock frameworks such as Mockito or EasyMock used?

Mockito lets you write tests by mocking the external dependencies with the desired behavior. Mock objects have the advantage over stubs in that they are created dynamically and only for the specific scenario tested.

Steps of using Mockito:

  1. Declare and create the mock
  2. Inject the mock
  3. Define the behavior of the mock
  4. Test
  5. Validate the execution
public class SimpleReviewServiceTest {

  private ReviewRepo reviewMockRepo = mock(ReviewRepo.class); // (1)
  private SimpleReviewService simpleReviewService;
  
  @Before
  public void setUp(){
    simpleReviewService = new SimpleReviewService();
    simpleReviewService.setRepo(reviewMockRepo); //(2)
  }
  
  @Test
  public void findByUserPositive() {
    User user = new User();
    Set<Review> reviewSet = new HashSet<>();
    when(reviewMockRepo.findAllForUser(user)).thenReturn(reviewSet);// (3)
    Set<Review> result = simpleReviewService.findAllByUser(user); // (4)
    assertEquals(result.size(), 1); //(5)
  }
}

Mockito with Annotations

public class MockPetServiceTest {

  @InjectMocks
  SimplePetService simplePetService;
  
  @Mock
  PetRepo petRepo;
  
  @Before
  public void initMocks() {
    MockitoAnnotations.initMocks(this);
  }
  
  @Test p
  ublic void findByOwnerPositive() {
    Set<Pet> sample = new HashSet<>();
    sample.add(new Pet());
    Mockito
      .when(petRepo.findAllByOwner(owner))
      .thenReturn(sample);

    Set<Pet> result = simplePetService.findAllByOwner(owner);

    assertEquals(result.size(), 1); }
  }
}

Mockito in Spring Boot

@MockBean

How is @ContextConfiguration used?

@ContextConfiguration defines class-level metadata that is used to determine how to load and configure an ApplicationContext for integration tests. Specifically, @ContextConfiguration declares the application context resource locations or the annotated classes used to load the context. Resource locations are typically XML configuration files or Groovy scripts located in the classpath, while annotated classes are typically @Configuration classes. However, resource locations can also refer to files and scripts in the file system, and annotated classes can be component classes, and so on.

@ContextConfiguration("/test-config.xml")
public class XmlApplicationContextTests {
    // class body...
}
@ContextConfiguration(classes = TestConfig.class)
public class ConfigClassApplicationContextTest {
    // class body...
}

As an alternative or in addition to declaring resource locations or annotated classes, you can use @ContextConfiguration to declare ApplicationContextInitializer classes. The following example shows such a case:

@ContextConfiguration(initializers = CustomContextIntializer.class)
public class ContextInitializaerTests {
    // class body...
}

You can optionally use @ContextConfiguration to declare the ContextLoader strategy as well. Note, however, that you typically do not need to explicitly configure the loader, since the default loader supports initializers and either resource locations or annotated classes.

@ContextConfiguration(locations = "/test-context.xml", loader = CustomContextLoader.class)
public class CustomLoaderXmlApplicationContextTests {
    // class body...
}

How does Spring Boot simplify writing tests?

Spring Boot provides a number of utilities and annotations to help when testing your application. Test support is provided by two modules: spring-boot-test contains core items, and spring-boot-test-autoconfigure supports auto-configuration for tests.Most developers use the spring-boot-starter-test “Starter”, which imports both Spring Boot test modules as well as JUnit, AssertJ, Hamcrest, and a number of other useful libraries. Spring Boot provides a @SpringBootTest annotation, which can be used as an alternative to the standard spring-test @ContextConfiguration annotation when you need Spring Boot features. The annotation works by creating the ApplicationContext used in your tests through SpringApplication. When testing Spring Boot applications, this is often not required. Spring Boot’s @*Test annotations search for your primary configuration automatically whenever you do not explicitly define one.The search algorithm works up from the package that contains the test until it finds a class annotated with @SpringBootApplication or @SpringBootConfiguration. By default, @SpringBootTest will not start a server. You can use the webEnvironment attribute of @SpringBootTest to further refine how your tests run:

Additional annotations:

What does @SpringBootTest do? How does it interact with @SpringBootApplication and @SpringBootConfiguration?

Annotation that can be specified on a test class that runs Spring Boot based tests. Provides the following features over and above the regular Spring TestContext Framework:

How does it interact with @SpringBootApplication and @SpringBootConfiguration?

When testing Spring Boot applications, this is often not required. Spring Boot’s @*Test annotations search for your primary configuration automatically whenever you do not explicitly define one.The search algorithm works up from the package that contains the test until it finds a class annotated with @SpringBootApplication or @SpringBootConfiguration. As long as you structured your code in a sensible way, your main configuration is usually found.

References

  1. MrR0807 Spring certification notes
  2. Moss Green Spring certification notes
  3. Spring Documentation
  4. Spring Boot Documentation