This is a question from a friend, and I feel it is necessary to talk with you about this question:

First of all, this is a bit of a problem, because http.authorizerequests () are not always the first. Although most of the time, what we see is the first one, there are many cases where http.authorizerequests () are not the first. To understand this, we need to figure out what http.authorizerequests () really means!

This involves the configuration of the filter chain in Spring Security. In this article, Songo will talk about it a little.

This article is the 36th in the Spring Security series, and reading the previous articles will help you understand it better:

  1. Dig a big hole and Spring Security will do it!
  2. How to decrypt the password
  3. A step-by-step guide to customizing form logins in Spring Security
  4. Spring Security does front and back separation, so don’t do page jumps! All JSON interactions
  5. Authorization in Spring Security used to be so simple
  6. How does Spring Security store user data into the database?
  7. Spring Security+Spring Data Jpa, Security management is only easier!
  8. Spring Boot + Spring Security enables automatic login
  9. Spring Boot automatic login. How to control security risks?
  10. How is Spring Security better than Shiro in microservices projects?
  11. Two ways for SpringSecurity to customize authentication logic (advanced play)
  12. How can I quickly view information such as the IP address of the login user in Spring Security?
  13. Spring Security automatically kicks out the previous login user.
  14. How can I kick out a user who has logged in to Spring Boot + Vue?
  15. Spring Security comes with a firewall! You have no idea how secure your system is!
  16. What is a session fixed attack? How do I defend against session fixation attacks in Spring Boot?
  17. How does Spring Security handle session sharing in a clustered deployment?
  18. Songgo hand in hand to teach you in SpringBoot CSRF attack! So easy!
  19. Learn to learn thoroughly! Spring Security CSRF defense source code parsing
  20. Two poses for password encryption in Spring Boot!
  21. How to learn Spring Security? Why must we study systematically?
  22. Spring Security has two different resource release policies. Do not use them incorrectly.
  23. Spring Boot + CAS single sign-on
  24. Spring Boot is the third way to implement single sign-on!
  25. How do I Connect to the Database in Spring Boot+CAS SINGLE Sign-on?
  26. Spring Boot+CAS default login page is too ugly, how to do?
  27. How to carry Token in request header with Swagger
  28. Summary of three cross-domain scenarios in Spring Boot
  29. How to implement HTTP authentication in Spring Boot?
  30. Four types of permission control in Spring Security
  31. Spring Security multiple encryption solutions coexist, old and old system integration sharp tools!
  32. Magic! New objects can also be managed by the Spring container!
  33. What is the meaning of and in Spring Security configuration?
  34. Spring Security exception handling
  35. I’ve never seen a login like this before in years of writing code!

1. Start with a filter

Even if you haven’t studied the implementation mechanism of authentication and authorization in Spring Security, you’ve probably heard that Spring Security implements these functions through filters.

Yes, that’s right! Spring Security provides a total of 32 filters, of which 15 are used by default. Songko will cover these filters in more detail in a future article, but today we will take a look at the configuration of filters.

In a Web project, the request flow might look something like this:

Requests originate from a client (such as a browser) and then travel through layers of filters to be processed by servlets.

Spring Security’s default 15 filters are nested between clients and servlets.

No!

The Filter in the figure above can be called Web Filter and the Filter in Spring Security can be called Security Filter. The relationship between them is shown as follows:

As you can see, Spring Security Filter is not directly embedded in the Web Filter, but is managed by FilterChainProxy. The FilterChainProxy itself is embedded in the Web Filter via the DelegatingFilterProxy proxy Filter provided by Spring.

DelegatingFilterProxy = DelegatingFilterProxy = DelegatingFilterProxy = DelegatingFilterProxy = DelegatingFilterProxy = DelegatingFilterProxy So sometimes it feels like the DelegatingFilterProxy is less present when it’s actually there all the time.

2. Multiple filter chains

This is a single filter chain. In fact, in Spring Security, there can be multiple filter chains.

In front of The Songgo OAuth2 series, there are multiple filter chains involved, but has not been singled out to speak, today to share with you.

One might ask, is the following configuration a chain of filters?

@Override
protected void configure(HttpSecurity http) throws Exception {
    http.authorizeRequests()
            .antMatchers("/admin/**").hasRole("admin")
            .antMatchers("/user/**").hasRole("user")
            .anyRequest().authenticated()
            ...
            .csrf().disable();
}
Copy the code

