You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

配置两个Spring Security安全配置类时出现Unauthorized错误排查

配置错误原因及修正方案

错误点梳理

  • 未给每套安全配置限定处理的路径范围
    Spring Security的多套安全链按@Order优先级顺序匹配请求,@Order值越小优先级越高,未显式标注的WebSecurityConfigurerAdapter默认优先级为100。你当前的两个配置都没有添加根路径匹配规则,只要优先级更高的配置匹配到请求,后续的配置就完全不会生效。从你的现象来看Customer配置优先级更高,所有请求都走它的校验逻辑,Employee配置全程不生效。
  • Customer安全配置的路径权限规则书写错误
    你在Customer配置的authorizeRequests下写了.antMatchers("/customers/**")后,没有紧跟该路径的权限规则,直接写了.anyRequest().authenticated(),这行路径匹配完全没有生效,等于所有路径只要登录就可以访问,所以Customer用户可以无限制访问/inventory/**路径。
  • 多套安全配置的用户池默认隔离
    每个WebSecurityConfigurerAdapter的AuthenticationManager是独立的,只会用自身配置的用户池做校验,因此Employee的用户在Customer配置的用户池中不存在,请求全部返回401。

修正方案

调整优先级,给每个配置添加根路径匹配限定各自处理的路径范围,同时修正Customer的权限规则即可:

// 客户侧安全配置,仅处理/customers/**路径
@Configuration
@Order(2) // 优先级低于员工侧配置
public class CustomerSecurityAppConfiguration extends WebSecurityConfigurerAdapter {

    @Override
    protected void configure(AuthenticationManagerBuilder auth) throws Exception {
        auth
                .inMemoryAuthentication()
                .withUser("user1")
                .password("{noop}password")
                .and()
                .withUser("user2")
                .password("{noop}password");
                
    }


    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http.csrf().disable();
        http.cors().disable();

        // 限定当前配置只处理/customers/**开头的请求
        http.antMatcher("/customers/**")
                .authorizeRequests()
                .anyRequest()
                .authenticated()
                .and()
                .formLogin()
                .and()
                .httpBasic();
    }
}

// 员工侧安全配置,仅处理/inventory/**路径
@Configuration
@Order(1) // 优先级更高,优先匹配/inventory/**的请求
class EmployeeSecurityConfiguration extends WebSecurityConfigurerAdapter {

    @Override
    protected void configure(AuthenticationManagerBuilder auth) throws Exception {
        auth
                .inMemoryAuthentication()
                .withUser("admin")
                .password("{noop}password")
                .roles("USER", "ADMIN")
                .and()
                .withUser("user")
                .password("{noop}password")
                .roles("USER");
    }

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http.csrf().disable();
        http.cors().disable();

        // 限定当前配置只处理/inventory/**开头的请求
        http.antMatcher("/inventory/**")
                .authorizeRequests()
                .antMatchers(HttpMethod.GET, "/inventory/**")
                .hasAnyRole("USER", "ADMIN")
                .antMatchers(HttpMethod.POST, "/inventory/**")
                .hasRole("ADMIN")
                .anyRequest()
                .authenticated()
                .and()
                .formLogin()
                .and()
                .httpBasic();
    }
}

修正后效果:

  • Customer用户(user1、user2)只能正常访问/customers/**路径,访问/inventory/**会走员工侧校验逻辑,因不在员工用户池返回401
  • Employee用户(admin、user)只能正常访问/inventory/**路径,访问/customers/**会走客户侧校验逻辑,因不在客户用户池返回401
  • 完全符合两套realm分别处理不同业务场景的需求

内容的提问来源于stack exchange,提问作者zilcuanu

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.19 19:15:06