Search code examples
javaspringspring-bootjunit

Spring filter chain is not applied on unit test MockMvc


I made a custom filter and registered on WebConfig, but when I call the api, the filter does not get invoked. I looked through the log, and seems like filter chain I described on the config is not applied. However I checked WebConfig is invoked using debugger.

//MyFilter.java
@Component
public class MyFilter implements Filter {
  @Override
  doFilter(...) { // This part is NOT getting invoked
    ...
  }
}
//WebConfig.java
@Configuration
public class WebConfig {
  @Bean
  public FilterRegistrationBean<MyFilter> myFilter() { // This part is getting invoked
    regBean = new FilterRegistrationBean();
    regBean.setFilter(new MyFilter());
    regBean.setOrder(0);
    return regBean;
  }
}
//MyTest.java
@SpringBootTest
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(classes = MyApplication.class)
public class MyTest {
  
  private MockMvc mockMvc;

  @Autowired
  WebApplicationContext ctx;

  @Before
  public void before() {
    mockMvc = MockMvcBuilders.webApplicationSetup(ctx).build();
  }

  @Test
  public void doTest() {
    mockMvc.perform(...);
  }
}

Solution

  • this.mockMvc = MockMvcBuilders.webApplicationSetup(ctx)
                .addFilters(filter).build();
    

    If you don't use @AutoConfigureMockMvc then you have to add filters to mockMvc builder.

    What's required to make mockMVC test a filter's init routine?

    Also there is a configuration problem here.

    @Bean
    public FilterRegistrationBean<MyFilter> myFilter(MyFilter myfilter) { // This part is getting invoked
        regBean = new FilterRegistrationBean();
        regBean.setFilter(myFilter);
        regBean.setOrder(0);
        return regBean;
    }
    

    You are putting new Instance of a filter to filter chain but you create singleton filter. You can use above configuration.