title: Spring Security for URL with permitAll() and expired Auth Token
body: <p>I'm using Spring 4 with Spring Security, custom GenericFilterBean and AuthenticationProvider implementations. I have mostly secured URLs with the exception of a URL to create new session: <strong><em>/v2/session</em></strong> (e.g. login based on the username and password and returns Auth Token to be used in the subsequent requests that require authentication) configured as follows:</p>
  
  <pre><code>@Configuration
  @ComponentScan(basePackages={"com.api.security"})
  @EnableWebSecurity
  public class SecurityConfig extends WebSecurityConfigurerAdapter {
  
  @Autowired
  private ApiAuthenticationProvider apiAuthenticationProvider;
  
  @Autowired
  private AuthTokenHeaderAuthenticationFilter authTokenHeaderAuthenticationFilter;
  
  @Autowired
  private AuthenticationEntryPoint apiAuthenticationEntryPoint;
  
  @Autowired
  public void configureGlobal(AuthenticationManagerBuilder auth) {
      auth.authenticationProvider(apiAuthenticationProvider);
  }
  
  @Override
  protected void configure(HttpSecurity http) throws Exception {
      http
          .addFilterBefore(authTokenHeaderAuthenticationFilter, BasicAuthenticationFilter.class) // Main auth filter
          .sessionManagement()
              .sessionCreationPolicy(SessionCreationPolicy.STATELESS);
  
      http.authorizeRequests()
          .antMatchers(HttpMethod.POST, "/v2/session").permitAll()
          .anyRequest().authenticated();
  
      http.exceptionHandling()
          .authenticationEntryPoint(apiAuthenticationEntryPoint);
  }
  }
  </code></pre>
  
  <p>The <strong><em>authTokenHeaderAuthenticationFilter</em></strong> runs on every request and gets Token from the request header:</p>
  
  <pre><code>/**
   * Main Auth Filter. Always sets Security Context if the Auth token Header is not empty
   */
  @Component
  public class AuthTokenHeaderAuthenticationFilter extends GenericFilterBean {
  
  @Override
  public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
      final String token = ((HttpServletRequest) request).getHeader(RequestHeaders.AUTH_TOKEN_HEADER);
      if (StringUtils.isEmpty(token)) {
          chain.doFilter(request, response);
          return;
      }
  
      try {
              AuthenticationToken authRequest = new AuthenticationToken(token);
  
                SecurityContextHolder.getContext().setAuthentication(authRequest);
          }
      } catch (AuthenticationException failed) {
          SecurityContextHolder.clearContext();
  
          return;
      }
  
      chain.doFilter(request, response); // continue down the chain
  }
  </code></pre>
  
  <p>}</p>
  
  <p>The custom <strong><em>apiAuthenticationProvider</em></strong> will try to authenticate all requests based on the token provided in the header and if authentication is unsuccessful - throws AccessException and client will receive HTTP 401 response:</p>
  
  <pre><code>@Component
  public class ApiAuthenticationProvider implements AuthenticationProvider {
  
  @Autowired
  private remoteAuthService remoteAuthService;
  
  @Override
  public Authentication authenticate(Authentication authentication) throws AuthenticationException {
  
      AuthenticationToken authRequest = (AuthenticationToken) authentication;
      String identity = null;
  
      try {
          identity = remoteAuthService.getUserIdentityFromToken(authRequest.getToken());
      } catch (AccessException e) {
          throw new InvalidAuthTokenException("Cannot get user identity from the token", e);
      }
  
      return new AuthenticationToken(identity, authRequest.getToken(), getGrantedAuthorites());
      }
      }
  </code></pre>
  
  <p>This works perfectly fine for the requests that require authentication. This works fine for the <strong><em>/v2/session</em></strong> request without the Authentication Header in it. However, for the <strong><em>/v2/session</em></strong> request that has an expired Auth Token in the header (or in the cookie - not shown in the code samples; this may happen sometimes if the client didn't clear the headers or continues sending cookies with requests) the security context will be initialized and <strong><em>apiAuthenticationProvider</em></strong> will throw an exception and respond with HTTP 401 to the client. </p>
  
  <p>Since <strong><em>/v2/session</em></strong> has been configured as </p>
  
  <pre><code>http.authorizeRequests()
          .antMatchers(HttpMethod.POST, "/v2/session").permitAll()
  </code></pre>
  
  <p>I would expect Spring Security to determine that before calling ApiAuthenticationProvider.authenticate(). What should be the way for the filter or auth provider to ignore/not throw the exception for the URLs configured as permitAll()?</p>