我正在使用Spring Boot(1.2.6)和Spring Security(4.0.2)。
安全配置如下所示:
@Configuration @ConditionalOnWebApplication @Profile("!integTest") @EnableGlobalMethodSecurity(securedEnabled = true, prePostEnabled = true) @EnableWebSecurity @EnableRedisHttpSession(maxInactiveIntervalInSeconds = 60 * 60 * 24 * 30) class SecurityConfiguration extends WebSecurityConfigurerAdapter { public static final String[] PROTECTED_RESOURCES = new String[] { "/user/abc" }; /* * (non-Javadoc) * * @see org.springframework.security.config.annotation.web.configuration. * WebSecurityConfigurerAdapter#configure(org.springframework.security. * config.annotation.web.builders.HttpSecurity) */ @Override protected void configure(HttpSecurity http) throws Exception { http .csrf().disable() .authorizeRequests() .antMatchers(PROTECTED_RESOURCES) .hasRole("USER") .anyRequest() .permitAll() .and() .anonymous().disable(); } }
但是,当匿名用户正在访问受保护的资源( / user / abc )时,Spring Security Framework会以403(拒绝访问)响应。
我想知道如何配置Spring以在匿名用户访问受保护的URL时以HTTP 401代码响应。
以下是在上设置DEBUG级别后的日志ExceptionTranslationFilter。
DEBUG
ExceptionTranslationFilter
2015-11-20 10:59:07.406 DEBUG 14542 --- [nio-8000-exec-1] o.s.web.servlet.DispatcherServlet : Initializing servlet 'dispatcherServlet' 2015-11-20 10:59:07.410 INFO 14542 --- [nio-8000-exec-1] o.a.c.c.C.[Tomcat].[localhost].[/] : Initializing Spring FrameworkServlet 'dispatcherServlet' 2015-11-20 10:59:07.411 INFO 14542 --- [nio-8000-exec-1] o.s.web.servlet.DispatcherServlet : FrameworkServlet 'dispatcherServlet': initialization started 2015-11-20 10:59:07.412 DEBUG 14542 --- [nio-8000-exec-1] o.s.web.servlet.DispatcherServlet : Using MultipartResolver [org.springframework.web.multipart.support.StandardServletMultipartResolver@29e7e0b6] 2015-11-20 10:59:07.424 DEBUG 14542 --- [nio-8000-exec-1] o.s.web.servlet.DispatcherServlet : Unable to locate LocaleResolver with name 'localeResolver': using default [org.springframework.web.servlet.i18n.AcceptHeaderLocaleResolver@bf0f97a] 2015-11-20 10:59:07.434 DEBUG 14542 --- [nio-8000-exec-1] o.s.web.servlet.DispatcherServlet : Unable to locate ThemeResolver with name 'themeResolver': using default [org.springframework.web.servlet.theme.FixedThemeResolver@1189d7ae] 2015-11-20 10:59:07.453 DEBUG 14542 --- [nio-8000-exec-1] o.s.web.servlet.DispatcherServlet : Unable to locate RequestToViewNameTranslator with name 'viewNameTranslator': using default [org.springframework.web.servlet.view.DefaultRequestToViewNameTranslator@859e51c] 2015-11-20 10:59:07.466 DEBUG 14542 --- [nio-8000-exec-1] o.s.web.servlet.DispatcherServlet : Unable to locate FlashMapManager with name 'flashMapManager': using default [org.springframework.web.servlet.support.SessionFlashMapManager@18f8476f] 2015-11-20 10:59:07.466 DEBUG 14542 --- [nio-8000-exec-1] o.s.web.servlet.DispatcherServlet : Published WebApplicationContext of servlet 'dispatcherServlet' as ServletContext attribute with name [org.springframework.web.servlet.FrameworkServlet.CONTEXT.dispatcherServlet] 2015-11-20 10:59:07.466 INFO 14542 --- [nio-8000-exec-1] o.s.web.servlet.DispatcherServlet : FrameworkServlet 'dispatcherServlet': initialization completed in 55 ms 2015-11-20 10:59:07.466 DEBUG 14542 --- [nio-8000-exec-1] o.s.web.servlet.DispatcherServlet : Servlet 'dispatcherServlet' configured successfully 2015-11-20 10:59:07.496 DEBUG 14542 --- [nio-8000-exec-1] o.s.security.web.FilterChainProxy : /user/momentStats at position 1 of 10 in additional filter chain; firing Filter: 'WebAsyncManagerIntegrationFilter' 2015-11-20 10:59:07.497 DEBUG 14542 --- [nio-8000-exec-1] o.s.security.web.FilterChainProxy : /user/momentStats at position 2 of 10 in additional filter chain; firing Filter: 'SecurityContextPersistenceFilter' 2015-11-20 10:59:07.498 DEBUG 14542 --- [nio-8000-exec-1] w.c.HttpSessionSecurityContextRepository : No HttpSession currently exists 2015-11-20 10:59:07.498 DEBUG 14542 --- [nio-8000-exec-1] w.c.HttpSessionSecurityContextRepository : No SecurityContext was available from the HttpSession: null. A new one will be created. 2015-11-20 10:59:07.518 DEBUG 14542 --- [nio-8000-exec-1] o.s.security.web.FilterChainProxy : /user/momentStats at position 3 of 10 in additional filter chain; firing Filter: 'HeaderWriterFilter' 2015-11-20 10:59:07.519 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.header.writers.HstsHeaderWriter : Not injecting HSTS header since it did not match the requestMatcher org.springframework.security.web.header.writers.HstsHeaderWriter$SecureRequestMatcher@96c224 2015-11-20 10:59:07.519 DEBUG 14542 --- [nio-8000-exec-1] o.s.security.web.FilterChainProxy : /user/momentStats at position 4 of 10 in additional filter chain; firing Filter: 'LogoutFilter' 2015-11-20 10:59:07.519 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.u.matcher.AntPathRequestMatcher : Checking match of request : '/user/momentstats'; against '/logout' 2015-11-20 10:59:07.520 DEBUG 14542 --- [nio-8000-exec-1] o.s.security.web.FilterChainProxy : /user/momentStats at position 5 of 10 in additional filter chain; firing Filter: 'RequestCacheAwareFilter' 2015-11-20 10:59:07.522 DEBUG 14542 --- [nio-8000-exec-1] o.s.security.web.FilterChainProxy : /user/momentStats at position 6 of 10 in additional filter chain; firing Filter: 'SecurityContextHolderAwareRequestFilter' 2015-11-20 10:59:07.524 DEBUG 14542 --- [nio-8000-exec-1] o.s.security.web.FilterChainProxy : /user/momentStats at position 7 of 10 in additional filter chain; firing Filter: 'AnonymousAuthenticationFilter' 2015-11-20 10:59:07.532 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.a.AnonymousAuthenticationFilter : Populated SecurityContextHolder with anonymous token: 'org.springframework.security.authentication.AnonymousAuthenticationToken@9055e4a6: Principal: anonymousUser; Credentials: [PROTECTED]; Authenticated: true; Details: org.springframework.security.web.authentication.WebAuthenticationDetails@957e: RemoteIpAddress: 127.0.0.1; SessionId: null; Granted Authorities: ROLE_ANONYMOUS' 2015-11-20 10:59:07.532 DEBUG 14542 --- [nio-8000-exec-1] o.s.security.web.FilterChainProxy : /user/momentStats at position 8 of 10 in additional filter chain; firing Filter: 'SessionManagementFilter' 2015-11-20 10:59:07.532 DEBUG 14542 --- [nio-8000-exec-1] o.s.security.web.FilterChainProxy : /user/momentStats at position 9 of 10 in additional filter chain; firing Filter: 'ExceptionTranslationFilter' 2015-11-20 10:59:07.532 DEBUG 14542 --- [nio-8000-exec-1] o.s.security.web.FilterChainProxy : /user/momentStats at position 10 of 10 in additional filter chain; firing Filter: 'FilterSecurityInterceptor' 2015-11-20 10:59:07.533 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.u.matcher.AntPathRequestMatcher : Checking match of request : '/user/momentstats'; against '/art/**/making' 2015-11-20 10:59:07.533 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.u.matcher.AntPathRequestMatcher : Checking match of request : '/user/momentstats'; against '/orders/**/payment/wx' 2015-11-20 10:59:07.533 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.u.matcher.AntPathRequestMatcher : Checking match of request : '/user/momentstats'; against '/user/momentstats' 2015-11-20 10:59:07.534 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.a.i.FilterSecurityInterceptor : Secure object: FilterInvocation: URL: /user/momentStats; Attributes: [authenticated] 2015-11-20 10:59:07.534 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.a.i.FilterSecurityInterceptor : Previously Authenticated: org.springframework.security.authentication.AnonymousAuthenticationToken@9055e4a6: Principal: anonymousUser; Credentials: [PROTECTED]; Authenticated: true; Details: org.springframework.security.web.authentication.WebAuthenticationDetails@957e: RemoteIpAddress: 127.0.0.1; SessionId: null; Granted Authorities: ROLE_ANONYMOUS 2015-11-20 10:59:07.551 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.access.vote.AffirmativeBased : Voter: org.springframework.security.web.access.expression.WebExpressionVoter@4d0267b0, returned: -1 2015-11-20 10:59:07.563 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.a.ExceptionTranslationFilter : Access is denied (user is anonymous); redirecting to authentication entry point org.springframework.security.access.AccessDeniedException: Access is denied at org.springframework.security.access.vote.AffirmativeBased.decide(AffirmativeBased.java:83) at org.springframework.security.access.intercept.AbstractSecurityInterceptor.beforeInvocation(AbstractSecurityInterceptor.java:232) at org.springframework.security.web.access.intercept.FilterSecurityInterceptor.invoke(FilterSecurityInterceptor.java:123) at org.springframework.security.web.access.intercept.FilterSecurityInterceptor.doFilter(FilterSecurityInterceptor.java:90) at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:330) at org.springframework.security.web.access.ExceptionTranslationFilter.doFilter(ExceptionTranslationFilter.java:114) at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:330) at org.springframework.security.web.session.SessionManagementFilter.doFilter(SessionManagementFilter.java:122) at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:330) at org.springframework.security.web.authentication.AnonymousAuthenticationFilter.doFilter(AnonymousAuthenticationFilter.java:111) at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:330) at org.springframework.security.web.servletapi.SecurityContextHolderAwareRequestFilter.doFilter(SecurityContextHolderAwareRequestFilter.java:169) at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:330) at org.springframework.security.web.savedrequest.RequestCacheAwareFilter.doFilter(RequestCacheAwareFilter.java:48) at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:330) at org.springframework.security.web.authentication.logout.LogoutFilter.doFilter(LogoutFilter.java:120) at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:330) at org.springframework.security.web.header.HeaderWriterFilter.doFilterInternal(HeaderWriterFilter.java:64) at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:330) at org.springframework.security.web.context.SecurityContextPersistenceFilter.doFilter(SecurityContextPersistenceFilter.java:91) at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:330) at org.springframework.security.web.context.request.async.WebAsyncManagerIntegrationFilter.doFilterInternal(WebAsyncManagerIntegrationFilter.java:53) at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:330) at org.springframework.security.web.FilterChainProxy.doFilterInternal(FilterChainProxy.java:213) at org.springframework.security.web.FilterChainProxy.doFilter(FilterChainProxy.java:176) at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:239) at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) at io.vme.wechat.filter.SimpleCORSFilter.doFilterInternal(SimpleCORSFilter.java:49) at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:239) at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) at org.springframework.session.web.http.SessionRepositoryFilter.doFilterInternal(SessionRepositoryFilter.java:125) at org.springframework.session.web.http.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:65) at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:239) at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) at org.springframework.web.filter.HiddenHttpMethodFilter.doFilterInternal(HiddenHttpMethodFilter.java:77) at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:239) at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) at org.springframework.web.filter.CharacterEncodingFilter.doFilterInternal(CharacterEncodingFilter.java:85) at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:239) at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:219) at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:106) at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:502) at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:142) at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:79) at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:88) at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:518) at org.apache.coyote.http11.AbstractHttp11Processor.process(AbstractHttp11Processor.java:1091) at org.apache.coyote.AbstractProtocol$AbstractConnectionHandler.process(AbstractProtocol.java:673) at org.apache.tomcat.util.net.NioEndpoint$SocketProcessor.doRun(NioEndpoint.java:1526) at org.apache.tomcat.util.net.NioEndpoint$SocketProcessor.run(NioEndpoint.java:1482) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617) at org.apache.tomcat.util.threads.TaskThread$WrappingRunnable.run(TaskThread.java:61) at java.lang.Thread.run(Thread.java:745) 2015-11-20 10:59:07.565 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.util.matcher.AndRequestMatcher : Trying to match using NegatedRequestMatcher [requestMatcher=Ant [pattern='/**/favicon.ico']] 2015-11-20 10:59:07.565 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.u.matcher.AntPathRequestMatcher : Checking match of request : '/user/momentstats'; against '/**/favicon.ico' 2015-11-20 10:59:07.565 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.u.matcher.NegatedRequestMatcher : matches = true 2015-11-20 10:59:07.566 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.util.matcher.AndRequestMatcher : Trying to match using NegatedRequestMatcher [requestMatcher=MediaTypeRequestMatcher [contentNegotiationStrategy=org.springframework.web.accept.ContentNegotiationManager@6036ed6e, matchingMediaTypes=[application/json], useEquals=false, ignoredMediaTypes=[*/*]]] 2015-11-20 10:59:07.584 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.u.m.MediaTypeRequestMatcher : httpRequestMediaTypes=[text/html, application/xhtml+xml, image/webp, application/xml;q=0.9, */*;q=0.8] 2015-11-20 10:59:07.584 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.u.m.MediaTypeRequestMatcher : Processing text/html 2015-11-20 10:59:07.584 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.u.m.MediaTypeRequestMatcher : application/json .isCompatibleWith text/html = false 2015-11-20 10:59:07.584 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.u.m.MediaTypeRequestMatcher : Processing application/xhtml+xml 2015-11-20 10:59:07.584 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.u.m.MediaTypeRequestMatcher : application/json .isCompatibleWith application/xhtml+xml = false 2015-11-20 10:59:07.584 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.u.m.MediaTypeRequestMatcher : Processing image/webp 2015-11-20 10:59:07.584 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.u.m.MediaTypeRequestMatcher : application/json .isCompatibleWith image/webp = false 2015-11-20 10:59:07.584 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.u.m.MediaTypeRequestMatcher : Processing application/xml;q=0.9 2015-11-20 10:59:07.584 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.u.m.MediaTypeRequestMatcher : application/json .isCompatibleWith application/xml;q=0.9 = false 2015-11-20 10:59:07.584 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.u.m.MediaTypeRequestMatcher : Processing */*;q=0.8 2015-11-20 10:59:07.584 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.u.m.MediaTypeRequestMatcher : Ignoring 2015-11-20 10:59:07.584 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.u.m.MediaTypeRequestMatcher : Did not match any media types 2015-11-20 10:59:07.584 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.u.matcher.NegatedRequestMatcher : matches = true 2015-11-20 10:59:07.584 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.util.matcher.AndRequestMatcher : Trying to match using NegatedRequestMatcher [requestMatcher=RequestHeaderRequestMatcher [expectedHeaderName=X-Requested-With, expectedHeaderValue=XMLHttpRequest]] 2015-11-20 10:59:07.585 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.u.matcher.NegatedRequestMatcher : matches = true 2015-11-20 10:59:07.585 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.util.matcher.AndRequestMatcher : All requestMatchers returned true 2015-11-20 10:59:07.593 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.s.HttpSessionRequestCache : DefaultSavedRequest added to Session: DefaultSavedRequest[http://127.0.0.1:8000/user/momentStats] 2015-11-20 10:59:07.594 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.a.ExceptionTranslationFilter : Calling Authentication entry point. 2015-11-20 10:59:07.595 DEBUG 14542 --- [nio-8000-exec-1] o.s.s.w.a.Http403ForbiddenEntryPoint : Pre-authenticated entry point called. Rejecting access 2015-11-20 10:59:07.595 DEBUG 14542 --- [nio-8000-exec-1] w.c.HttpSessionSecurityContextRepository : SecurityContext is empty or contents are anonymous - context will not be stored in HttpSession. 2015-11-20 10:59:07.772 DEBUG 14542 --- [nio-8000-exec-1] s.s.w.c.SecurityContextPersistenceFilter : SecurityContextHolder now cleared, as request processing completed 2015-11-20 10:59:07.784 DEBUG 14542 --- [nio-8000-exec-1] o.s.web.servlet.DispatcherServlet : DispatcherServlet with name 'dispatcherServlet' processing GET request for [/error] 2015-11-20 10:59:07.787 DEBUG 14542 --- [nio-8000-exec-1] s.w.s.m.m.a.RequestMappingHandlerMapping : Looking up handler method for path /error 2015-11-20 10:59:07.791 DEBUG 14542 --- [nio-8000-exec-1] s.w.s.m.m.a.RequestMappingHandlerMapping : Returning handler method [public io.vme.wechat.model.dto.ErrorDTO io.vme.wechat.controller.VMEErrorHandler.handleError(javax.servlet.http.HttpServletRequest)] 2015-11-20 10:59:07.794 DEBUG 14542 --- [nio-8000-exec-1] o.s.web.servlet.DispatcherServlet : Last-Modified value for [/error] is: -1 2015-11-20 10:59:08.011 DEBUG 14542 --- [nio-8000-exec-1] m.m.a.RequestResponseBodyMethodProcessor : Written [org.springframework.http.converter.json.MappingJacksonValue@663d36b1] as "application/json" using [org.springframework.http.converter.json.MappingJackson2HttpMessageConverter@68a39825] 2015-11-20 10:59:08.011 DEBUG 14542 --- [nio-8000-exec-1] o.s.web.servlet.DispatcherServlet : Null ModelAndView returned to DispatcherServlet with name 'dispatcherServlet': assuming HandlerAdapter completed request handling 2015-11-20 10:59:08.011 DEBUG 14542 --- [nio-8000-exec-1] o.s.web.servlet.DispatcherServlet : Successfully completed request 2015-11-20 10:59:08.480 DEBUG 14542 --- [nio-8000-exec-2] o.s.security.web.FilterChainProxy : /favicon.ico at position 1 of 10 in additional filter chain; firing Filter: 'WebAsyncManagerIntegrationFilter' 2015-11-20 10:59:08.481 DEBUG 14542 --- [nio-8000-exec-2] o.s.security.web.FilterChainProxy : /favicon.ico at position 2 of 10 in additional filter chain; firing Filter: 'SecurityContextPersistenceFilter' 2015-11-20 10:59:08.493 DEBUG 14542 --- [nio-8000-exec-2] w.c.HttpSessionSecurityContextRepository : HttpSession returned null object for SPRING_SECURITY_CONTEXT 2015-11-20 10:59:08.494 DEBUG 14542 --- [nio-8000-exec-2] w.c.HttpSessionSecurityContextRepository : No SecurityContext was available from the HttpSession: org.springframework.session.web.http.SessionRepositoryFilter$SessionRepositoryRequestWrapper$HttpSessionWrapper@5fc0b4a0. A new one will be created. 2015-11-20 10:59:08.494 DEBUG 14542 --- [nio-8000-exec-2] o.s.security.web.FilterChainProxy : /favicon.ico at position 3 of 10 in additional filter chain; firing Filter: 'HeaderWriterFilter' 2015-11-20 10:59:08.494 DEBUG 14542 --- [nio-8000-exec-2] o.s.s.w.header.writers.HstsHeaderWriter : Not injecting HSTS header since it did not match the requestMatcher org.springframework.security.web.header.writers.HstsHeaderWriter$SecureRequestMatcher@96c224 2015-11-20 10:59:08.494 DEBUG 14542 --- [nio-8000-exec-2] o.s.security.web.FilterChainProxy : /favicon.ico at position 4 of 10 in additional filter chain; firing Filter: 'LogoutFilter' 2015-11-20 10:59:08.494 DEBUG 14542 --- [nio-8000-exec-2] o.s.s.w.u.matcher.AntPathRequestMatcher : Checking match of request : '/favicon.ico'; against '/logout' 2015-11-20 10:59:08.494 DEBUG 14542 --- [nio-8000-exec-2] o.s.security.web.FilterChainProxy : /favicon.ico at position 5 of 10 in additional filter chain; firing Filter: 'RequestCacheAwareFilter' 2015-11-20 10:59:08.494 DEBUG 14542 --- [nio-8000-exec-2] o.s.s.w.s.DefaultSavedRequest : pathInfo: both null (property equals) 2015-11-20 10:59:08.494 DEBUG 14542 --- [nio-8000-exec-2] o.s.s.w.s.DefaultSavedRequest : queryString: both null (property equals) 2015-11-20 10:59:08.495 DEBUG 14542 --- [nio-8000-exec-2] o.s.s.w.s.DefaultSavedRequest : requestURI: arg1=/user/momentStats; arg2=/favicon.ico (property not equals) 2015-11-20 10:59:08.495 DEBUG 14542 --- [nio-8000-exec-2] o.s.s.w.s.HttpSessionRequestCache : saved request doesn't match 2015-11-20 10:59:08.495 DEBUG 14542 --- [nio-8000-exec-2] o.s.security.web.FilterChainProxy : /favicon.ico at position 6 of 10 in additional filter chain; firing Filter: 'SecurityContextHolderAwareRequestFilter' 2015-11-20 10:59:08.495 DEBUG 14542 --- [nio-8000-exec-2] o.s.security.web.FilterChainProxy : /favicon.ico at position 7 of 10 in additional filter chain; firing Filter: 'AnonymousAuthenticationFilter' 2015-11-20 10:59:08.495 DEBUG 14542 --- [nio-8000-exec-2] o.s.s.w.a.AnonymousAuthenticationFilter : Populated SecurityContextHolder with anonymous token: 'org.springframework.security.authentication.AnonymousAuthenticationToken@6faba4dc: Principal: anonymousUser; Credentials: [PROTECTED]; Authenticated: true; Details: org.springframework.security.web.authentication.WebAuthenticationDetails@fffed504: RemoteIpAddress: 127.0.0.1; SessionId: e3e46247-a88a-4c60-8574-6579f00d5e9d; Granted Authorities: ROLE_ANONYMOUS' 2015-11-20 10:59:08.495 DEBUG 14542 --- [nio-8000-exec-2] o.s.security.web.FilterChainProxy : /favicon.ico at position 8 of 10 in additional filter chain; firing Filter: 'SessionManagementFilter' 2015-11-20 10:59:08.495 DEBUG 14542 --- [nio-8000-exec-2] o.s.security.web.FilterChainProxy : /favicon.ico at position 9 of 10 in additional filter chain; firing Filter: 'ExceptionTranslationFilter' 2015-11-20 10:59:08.495 DEBUG 14542 --- [nio-8000-exec-2] o.s.security.web.FilterChainProxy : /favicon.ico at position 10 of 10 in additional filter chain; firing Filter: 'FilterSecurityInterceptor' 2015-11-20 10:59:08.495 DEBUG 14542 --- [nio-8000-exec-2] o.s.s.w.u.matcher.AntPathRequestMatcher : Checking match of request : '/favicon.ico'; against '/art/**/making' 2015-11-20 10:59:08.495 DEBUG 14542 --- [nio-8000-exec-2] o.s.s.w.u.matcher.AntPathRequestMatcher : Checking match of request : '/favicon.ico'; against '/orders/**/payment/wx' 2015-11-20 10:59:08.495 DEBUG 14542 --- [nio-8000-exec-2] o.s.s.w.u.matcher.AntPathRequestMatcher : Checking match of request : '/favicon.ico'; against '/user/momentstats' 2015-11-20 10:59:08.495 DEBUG 14542 --- [nio-8000-exec-2] o.s.s.w.a.i.FilterSecurityInterceptor : Secure object: FilterInvocation: URL: /favicon.ico; Attributes: [permitAll] 2015-11-20 10:59:08.495 DEBUG 14542 --- [nio-8000-exec-2] o.s.s.w.a.i.FilterSecurityInterceptor : Previously Authenticated: org.springframework.security.authentication.AnonymousAuthenticationToken@6faba4dc: Principal: anonymousUser; Credentials: [PROTECTED]; Authenticated: true; Details: org.springframework.security.web.authentication.WebAuthenticationDetails@fffed504: RemoteIpAddress: 127.0.0.1; SessionId: e3e46247-a88a-4c60-8574-6579f00d5e9d; Granted Authorities: ROLE_ANONYMOUS 2015-11-20 10:59:08.497 DEBUG 14542 --- [nio-8000-exec-2] o.s.s.access.vote.AffirmativeBased : Voter: org.springframework.security.web.access.expression.WebExpressionVoter@4d0267b0, returned: 1 2015-11-20 10:59:08.497 DEBUG 14542 --- [nio-8000-exec-2] o.s.s.w.a.i.FilterSecurityInterceptor : Authorization successful 2015-11-20 10:59:08.497 DEBUG 14542 --- [nio-8000-exec-2] o.s.s.w.a.i.FilterSecurityInterceptor : RunAsManager did not change Authentication object 2015-11-20 10:59:08.497 DEBUG 14542 --- [nio-8000-exec-2] o.s.security.web.FilterChainProxy : /favicon.ico reached end of additional filter chain; proceeding with original chain 2015-11-20 10:59:08.497 DEBUG 14542 --- [nio-8000-exec-2] o.s.web.servlet.DispatcherServlet : DispatcherServlet with name 'dispatcherServlet' processing GET request for [/favicon.ico] 2015-11-20 10:59:08.498 DEBUG 14542 --- [nio-8000-exec-2] o.s.w.s.handler.SimpleUrlHandlerMapping : Matching patterns for request [/favicon.ico] are [/**/favicon.ico] 2015-11-20 10:59:08.499 DEBUG 14542 --- [nio-8000-exec-2] o.s.w.s.handler.SimpleUrlHandlerMapping : URI Template variables for request [/favicon.ico] are {} 2015-11-20 10:59:08.500 DEBUG 14542 --- [nio-8000-exec-2] o.s.w.s.handler.SimpleUrlHandlerMapping : Mapping [/favicon.ico] to HandlerExecutionChain with handler [ResourceHttpRequestHandler [locations=[class path resource [META-INF/resources/], class path resource [resources/], class path resource [static/], class path resource [public/], class path resource []], resolvers=[org.springframework.web.servlet.resource.PathResourceResolver@320e179f]]] and 1 interceptor 2015-11-20 10:59:08.501 DEBUG 14542 --- [nio-8000-exec-2] o.s.web.servlet.DispatcherServlet : Last-Modified value for [/favicon.ico] is: -1 2015-11-20 10:59:08.531 DEBUG 14542 --- [nio-8000-exec-2] w.c.HttpSessionSecurityContextRepository : SecurityContext is empty or contents are anonymous - context will not be stored in HttpSession. 2015-11-20 10:59:08.538 DEBUG 14542 --- [nio-8000-exec-2] tRepository$SaveToSessionResponseWrapper : Skip invoking on 2015-11-20 10:59:08.539 DEBUG 14542 --- [nio-8000-exec-2] o.s.web.servlet.DispatcherServlet : Null ModelAndView returned to DispatcherServlet with name 'dispatcherServlet': assuming HandlerAdapter completed request handling 2015-11-20 10:59:08.540 DEBUG 14542 --- [nio-8000-exec-2] o.s.web.servlet.DispatcherServlet : Successfully completed request 2015-11-20 10:59:08.541 DEBUG 14542 --- [nio-8000-exec-2] o.s.s.w.a.ExceptionTranslationFilter : Chain processed normally 2015-11-20 10:59:08.542 DEBUG 14542 --- [nio-8000-exec-2] s.s.w.c.SecurityContextPersistenceFilter : SecurityContextHolder now cleared, as request processing completed
将您的Spring Boot版本更新为1.3.0.RELEASE,您将Http401AuthenticationEntryPoint免费获得。像这样在您的安全配置中配置身份验证入口点:
Http401AuthenticationEntryPoint
@Override protected void configure(HttpSecurity http) throws Exception { http .csrf().disable() .authorizeRequests() .antMatchers(PROTECTED_RESOURCES) .hasRole("USER") .anyRequest() .permitAll() .and() .anonymous().disable() .exceptionHandling() .authenticationEntryPoint(new org.springframework.boot.autoconfigure.security.Http401AuthenticationEntryPoint("headerValue")); }
然后Spring Boot将返回HTTP 401:
HTTP 401
Status Code: 401 Unauthorized Cache-Control: no-cache, no-store, max-age=0, must-revalidate Expires: 0 Pragma: no-cache Server: Apache-Coyote/1.1 Transfer-Encoding: chunked WWW-Authenticate: headerValue X-Content-Type-Options: nosniff x-xss-protection: 1; mode=block