我创建了一个过滤器,在过滤器超级构造函数中,它需要一个defaultFilterProcessesUrl。我通过URL /v1/**选择了所有请求。

我需要不登录/v1/usersPOST方法)和/v1/users/signinPOST方法),但是过滤器不允许。如何解决这个问题呢?

JWT过滤器:

public class JwtAuthenticationTokenFilter extends AbstractAuthenticationProcessingFilter {

    public JwtAuthenticationTokenFilter() {
        super("/v1/**");
    }

    @Override
    public Authentication attemptAuthentication(HttpServletRequest request, HttpServletResponse response) throws AuthenticationException, IOException, ServletException {

         String header = request.getHeader("Authorization");
         if(header == null || !header.startsWith("Bearer")){
             throw new RuntimeException("JWT token is missing");
         }

         String authenticationToken = header.substring(7);

        JwtAuthenticationToken token = new JwtAuthenticationToken(authenticationToken);
        return getAuthenticationManager().authenticate(token);
    }

    @Override
    protected void successfulAuthentication(HttpServletRequest request, HttpServletResponse response, FilterChain chain, Authentication authResult) throws IOException, ServletException {
        super.successfulAuthentication(request, response, chain, authResult);
        chain.doFilter(request, response);
    }
}


Spring Security配置:

public class SecurityConfig extends WebSecurityConfigurerAdapter {

    @Autowired
    private JwtAuthenticationProvider authenticationProvider;
    @Autowired
    private JwtAuthenticationEntryPoint entryPoint;

    @Bean
    public AuthenticationManager authenticationManager(){
        return new ProviderManager(Collections.singletonList(authenticationProvider));
    }

    @Bean
    public JwtAuthenticationTokenFilter authenticationTokenFilter(){
        JwtAuthenticationTokenFilter filter = new JwtAuthenticationTokenFilter();
        filter.setAuthenticationManager(authenticationManager());
        filter.setAuthenticationSuccessHandler(new JwtSuccessHandler());
        return filter;
    }

    @Override
    public void configure(WebSecurity web) throws Exception {
        web
            .ignoring()
                .antMatchers(HttpMethod.POST, "/v1/users")
                .antMatchers(HttpMethod.POST, "/v1/users/signin")
                .antMatchers(HttpMethod.POST, "/token");
    }

    @Override
    protected void configure(HttpSecurity http) throws Exception{
        http
             .csrf().disable()
             .authorizeRequests()
                .anyRequest().hasAnyRole("SG_ADMIN", "O_ADMIN", "OS_ADMIN")
                .and()
             .exceptionHandling().authenticationEntryPoint(entryPoint)
                .and()
             .sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS);

        http.addFilterBefore(authenticationTokenFilter(), UsernamePasswordAuthenticationFilter.class);
        http.headers().cacheControl();
    }
}

最佳答案

您可以将其他构造函数与RequestMatcher一起使用,请参见AbstractAuthenticationProcessingFilter


  AbstractAuthenticationProcessingFilter
  
  protected AbstractAuthenticationProcessingFilter(RequestMatcher requiresAuthenticationRequestMatcher)
  
  创建一个新实例
  
  参数:
  
  requiresAuthenticationRequestMatcher-用于确定是否需要身份验证的RequestMatcher。不能为null。


您修改的代码:

public JwtAuthenticationTokenFilter() {
    super(customRequestMatcher);
}




 RequestMatcher customRequestMatcher = new AndRequestMatcher(
      new AntPathRequestMatcher("/v1/**"),
      new NegatedRequestMatcher(
          new AntPathRequestMatcher("/v1/users", "POST")
      ),
      new NegatedRequestMatcher(
          new AntPathRequestMatcher("/v1/users/signin", "POST")
      )
 );

关于java - WebSecurity忽略不适用于AbstractAuthenticationProcessingFilter,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/55655950/

10-11 01:17