Java – spring boot security will not throw 401 unauthorized exception, but 404 not found
•
Java
My authentication is based on spring boot security example
What do I need to change to throw 401 exceptions?
I have an authentication filter:
public class AuthenticationFilter extends GenericFilterBean { ... @Override public void doFilter(ServletRequest request,ServletResponse response,FilterChain chain) throws IOException,ServletException { HttpServletRequest httpRequest = asHttp(request); HttpServletResponse httpResponse = asHttp(response); Optional<String> token = Optional.fromNullable(httpRequest.getHeader("X-Auth-Token")); try { if (token.isPresent()) { logger.debug("Trying to authenticate user by X-Auth-Token method. Token: {}",token); processTokenAuthentication(token); addSessionContextToLogging(); } logger.debug("AuthenticationFilter is passing request down the filter chain"); chain.doFilter(request,response); } catch (InternalAuthenticationServiceException internalAuthenticationServiceException) { SecurityContextHolder.clearContext(); logger.error("Internal authentication service exception",internalAuthenticationServiceException); httpResponse.sendError(HttpServletResponse.SC_INTERNAL_SERVER_ERROR); } catch (AuthenticationException authenticationException) { SecurityContextHolder.clearContext(); httpResponse.sendError(HttpServletResponse.SC_UNAUTHORIZED,authenticationException.getMessage()); } finally { MDC.remove(TOKEN_SESSION_KEY); MDC.remove(USER_SESSION_KEY); } } private void addSessionContextToLogging() { ... } ... private void processTokenAuthentication(Optional<String> token) { Authentication resultOfAuthentication = tryToAuthenticateWithToken(token); SecurityContextHolder.getContext().setAuthentication(resultOfAuthentication); } private Authentication tryToAuthenticateWithToken(Optional<String> token) { PreAuthenticatedAuthenticationToken requestAuthentication = new PreAuthenticatedAuthenticationToken(token,null); return tryToAuthenticate(requestAuthentication); } private Authentication tryToAuthenticate(Authentication requestAuthentication) { Authentication responseAuthentication = authenticationManager.authenticate(requestAuthentication); if (responseAuthentication == null || !responseAuthentication.isAuthenticated()) { throw new InternalAuthenticationServiceException("Unable to authenticate Domain User for provided credentials"); } logger.debug("User successfully authenticated"); return responseAuthentication; }
Authenticationprovider implementation:
@Provider public class TokenAuthenticationProvider implements AuthenticationProvider { @Override public Authentication authenticate(Authentication authentication) throws AuthenticationException { Optional<String> token = (Optional) authentication.getPrincipal(); if (!token.isPresent() || token.get().isEmpty()) { throw new BadCredentialsException("No token set."); } if (!myCheckHere()){ throw new BadCredentialsException("Invalid token"); } return new PreAuthenticatedAuthenticationToken(myConsumerObject,null,AuthorityUtils.commaSeparatedStringToAuthorityList("ROLE_API_USER")); } ... }
And the following configurations:
@Configuration @EnableWebSecurity @EnableGlobalMethodSecurity(prePostEnabled = true) public class SecurityConfiguration extends WebSecurityConfigurerAdapter { @Override protected void configure(HttpSecurity http) throws Exception { http. csrf().disable(). sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS). and(). anonymous().disable(). exceptionHandling().authenticationEntryPoint(unauthorizedEntryPoint()); http.addFilterBefore(new AuthenticationFilter(authenticationManager()),BasicAuthenticationFilter.class); } @Override protected void configure(AuthenticationManagerBuilder auth) throws Exception { auth.authenticationProvider(tokenAuthenticationProvider()); } @Bean public AuthenticationProvider tokenAuthenticationProvider() { return new TokenAuthenticationProvider(); } @Bean public AuthenticationEntryPoint unauthorizedEntryPoint() { return (request,response,authException) -> response.sendError(HttpServletResponse.SC_UNAUTHORIZED); } }
Solution
I found the answer in this post: return HTTP error 401 code & skip filter chains
replace
httpResponse.sendError(HttpServletResponse.SC_UNAUTHORIZED,authenticationException.getMessage());
I need to call
httpResponse.setStatus(HttpServletResponse.SC_UNAUTHORIZED);
When I stop calling it and set the state to a different code, the chain seems to stop - the exception is thrown correctly
The content of this article comes from the network collection of netizens. It is used as a learning reference. The copyright belongs to the original author.
THE END
二维码