Spring Security Ant Matcher的permitAll失效问题排查
Spring Security Ant Matcher权限失效问题排查
核心问题分析
你的配置中hasRole(ADMIN.name())的使用存在关键问题:Spring Security的hasRole()方法会自动给传入的角色名添加ROLE_前缀。假设你的ADMIN枚举的name()返回值是"ADMIN",那么hasRole("ADMIN")实际校验的是用户是否拥有ROLE_ADMIN权限。如果你的用户角色存储的是ADMIN而非ROLE_ADMIN,那么即使是USER角色的用户,也会因为权限不匹配导致规则校验失效,从而意外允许访问/get等受限端点。
解决方案
针对这个问题,有两种直接修复方式:
方式一:使用hasAuthority()替代hasRole()
hasAuthority()不会自动添加前缀,直接校验传入的角色字符串,更贴合原始角色存储逻辑:
@Override public void configure(HttpSecurity http) throws Exception { http .csrf().disable() .authorizeRequests() .antMatchers( "/css/*", "/js/*", "/index").permitAll() // 修正index路径,添加斜杠保证匹配正确 .antMatchers(HttpMethod.POST, "/api/v1/user/auth/register").permitAll() .antMatchers("/get", "/delete/*", "/api/v1/user/auth/**").hasAuthority(ADMIN.name()) .anyRequest() .authenticated() .and() .httpBasic(); }
方式二:保持hasRole(),确保角色存储带ROLE_前缀
如果坚持使用hasRole(),需要调整角色数据的存储格式,或者修改枚举定义让name()返回带前缀的值:
enum Role { ADMIN("ROLE_ADMIN"), USER("ROLE_USER"); private final String value; Role(String value) { this.value = value; } @Override public String toString() { return this.value; } // 或者重写name()方法,根据枚举规范建议用toString替代 public String name() { return value; } }
额外注意点
- 路径匹配顺序:Spring Security按配置顺序匹配规则,你当前将严格权限规则放在宽松规则之后的顺序是正确的,无需调整。
- 路径格式:原配置中的
"index"需改为"/index",否则无法正确匹配首页的路径请求。
内容的提问来源于stack exchange,提问作者Yosseuf
相关产品推荐
相关产品推荐

