7

I have a Spring mock-mvc JUnit test class that contains two tests. When I run the tests within Eclipse IDE both tests pass (I use Eclipse Maven plugin).

When running the tests from the command line using

mvn test

one of the tests fails because the WebApplicationContext that is @Autowired is sometimes null.

Here is my test class

@WebAppConfiguration
@ActiveProfiles({ "dev", "test" })
public class AddLinkEndpointMvcTest extends BaseMvc {

    @Autowired
    private WebApplicationContext wac;

    private MockMvc mockMvc;

    @Before
    public void before() {
        System.out.println("WAC = " + wac);
        mockMvc = MockMvcBuilders.webAppContextSetup(wac).build();
    }

    @Test
    public void addLinkDoesNotSupportGet() throws Exception {
        mockMvc.perform(get("/myurl")).andExpect(status().is(HttpStatus.SC_METHOD_NOT_ALLOWED));
    }

    @Test
    public void addLinkBadRequestNoLinkAddress() throws Exception {
        mockMvc.perform(post("/myurl")).andExpect(status().is(HttpStatus.SC_BAD_REQUEST));
    }
}

Here is the BaseMvc class

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration
public class BaseMvc {

    @Configuration
    @ComponentScan(basePackages = { "com.example.a", "com.example.b" })
    @Profile("test")
    public static class TestConfig {

        static {
            System.out.println("TEST CONFIG");
        }

        // ...some beans defined here

        @Bean
        public static PropertySourcesPlaceholderConfigurer properties() {
            PropertySourcesPlaceholderConfigurer configurer = new PropertySourcesPlaceholderConfigurer();
            configurer.setIgnoreUnresolvablePlaceholders(false);
            configurer.setLocations(new Resource[] { new ClassPathResource("sample-webapp.properties"),
                new ClassPathResource("sample-domain.properties") });
            return configurer;
        }

    }

}

I have added the println calls to aide debugging. When running mvn test here is the relevant console output:

WAC = null
WAC = org.springframework.web.context.support.GenericWebApplicationContext@38795184: startup date [Thu Sep 19 16:24:22 BST 2013]; root of context hierarchy

and the error

java.lang.IllegalArgumentException: WebApplicationContext is required
        at org.springframework.util.Assert.notNull(Assert.java:112)
        at org.springframework.test.web.servlet.setup.DefaultMockMvcBuilder.<init>(DefaultMockMvcBuilder.java:66)
        at org.springframework.test.web.servlet.setup.MockMvcBuilders.webAppContextSetup(MockMvcBuilders.java:46)
        at com.mypackage.AddLinkEndpointMvcTest.before(AddLinkEndpointMvcTest.java:31)

So this is the problem line in the test

@Autowired
private WebApplicationContext wac;  

Sometimes wac is null or has not completed initialisation before the JUnit @Before kicks in.

What I don't understand is the WebApplicationContext is sometimes null and why it passes in Eclipse IDE!

Ayub Malik
  • 2,488
  • 6
  • 27
  • 42

3 Answers3

3

you should add @SpringBootTest as an annotation before your test class. Like this:

@RunWith(SpringRunner.class)
@SpringBootTest
Michu93
  • 5,058
  • 7
  • 47
  • 80
-3

Try using getBean instead of auto wiring. This should assure that WebApplicationContext is initialized when you access it.

Example:

MyClass myClass = applicationContext.getBean("myClass");
Rylander
  • 19,449
  • 25
  • 93
  • 144
-3

Please use @WebAppConfiguration annotation. Your question is already answered here : WebApplicationContext doesn't autowire

Community
  • 1
  • 1