1. Introduction

In this quick article, we’ll take a look at the new @SpringJUnitConfig and @SpringJUnitWebConfig annotations available in Spring and Spring Boot.

These annotations are a composition of JUnit 5 and Spring annotations that make test creation easier and faster.

2. @SpringJUnitConfig

@SpringJUnitConfig combines these 2 annotations:

  • @ExtendWith(SpringExtension.class) from JUnit 5 to run the test with the SpringExtension class and
  • @ContextConfiguration from Spring Testing to load the Spring context

2.1. Test Configuration

Let’s create a test and use this annotation in practice:

@SpringJUnitConfig(SpringJUnitConfigIntegrationTest.Config.class)
public class SpringJUnitConfigIntegrationTest {

    @Configuration
    static class Config {}
}

Notice that, in contrast to the @ContextConfiguration, configuration classes are declared using the value attribute. However, resource locations should be specified with the locations attribute.

We can now verify that the Spring context was really loaded:

@Autowired
private ApplicationContext applicationContext;

@Test
void givenAppContext_WhenInjected_ThenItShouldNotBeNull() {
    assertNotNull(applicationContext);
}

Finally, here we have the equivalent code of @SpringJUnitConfig(SpringJUnitConfigTest.Config.class):

@ExtendWith(SpringExtension.class)
@ContextConfiguration(classes = SpringJUnitConfigTest.Config.class)

2.2. The loader Attribute

One of the attributes of @ContextConfiguration named loader wasn’t an attribute in @SpringJUnitConfig when it was initially released. In a case where we need to explicitly set a custom loader, we have to revert to the lower-level annotations:

@ExtendWith(SpringExtension.class)
@ContextConfiguration(loader = SpringConfigTest.class)

As of Spring version 6 and Spring Boot version 3.2.0, the loader attribute is available as a parameter in the @SpringJUnitConfig annotation. This provides support for configuring a custom ContextLoader or SmartContextLoader.

For example, let’s explicitly specify annotation-based loading directly in the @SpringJUnitConfig annotation:

@SpringJUnitConfig(classes = TestConfig.class, loader = AnnotationConfigContextLoader.class)
public class SpringJUnitConfigurationUnitTest {
    @ParameterizedTest
    @ValueSource(strings = { "Dilbert", "Wally" })
    void whenSetPeopleWithName_thenListContainsOnePerson(String name, @Autowired List people) {
        assertThat(people.stream()
          .map(Person::getName)
          .filter(name::equals)).hasSize(1);
    }
}

Using the loader attribute, we have a simpler test configuration without the need for multiple annotations.

3. @SpringJUnitWebConfig

@SpringJUnitWebConfig combines the same annotations of @SpringJUnitConfig plus the @WebAppConfiguration from Spring testing – to load the WebApplicationContext.

Let’s see how this annotation works:

@SpringJUnitWebConfig(SpringJUnitWebConfigIntegrationTest.Config.class)
public class SpringJUnitWebConfigIntegrationTest {

    @Configuration
    static class Config {
    }
}

Like @SpringJUnitConfig, the configuration classes go in the value attribute, and any resources are specified using the locations attribute.

Also, the value attribute of @WebAppConfiguration should now be specified using the resourcePath attribute. By default, this attribute is set to “src/main/webapp”.

Let’s now verify that the WebApplicationContext was really loaded:

@Autowired
private WebApplicationContext webAppContext;

@Test
void givenWebAppContext_WhenInjected_ThenItShouldNotBeNull() {
    assertNotNull(webAppContext);
}

Again, here we have the equivalent code without using @SpringJUnitWebConfig:

@ExtendWith(SpringExtension.class)
@WebAppConfiguration
@ContextConfiguration(classes = SpringJUnitWebConfigIntegrationTest.Config.class)

Similarly, Spring version 6 and Spring Boot version 3.2.0 add loader support to @SpringJUnitWebConfig to configure a custom context loader for tests. This gives the annotation the full capabilities of @ContextConfiguration annotation.

4. Conclusion

In this brief tutorial, we showed how to use the introduced @SpringJUnitConfig and @SpringJUnitWebConfig annotations in Spring 5 and above.

As always, the full source code for the examples is available over on GitHub.