Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Using multiple WebSecurityConfigurerAdapter in spring boot

I'm having 2 classes which extends WebSecurityConfigurerAdapter. And can't make them work together.

The idea is as follows:

  1. Have one WebSecurityConfigurerAdapter which only adds custom filter to security chain. The filter does some custom authentication and saves Authentication into SecurityContext. This generally works fine. Configured as follows (imports omitted):
 @Order(1)  @Configuration  @EnableWebMvcSecurity  public class BestSecurityConfig extends WebSecurityConfigurerAdapter {       @Autowired      private BestPreAuthenticationFilter ssoAuthenticationFilter;       @Bean      protected FilterRegistrationBean getSSOAuthenticationFilter() {          FilterRegistrationBean filterRegistrationBean = new FilterRegistrationBean(ssoAuthenticationFilter);           // Avoid include to the default chain          filterRegistrationBean.setEnabled(false);           return filterRegistrationBean;      }       @Override      protected void configure(HttpSecurity http) throws Exception {          http             .addFilterAfter(ssoAuthenticationFilter, SecurityContextPersistenceFilter.class);       }       @Configuration      protected static class AuthenticationConfiguration extends              GlobalAuthenticationConfigurerAdapter {           @Autowired          private BestAuthenticationProvider authenticationProvider;           @Override          public void configure(AuthenticationManagerBuilder auth) throws Exception {              auth.authenticationProvider(authenticationProvider);          }      }  } 
  1. I want the above to be kind of library class which anyone can include via @ComponentScan and get the custom authentication sorted. Obviously they want to provide custom HttpSecurity to secure edpoints. Trying something like:
 @Configuration  @EnableGlobalMethodSecurity(securedEnabled = true, prePostEnabled = true)  @Order(SecurityProperties.ACCESS_OVERRIDE_ORDER)  public class SecurityConfig extends WebSecurityConfigurerAdapter {       @Override      protected void configure(HttpSecurity http) throws Exception {          http              .csrf().disable()              .authorizeRequests()              .antMatchers("/testUrl").hasRole("NON_EXISTING")              .anyRequest().authenticated();      }  } 

Obviously the test URL should not be accessible as my user is not member of role NON_EXISTING. Unfortunatelly she is.

If I move the security authorizeRequests() part to the configuration class form 1. next to adding the security filter then it blocks the access as expected. But in my case it looks like the second configuration is ignored.

I also debugged the configure() methods and noticed that HttpSecurity is not the same object which smells a bit.

Any tips how can I make this work much appreciated.

Sum up of the goal:

  • have one WebSecurityConfigurerAdapter which adds the filter and is hidden from the user of the library
  • let the user define her own custom endpoint security

Spring boot 1.1.6-RELEASE

like image 583
Jan Zyka Avatar asked Sep 30 '14 06:09

Jan Zyka


People also ask

Can we have 2 WebSecurityConfigurerAdapter?

When using Java configuration, the way to define multiple security realms is to have multiple @Configuration classes that extend the WebSecurityConfigurerAdapter base class – each with its own security configuration. These classes can be static and placed inside the main config.

Is WebSecurityConfigurerAdapter deprecated?

The type WebSecurityConfigurerAdapter is deprecatedWell, it's because the developers of Spring framework encourage users to move towards a component-based security configuration.

What is the use of WebSecurityConfigurerAdapter in Spring boot?

In Spring Boot 2, if we want our own security configuration, we can simply add a custom WebSecurityConfigurerAdapter. This will disable the default auto-configuration and enable our custom security configuration. Spring Boot 2 also uses most of Spring Security's defaults.

What is the use of AuthenticationEntryPoint in Spring Security?

AuthenticationEntryPoint is used in Spring Web Security to configure an application to perform certain actions whenever an unauthenticated client tries to access private resources.


2 Answers

Define a special interface

public interface ServiceWebSecurityConfigurer {     void configure(HttpSecurity http) throws Exception; } 

Then have just one ConfigurerAdapter:

public class MyConfigurerAdapter extends WebSecurityConfigurerAdapter {      @Autowired(required = false)     ServiceWebSecurityConfigurer serviceSecConfig;      public void configure(HttpSecurity http) throws Exception {         http.authorizeRequests(). // whatever          if (serviceSecConfig != null) serviceSecConfig.configure(http);          http.authorizeRequests(). // whatever     } } 

and then just implement ServiceWebSecurityConfigurer elsewhere when needed. There can be multiple implementations as well, just autowire them as list and iterate and use them all in your main configuration.

like image 77
eis Avatar answered Sep 22 '22 11:09

eis


So one option I just found is:

  1. Remove the @Configuration annotation from the first bean

And change the 2. to:

 @Configuration  @EnableGlobalMethodSecurity(securedEnabled = true, prePostEnabled = true)  @Order(SecurityProperties.ACCESS_OVERRIDE_ORDER)  public class SecurityConfig extends BestSecurityConfig { //Note the changed extend !       @Override      protected void configure(HttpSecurity http) throws Exception {           super.configure(http); // Merge of the 2 HTTP configurations           http              .csrf().disable()              .authorizeRequests()              .antMatchers("/testUrl").hasRole("NON_EXISTING")              .anyRequest().authenticated();      }  } 

Any comments on whether this is right or wrong approach much appreciated

Edit: After few years I still didn't find other way but I like this way more and more. Even in the default case you extend the abstract WebSecurityConfigurerAdapter there is no reason why some other layer of abstraction can't provide another abstract extension which provides meaningful defaults.

like image 26
Jan Zyka Avatar answered Sep 20 '22 11:09

Jan Zyka