Partner – Microsoft – NPI (cat= Spring)
announcement - icon

Azure Spring Apps is a fully managed service from Microsoft (built in collaboration with VMware), focused on building and deploying Spring Boot applications on Azure Cloud without worrying about Kubernetes.

And, the Enterprise plan comes with some interesting features, such as commercial Spring runtime support, a 99.95% SLA and some deep discounts (up to 47%) when you are ready for production.

>> Learn more and deploy your first Spring Boot app to Azure.

You can also ask questions and leave feedback on the Azure Spring Apps GitHub page.

1. Overview

The hybrid definition of beans in a Spring Boot application is one that includes both an Annotation-Based and XML-Based configuration. In this environment, we may want to use the XML-Based configuration in the test classes. However, sometimes in this situation, we may encounter the application context loading error “Failed to load ApplicationContext.” This error appears in the test classes because the application context isn’t loaded in the test context.

In this tutorial, we’ll discuss how to integrate the XML application context into testing in a Spring Boot application.

Further reading:

Testing in Spring Boot

Learn about how the Spring Boot supports testing, to write unit tests efficiently.

Integration Testing in Spring

A quick guide to writing integration tests for a Spring Web application.

Spring Boot Error ApplicationContextException

Learn how to solve the ApplicationContextException in Spring Boot.

2. “Failed to load ApplicationContext” Error

Let’s reproduce the error by integrating the XML-Based application context in a Spring Boot application.

First, let’s suppose we have an application-context.xml file with the definition of a service bean:

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="
    http://www.springframework.org/schema/beans 
    http://www.springframework.org/schema/beans/spring-beans.xsd">
	  
    <bean id="employeeServiceImpl" class="com.baeldung.xmlapplicationcontext.service.EmployeeServiceImpl" />
</beans>

Now we can add the application-context.xml file in the webapp/WEB-INF/ location:

ApplicationContextDirecory

We’ll also create a service interface and class:

public interface EmployeeService {
    Employee getEmployee();
}

public class EmployeeServiceImpl implements EmployeeService {

    @Override
    public Employee getEmployee() {
        return new Employee("Baeldung", "Admin");
    }
}

Finally, we’ll create a test case for getting the EmployeeService bean from the application context:

@RunWith(SpringRunner.class)
@ContextConfiguration(locations={"classpath:WEB-INF/application-context.xml"})
public class EmployeeServiceAppContextIntegrationTest {

    @Autowired
    private EmployeeService service;

    @Test
    public void whenContextLoads_thenServiceISNotNull() {
        assertThat(service).isNotNull();
    }

}

Now if we try to run this test, we’ll observe the error:

java.lang.IllegalStateException: Failed to load ApplicationContext

This error appears in the test classes because the application context isn’t loaded in the test context. Moreover, the root cause is that the WEB-INF isn’t included in the classpath:

@ContextConfiguration(locations={"classpath:WEB-INF/application-context.xml"})

3. Using an XML-Based ApplicationContext in Test

Let’s see how we can use an XML-Based ApplicationContext in test classes. We have two options to use the XML-Based ApplicationContext in the test: @SpringBootTest and @ContextConfiguration annotations.

3.1. Test Using @SpringBootTest and @ImportResource

Spring Boot provides the @SpringBootTest annotation, which we can use to create an application context to be used in a test. In addition, we must use @ImportResource in the Spring Boot main class for reading XML beans. This annotation allows us to import one or more resources containing bean definitions.

First, let’s use the @ImportResource annotation in the main class:

@SpringBootApplication
@ImportResource({"classpath*:application-context.xml"})

Now let’s create a test case for getting EmployeeService bean from the application context:

@RunWith(SpringRunner.class)
@SpringBootTest(classes = XmlBeanApplication.class)
public class EmployeeServiceAppContextIntegrationTest {

    @Autowired
    private EmployeeService service;

    @Test
    public void whenContextLoads_thenServiceISNotNull() {
        assertThat(service).isNotNull();
    }

}

The @ImportResource annotation loads XML beans located in the resource directory. In addition, the @SpringBootTest annotation loads the whole application’s beans in the test class. Therefore, we’re able to access the EmployeeService bean in the test class.

3.2. Test Using @ContextConfiguration With resources

We can create our test context with different configurations of beans by placing our test configuration file in the src/test/resources directory.

In this case, we use the @ContextConfiguration annotation for loading the test context from the src/test/resources directory.

First, let’s create another bean from the EmployeeService interface:

public class EmployeeServiceTestImpl implements EmployeeService {

    @Override
    public Employee getEmployee() {
        return new Employee("Baeldung-Test", "Admin");
    }
}

Then we’ll create the test-context.xml file in the src/test/resources directory:

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://www.springframework.org/schema/beans 
    http://www.springframework.org/schema/beans/spring-beans.xsd">
	
    <bean id="employeeServiceTestImpl" class="process.service.EmployeeServiceTestImpl" />
</beans>

Finally, we’ll create the test case:

@SpringBootTest
@ContextConfiguration(locations = "/test-context.xml")
public class EmployeeServiceTestContextIntegrationTest {

    @Autowired
    @Qualifier("employeeServiceTestImpl")
    private EmployeeService serviceTest;

    @Test
    public void whenTestContextLoads_thenServiceTestISNotNull() {
        assertThat(serviceTest).isNotNull();
    }

}

Here we loaded employeeServiceTestImpl from the test-context.xml using the @ContextConfiguration annotation.

3.3. Test Using @ContextConfiguration With WEB-INF

We can also import an application context in the test classes from the WEB-INF directory. To do this, we can address the application context using its file URL:

@RunWith(SpringRunner.class)
@ContextConfiguration(locations = "file:src/main/webapp/WEB-INF/application-context.xml")

4. Conclusion

In this article, we learned how to use XML-Based configuration files in test classes in a Spring Boot application. As always, the source code used in this article is available over on GitHub.

Course – LS (cat=Spring)

Get started with Spring and Spring Boot, through the Learn Spring course:

>> THE COURSE
res – REST with Spring (eBook) (everywhere)
Comments are open for 30 days after publishing a post. For any issues past this date, use the Contact form on the site.