Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

@WebMvcTest using security returns 401 status instead of redirection

I'm writing a test for a simple controller with Spring Security. There is a login form enabled. When user enters /books URL they are redirected to login page. And this is what I see in web console. GET on /books returns 302 followed by /login and status 200.

@RunWith(SpringRunner.class)
@WebMvcTest(controllers = BookController.class)
public class BookControllerIT {

    @Autowired
    private MockMvc mockMvc;

    // ... some mock beans

    @Test
    public void shouldReturnUnauthorizedStatus() throws Exception {
        mockMvc.perform(get("/books")).andExpect(status().is3xxRedirection());
    }
}

Here is my security configuration:

@Configuration
@EnableWebSecurity
public class BasicSecurityConfiguration extends WebSecurityConfigurerAdapter {

    private DataSource dataSource;
    private BCryptPasswordEncoder encoder;

    @Autowired
    public BasicSecurityConfiguration(@Qualifier("security.datasource") DataSource dataSource, BCryptPasswordEncoder encoder) {
        this.dataSource = dataSource;
        this.encoder = encoder;
    }

    @Override
    public void configure(WebSecurity web) throws Exception {
        super.configure(web);
    }

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http
                .authorizeRequests().antMatchers("/").permitAll()
                .and()
                .authorizeRequests().antMatchers("/h2-console/**").permitAll()
                .anyRequest()
                .authenticated()
                .and()
                .formLogin()
                .and()
                .httpBasic()
                .and()
                .csrf().disable()
                .headers().frameOptions().disable();
    }

    @Override
    protected void configure(AuthenticationManagerBuilder auth) throws Exception {
        auth
        .jdbcAuthentication()
                .dataSource(dataSource)
                .passwordEncoder(encoder);
    }
}

Why my test doesn't redirect as in the browser below? enter image description here

I tried by adding @Import(BasicSecurityConfiguration.class) in my test but I still get 401.

This is the Spring Boot version I'm using: springBootVersion = '2.1.0.M2'

like image 862
mate00 Avatar asked Dec 03 '25 16:12

mate00


1 Answers

I came across a discussion here about what status should be returned when client tries to access protected resource. Should it be client error or redirection. The answer that convinces me most is that server should return 401/403.

I checked what MockMvc does in that case. During filtering in FilterSecurityInterceptor there is AccessDeniedException thrown, and ExceptionTranslationFilter handles it in handleSpringSecurityException and indeed sets response status to 401.

I'm modifying my test to assert that server returns 4xx status.

like image 56
mate00 Avatar answered Dec 06 '25 06:12

mate00