Spring 安全过滤器链不适用于转发的请求

Spring Security filter chain does not work for forwarded request

我的应用程序只需要支持一个 URL。比如 http://.../service/api。要执行的操作取决于“ACTION”请求参数

为了解决这个问题,我创建了下面的控制器

@RestController
public class Controller {

@PostMapping(path = "/api", params = "ACTION=INIT")
 public String init() {
   return "Inside Initialize";
 }

 @PostMapping(path = "/api", params = "ACTION=FETCH")
 public String fetch() {
   return "Inside Fetch";
 }
 
 @PostMapping(path="/view", param = "!ACTION")
 public String view() {
   return "Inside View";
 }

当缺少 ACTION 参数时将调用 /view。对于前两个请求,我配置了 OAuth 身份验证,而后者,即 /view 将使用 formlogin。

我创建了一个过滤器,我在其中检查 ACTION 参数,如果缺少,我将请求转发给 /view 处理程序。

@Component
public class RouteFilter extends OncePerRequestFilter {

  @Override
  protected void doFilterInternal(HttpServletRequest httpServletRequest,
      HttpServletResponse httpServletResponse, FilterChain filterChain)
      throws ServletException, IOException {
    if(!StringUtils.hasText(httpServletRequest.getParameter("ACTION"))){
      httpServletRequest.getRequestDispatcher("/view").forward(httpServletRequest,httpServletResponse);
    }else {
      filterChain.doFilter(httpServletRequest,httpServletResponse);
    }
  }

下面是过滤器注册。我已确保我的过滤器在 FilterChainProxy

之前被调用
@Autowired
private RouteFilter routeFilter;

@Bean
public FilterRegistrationBean<RouteFilter> filter() {
  FilterRegistrationBean<RouteFilter> bean = new FilterRegistrationBean<>();
  bean.setFilter(routeFilter);
  bean.addUrlPatterns("/api");
  bean.setOrder(-100);
  return bean;
}

下面是安全配置

@Configuration
@Order(1)
public class Config extends WebSecurityConfigurerAdapter {

  @Override
  protected void configure(HttpSecurity http) throws Exception {
    http
        .authorizeRequests()
        .antMatchers("/api")
        .hasAuthority("SCOPE_API")
        .anyRequest()
        .authenticated()
        .and()
        .oauth2ResourceServer()
        .opaqueToken();
  }
}

@Configuration
@Order(2)
public class Config2 extends WebSecurityConfigurerAdapter {

  @Override
  protected void configure(HttpSecurity http) throws Exception {
    http
        .authorizeRequests()
        .antMatchers("/view")
        .permitAll()
        .and()
        .formLogin();
  }
}

当我调用 /service/api 时,RouteFilter 将请求转发给 /view 处理程序,但 Spring 与 /view 关联的安全性未得到尊重。 Spring 安全过滤器链是否不适用于转发的请求,或者我在这里遗漏了什么。我正在使用 spring-引导版本 2.4.0

here所述,我们需要将DispatcherType.FORWARD添加到springFilterChain来拦截转发的请求。上述 link 中描述的步骤无效,因为 springFilterChain 是由 SecurityAutoConfiguration 创建的。要在此添加转发调度程序,我们需要将 application.yml 中的 属性 设置为

security:
    filter:
      dispatcher-types:
        - request
        - async
        - error
        - forward 

设置此 属性 请求后将被安全过滤器链拦截。