I’m sure you’ve all seen this configuration, but it’s not a chain of filters, it’s a chain of filters. Because whether /admin/** or /user/**, the filter is the same, but different path judgment conditions are different.

If the system has multiple filter chains, these filter chains will be divided in FilterChainProxy, as shown below:

As you can see, when the request arrives at FilterChainProxy, FilterChainProxy forwards the request to different Spring Security Filters based on the requested path. Different Spring Security Filters correspond to different Filters, meaning that different requests will pass through different Filters.

Under normal circumstances, we configure a filter chain, how to configure multiple filter chains? Songo gives you a simple example:

@Configuration
public class SecurityConfig {
    @Bean
    protected UserDetailsService userDetailsService(a) {
        InMemoryUserDetailsManager manager = new InMemoryUserDetailsManager();
        manager.createUser(User.withUsername("javaboy").password("{bcrypt}$2a$10$Sb1gAUH4wwazfNiqflKZve4Ubh.spJcxgHG8Cp29DeGya5zsHENqi").roles("admin"."aaa"."bbb").build());
        manager.createUser(User.withUsername("sang").password("{noop}123").roles("admin").build());
        manager.createUser(User.withUsername("A little Rain in the South").password("{MD5}{Wucj/L8wMTMzFi3oBKWsETNeXbMFaHZW9vCK9mahMHc=}4d43db282b36d7f0421498fdc693f2a2").roles("user"."aaa"."bbb").build());
        return manager;
    }

    @Configuration
    @Order(1)
    static class DefaultWebSecurityConfig extends WebSecurityConfigurerAdapter {

        @Override
        protected void configure(HttpSecurity http) throws Exception {
            http.antMatcher("/foo/**")
                    .authorizeRequests()
                    .anyRequest().hasRole("admin") .and() .csrf().disable(); }}@Configuration
    @Order(2)
    static class DefaultWebSecurityConfig2 extends WebSecurityConfigurerAdapter {

        @Override
        protected void configure(HttpSecurity http) throws Exception {
            http.antMatcher("/bar/**")
                    .authorizeRequests()
                    .anyRequest().hasRole("user") .and() .formLogin() .permitAll() .and() .csrf().disable(); }}}Copy the code
  1. First of all, SecurityConfig no longer need to inherit from WebSecurityConfigurerAdapter, just as a normal class, add @ the Configuration notes.
  2. Provide the UserDetailsService instance, which acts as our data source.
  3. Create a static inner class inheritance WebSecurityConfigurerAdapter class, at the same time, use the @ Configuration comments mark a static inner class is a Configuration, Configuration class inside the code is the same as before, without much elaboration.
  4. Each static inner class is a configuration of a chain of filters.
  5. Notice that in the static inner class, I didn’t use ithttp.authorizeRequests()To start,http.authorizeRequests()The configuration indicates that the path of the filter chain is/ * *. In the static inner class, I didhttp.antMatcher("/bar/**")If the configuration is enabled, the blocking scope of the current filter chain is limited to/bar/**.
  6. When there are multiple filter chains, there must be a priority issue, so the @order (2) annotation on the configuration class of each filter chain marks the priority.

Configure (HttpSecurity HTTP) {configure(HttpSecurity HTTP) { Yes, it is! In this method, we are adding/removing/modifying the filters provided by Spring Security by default, so this method is configuring the filter chain in Spring Security. As for how to configure the filter chain, Songo will discuss this later.

3. Back to the question

Finally, let’s go back to the question our friend asked at the beginning.

First, the HTTP.authorizerequests () configuration does not always occur on the first line. If there is only one filter chain, it always occurs on the first line, indicating that the filter chain’s interception rule is /** (requests must be intercepted by the filter chain first, This is then processed in different Security Filters), not necessarily if there are multiple filter chains.

Only from the literal meaning to understand, authorizeRequests () method return values is ExpressionUrlAuthorizationConfigurer ExpressionInterceptUrlRegistry, ExpressionUrlAuthorizationConfigurer can different permissions for different sets of RequestMatcher configuration rules, Is everyone to see. AntMatchers (“/admin / * * “). HasRole (” admin “). AntMatchers (“/user / * * “). HasRole (” user “).

4. Summary

Today, I will simply share the problem of the filter chain in Spring Security with my friends. Later, Songgo will spare some time to talk with you about the configuration and meaning of every filter in the filter chain. Get 40+ complete articles in the Spring Security series

If you feel that you have gained something, remember to click on songko under the encouragement of watching oh ~