Spring 控制器上的安全 @PreAuthorize

Spring Security @PreAuthorize on controllers

我正在尝试在某些控制器上使用 url(基于蚂蚁的)匹配以及 @PreAuthorize("permitAll"),即

@Controller
@RequestMapping("/register")
public class RegistrationController {
...

  @PreAuthorize("permitAll")
  @RequestMapping(method = RequestMethod.GET)
  public String register() { ... }

安全配置:

@Configuration
@EnableWebMvcSecurity
@EnableGlobalMethodSecurity(prePostEnabled = true)
public class SecurityConfig extends WebSecurityConfigurerAdapter {

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        // @formatter:off
        http
            .authorizeRequests()
                .antMatchers("/").permitAll()
                .anyRequest().authenticated()

我还尝试将 @EnableGlobalMethodSecurity 添加到我的 MVC 配置中:

@Configuration
@EnableGlobalMethodSecurity(prePostEnabled = true)
public class MvcConfig extends WebMvcConfigurerAdapter { ... }

但这没有效果

然而,当我点击 /register 时,系统仍然提示我进行身份验证。如果我将“/register”添加到蚂蚁匹配器,它就会工作,即 .antMatchers("/", "/register").permitAll()

我在这里错过了什么? @PreAuthorize 似乎对我的控制器没有影响

你不能那样做,因为蚂蚁匹配器和 @PreAuthorize 在不同的级别工作。

蚂蚁匹配器在 http 安全级别工作。 Spring 安全过滤器查看请求,如果发现应该拒绝访问,它甚至不会将请求传递给调度程序 servlet,直接发送 403 错误。

PreAuthorize 方法 级别工作。当一个方法即将被调用时,AOP 代理控制是否应该允许访问。所以 2 个授权级别是 链接 ,而不是第二个覆盖第一个。

无论如何,我强烈建议您不要在控制器上使用@PreAuthorize("hasRole('ADMIN')"):

  • 用一个简单的蚂蚁匹配器就可以轻松完成
  • 它强制您允许在控制器上进行代理,或者使用 class 代理而不是 JDK 代理,或者使用控制器接口

恕我直言,@PreAuthorize 最适合服务级别,因为您可以将域对象与用户授予的权限混合以获得细粒度的授权。