When to use Spring Security`s antMatcher()?

Spring MvcSpring SecuritySpring Security4

Spring Mvc Problem Overview


When do we use antMatcher() vs antMatchers()?

For example:

http
   .antMatcher("/high_level_url_A/**")
   .authorizeRequests()
      .antMatchers("/high_level_url_A/sub_level_1").hasRole('USER')
      .antMatchers("/high_level_url_A/sub_level_2").hasRole('USER2')
      .somethingElse()
      .anyRequest().authenticated()
      .and()
   .antMatcher("/high_level_url_B/**")
   .authorizeRequests()
      .antMatchers("/high_level_url_B/sub_level_1").permitAll()
      .antMatchers("/high_level_url_B/sub_level_2").hasRole('USER3')
      .somethingElse()
      .anyRequest().authenticated()
      .and()
   ...

What I expect here is,

  • Any request matches to /high_level_url_A/** should be authenticated + /high_level_url_A/sub_level_1 only for USER and /high_level_url_A/sub_level_2 only for USER2
  • Any request matches to /high_level_url_B/** should be authenticated + /high_level_url_B/sub_level_1 for public access and /high_level_url_A/sub_level_2 only for USER3.
  • Any other pattern I don't care - But should be public ?

I have seen latest examples do not include antMatcher() these days. Why is that? Is antMatcher() no longer required?

Spring Mvc Solutions


Solution 1 - Spring Mvc

You need antMatcher for multiple HttpSecurity, see Spring Security Reference:

> 5.7 Multiple HttpSecurity > > We can configure multiple HttpSecurity instances just as we can have multiple <http> blocks. The key is to extend the WebSecurityConfigurationAdapter multiple times. For example, the following is an example of having a different configuration for URL’s that start with /api/. > > @EnableWebSecurity > public class MultiHttpSecurityConfig { > @Autowired > public void configureGlobal(AuthenticationManagerBuilder auth) { 1 > auth > .inMemoryAuthentication() > .withUser("user").password("password").roles("USER").and() > .withUser("admin").password("password").roles("USER", "ADMIN"); > } > > @Configuration > @Order(1) 2 > public static class ApiWebSecurityConfigurationAdapter extends WebSecurityConfigurerAdapter { > protected void configure(HttpSecurity http) throws Exception { > http > .antMatcher("/api/**") 3 > .authorizeRequests() > .anyRequest().hasRole("ADMIN") > .and() > .httpBasic(); > } > }
> > @Configuration 4 > public static class FormLoginWebSecurityConfigurerAdapter extends WebSecurityConfigurerAdapter { > > @Override > protected void configure(HttpSecurity http) throws Exception { > http > .authorizeRequests() > .anyRequest().authenticated() > .and() > .formLogin(); > } > } > } > > 1 Configure Authentication as normal > > 2 Create an instance of WebSecurityConfigurerAdapter that contains @Order to specify which WebSecurityConfigurerAdapter should be considered first. > > 3 The http.antMatcher states that this HttpSecurity will only be applicable to URLs that start with /api/ > > 4 Create another instance of WebSecurityConfigurerAdapter. If the URL does not start with /api/ this configuration will be used. This configuration is considered after ApiWebSecurityConfigurationAdapter since it has an @Order value after 1 (no @Order defaults to last).

In your case you need no antMatcher, because you have only one configuration. Your modified code:

http
    .authorizeRequests()
        .antMatchers("/high_level_url_A/sub_level_1").hasRole('USER')
        .antMatchers("/high_level_url_A/sub_level_2").hasRole('USER2')
        .somethingElse() // for /high_level_url_A/**
        .antMatchers("/high_level_url_A/**").authenticated()
        .antMatchers("/high_level_url_B/sub_level_1").permitAll()
        .antMatchers("/high_level_url_B/sub_level_2").hasRole('USER3')
        .somethingElse() // for /high_level_url_B/**
        .antMatchers("/high_level_url_B/**").authenticated()
        .anyRequest().permitAll()

Solution 2 - Spring Mvc

I'm updating my answer...

antMatcher() is a method of HttpSecurity, it doesn't have anything to do with authorizeRequests(). Basically, http.antMatcher() tells Spring to only configure HttpSecurity if the path matches this pattern.

The authorizeRequests().antMatchers() is then used to apply authorization to one or more paths you specify in antMatchers(). Such as permitAll() or hasRole('USER3'). These only get applied if the first http.antMatcher() is matched.

Solution 3 - Spring Mvc

Basically http.antMatcher() tells Spring to only configure HttpSecurity if the path matches this pattern.

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
Questionsura2kView Question on Stackoverflow
Solution 1 - Spring MvcdurView Answer on Stackoverflow
Solution 2 - Spring MvcPatrick GrimardView Answer on Stackoverflow
Solution 3 - Spring MvcDarshanView Answer on Stackoverflow