Grails spring security在向控制器操作发出ajax请求时出现403错误
Posted
技术标签:
【中文标题】Grails spring security在向控制器操作发出ajax请求时出现403错误【英文标题】:Grails spring security getting 403 error while making ajax request to controller action 【发布时间】:2016-01-09 12:57:15 【问题描述】:这是我在 config.groovy 中的 grails.plugin.springsecurity.filterChain.chainMap
grails.plugin.springsecurity.filterChain.chainMap = [
// '/api/v/**': 'JOINED_FILTERS,-exceptionTranslationFilter,-authenticationProcessingFilter,-securityContextPersistenceFilter,-rememberMeAuthenticationFilter,-basicAuthenticationFilter,-basicExceptionTranslationFilter',
'/api/v/**': 'JOINED_FILTERS,-exceptionTranslationFilter,-authenticationProcessingFilter,-securityContextPersistenceFilter,-rememberMeAuthenticationFilter',
'/api/**': 'JOINED_FILTERS,-exceptionTranslationFilter,-apiAuthenticationFilter,-apiExceptionTranslationFilter',
'/**': 'JOINED_FILTERS,-basicAuthenticationFilter,-basicExceptionTranslationFilter,-apiAuthenticationFilter,-apiExceptionTranslationFilter'
]
我制作 ajax 的控制器也有 permitAll 规则:
grails.plugin.springsecurity.controllerAnnotations.staticRules = [
'/': ['permitAll'],
'/index': ['permitAll'],
'/index.gsp': ['permitAll'],
'/assets/**': ['permitAll'],
'/**/js/**': ['permitAll'],
'/**/css/**': ['permitAll'],
'/**/images/**': ['permitAll'],
'/**/img/**': ['permitAll'],
'/**/favicon.ico': ['permitAll'],
'/back/**': ['permitAll'],
'/lib/**': ['permitAll'],
'/ajax/dck/**': ['permitAll'],
'/api/**': ['permitAll'],
'/logout/**': ['permitAll'],
'/register/**': ['permitAll'],
'/webinar/test/**': ['permitAll'],
'/i/**': ['permitAll'],
'/a/**': ['permitAll'],
'/hangout/**': ['permitAll'],
'/pusher/**': ['permitAll'],
'/go/**': ['permitAll'],
'/redactor/**': ['permitAll'],
'/bootstrap/**': ['permitAll'],
'/bootstrap-switch/**': ['permitAll'],
'/js/**': ['permitAll'],
'/error/**': ['permitAll'],
'/integration/**': ['permitAll']
]
网址是/integration/ajaxSaveIntegrationData
,请求是http post。
spring 安全调试日志显示了下面这个 ajax 请求的日志:
2015-10-12 06:20:17,053Z DEBUG [http-bio-8443-exec-3] Checking match of request : '/integrations/ajaxsaveintegrationdata'; against '/api/v/**'
(SLF4JLog.java:debug:128) security.web.util.matcher.AntPathRequestMatcher
2015-10-12 06:20:17,053Z DEBUG [http-bio-8443-exec-3] Checking match of request : '/integrations/ajaxsaveintegrationdata'; against '/api/**'
(SLF4JLog.java:debug:128) security.web.util.matcher.AntPathRequestMatcher
2015-10-12 06:20:17,053Z DEBUG [http-bio-8443-exec-3] Request '/integrations/ajaxsaveintegrationdata' matched by universal pattern '/**'
(SLF4JLog.java:debug:128) security.web.util.matcher.AntPathRequestMatcher
2015-10-12 06:20:17,053Z DEBUG [http-bio-8443-exec-3] /integrations/ajaxSaveIntegrationData at position 1 of 10 in additional filter chain; firing Filter: 'SecurityContextPersistenceFilter'
(SLF4JLog.java:debug:128) org.springframework.security.web.FilterChainProxy
2015-10-12 06:20:17,054Z DEBUG [http-bio-8443-exec-3] Obtained a valid SecurityContext from SPRING_SECURITY_CONTEXT: 'org.springframework.security.core.context.SecurityContextImpl@963dd870: Authentication: org.springframework.security.authentication.UsernamePasswordAuthenticationToken@963dd870: Principal: rahulserver; Credentials: [PROTECTED]; Authenticated: true; Details: null; Granted Authorities: ROLE_USER, ROLE_WEBINAR, ROLE_API, ROLE_PREMIUM_PLAN, ROLE_API_USER'
(SLF4JLog.java:debug:128) springframework.security.web.context.HttpSessionSecurityContextRepository
2015-10-12 06:20:17,054Z DEBUG [http-bio-8443-exec-3] /integrations/ajaxSaveIntegrationData at position 2 of 10 in additional filter chain; firing Filter: 'ApiAuthenticationFilter'
(SLF4JLog.java:debug:128) org.springframework.security.web.FilterChainProxy
2015-10-12 06:20:17,054Z DEBUG [http-bio-8443-exec-3] /integrations/ajaxSaveIntegrationData at position 3 of 10 in additional filter chain; firing Filter: 'MutableLogoutFilter'
(SLF4JLog.java:debug:128) org.springframework.security.web.FilterChainProxy
2015-10-12 06:20:17,054Z DEBUG [http-bio-8443-exec-3] /integrations/ajaxSaveIntegrationData at position 4 of 10 in additional filter chain; firing Filter: 'RequestHolderAuthenticationFilter'
(SLF4JLog.java:debug:128) org.springframework.security.web.FilterChainProxy
2015-10-12 06:20:17,054Z DEBUG [http-bio-8443-exec-3] /integrations/ajaxSaveIntegrationData at position 5 of 10 in additional filter chain; firing Filter: 'SecurityContextHolderAwareRequestFilter'
(SLF4JLog.java:debug:128) org.springframework.security.web.FilterChainProxy
2015-10-12 06:20:17,054Z DEBUG [http-bio-8443-exec-3] /integrations/ajaxSaveIntegrationData at position 6 of 10 in additional filter chain; firing Filter: 'GrailsRememberMeAuthenticationFilter'
(SLF4JLog.java:debug:128) org.springframework.security.web.FilterChainProxy
2015-10-12 06:20:17,054Z DEBUG [http-bio-8443-exec-3] SecurityContextHolder not populated with remember-me token, as it already contained: 'org.springframework.security.authentication.UsernamePasswordAuthenticationToken@963dd870: Principal: rahulserver; Credentials: [PROTECTED]; Authenticated: true; Details: null; Granted Authorities: ROLE_USER, ROLE_WEBINAR, ROLE_API, ROLE_PREMIUM_PLAN, ROLE_API_USER'
(SLF4JLog.java:debug:128) plugin.springsecurity.web.filter.GrailsRememberMeAuthenticationFilter
2015-10-12 06:20:17,054Z DEBUG [http-bio-8443-exec-3] /integrations/ajaxSaveIntegrationData at position 7 of 10 in additional filter chain; firing Filter: 'GrailsAnonymousAuthenticationFilter'
(SLF4JLog.java:debug:128) org.springframework.security.web.FilterChainProxy
2015-10-12 06:20:17,055Z DEBUG [http-bio-8443-exec-3] SecurityContextHolder not populated with anonymous token, as it already contained: 'org.springframework.security.authentication.UsernamePasswordAuthenticationToken@963dd870: Principal: rahulserver; Credentials: [PROTECTED]; Authenticated: true; Details: null; Granted Authorities: ROLE_USER, ROLE_WEBINAR, ROLE_API, ROLE_PREMIUM_PLAN, ROLE_API_USER'
(GrailsAnonymousAuthenticationFilter.java:applyAnonymousForThisRequest:67) plugin.springsecurity.web.filter.GrailsAnonymousAuthenticationFilter
2015-10-12 06:20:17,058Z DEBUG [http-bio-8443-exec-3] /integrations/ajaxSaveIntegrationData at position 8 of 10 in additional filter chain; firing Filter: 'ExceptionTranslationFilter'
(SLF4JLog.java:debug:128) org.springframework.security.web.FilterChainProxy
2015-10-12 06:20:17,058Z DEBUG [http-bio-8443-exec-3] /integrations/ajaxSaveIntegrationData at position 9 of 10 in additional filter chain; firing Filter: 'ExceptionTranslationFilter'
(SLF4JLog.java:debug:128) org.springframework.security.web.FilterChainProxy
2015-10-12 06:20:17,058Z DEBUG [http-bio-8443-exec-3] /integrations/ajaxSaveIntegrationData at position 10 of 10 in additional filter chain; firing Filter: 'FilterSecurityInterceptor'
(SLF4JLog.java:debug:128) org.springframework.security.web.FilterChainProxy
2015-10-12 06:20:17,060Z DEBUG [http-bio-8443-exec-3] Secure object: FilterInvocation: URL: /integrations/ajaxSaveIntegrationData; Attributes: [_DENY_]
(SLF4JLog.java:debug:128) security.web.access.intercept.FilterSecurityInterceptor
2015-10-12 06:20:17,060Z DEBUG [http-bio-8443-exec-3] Previously Authenticated: org.springframework.security.authentication.UsernamePasswordAuthenticationToken@963dd870: Principal: rahulserver; Credentials: [PROTECTED]; Authenticated: true; Details: null; Granted Authorities: ROLE_USER, ROLE_WEBINAR, ROLE_API, ROLE_PREMIUM_PLAN, ROLE_API_USER
(SLF4JLog.java:debug:128) security.web.access.intercept.FilterSecurityInterceptor
2015-10-12 06:20:17,060Z DEBUG [http-bio-8443-exec-3] getReachableGrantedAuthorities() - From the roles [ROLE_USER, ROLE_WEBINAR, ROLE_API, ROLE_PREMIUM_PLAN, ROLE_API_USER] one can reach [ROLE_PREMIUM_PLAN, ROLE_USER, ROLE_API, ROLE_API_USER, ROLE_WEBINAR] in zero or more steps.
(SLF4JLog.java:debug:128) springframework.security.access.hierarchicalroles.RoleHierarchyImpl
2015-10-12 06:20:17,060Z DEBUG [http-bio-8443-exec-3] SecurityContextHolder now cleared, as request processing completed
(SLF4JLog.java:debug:128) springframework.security.web.context.SecurityContextPersistenceFilter
2015-10-12 06:20:17,061Z ERROR [http-bio-8443-exec-3] Servlet.service() for servlet [default] in context with path [] threw exception [Filter execution threw an exception] with root cause
(StandardWrapperValve.java:invoke:258) ContainerBase.[Tomcat].[localhost].[/].[default] java.lang.IllegalAccessError: tried to access method org.springframework.security.access.vote.AbstractAccessDecisionManager.checkAllowIfAllAbstainDecisions()V from class grails.plugin.springsecurity.access.vote.AuthenticatedVetoableDecisionManager$$EPQsT6eI
at grails.plugin.springsecurity.access.vote.AuthenticatedVetoableDecisionManager$$EPQsT6eI.decide(AuthenticatedVetoableDecisionManager.java:43)
at grails.plugin.springsecurity.access.vote.AuthenticatedVetoableDecisionManager$$DPQsT6eI.decide(Unknown Source)
at grails.plugin.springsecurity.access.vote.AuthenticatedVetoableDecisionManager.decide(AuthenticatedVetoableDecisionManager.java)
at org.springframework.security.access.intercept.AbstractSecurityInterceptor.beforeInvocation(AbstractSecurityInterceptor.java:206)
at org.springframework.security.web.access.intercept.FilterSecurityInterceptor.invoke(FilterSecurityInterceptor.java:115)
at org.springframework.security.web.access.intercept.FilterSecurityInterceptor.doFilter(FilterSecurityInterceptor.java:84)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
at org.springframework.security.web.access.ExceptionTranslationFilter.doFilter(ExceptionTranslationFilter.java:113)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
at org.springframework.security.web.access.ExceptionTranslationFilter.doFilter(ExceptionTranslationFilter.java:113)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
at grails.plugin.springsecurity.web.filter.GrailsAnonymousAuthenticationFilter.doFilter(GrailsAnonymousAuthenticationFilter.java:53)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
at org.springframework.security.web.authentication.rememberme.RememberMeAuthenticationFilter.doFilter(RememberMeAuthenticationFilter.java:146)
at grails.plugin.springsecurity.web.filter.GrailsRememberMeAuthenticationFilter.doFilter(GrailsRememberMeAuthenticationFilter.java)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
at org.springframework.security.web.servletapi.SecurityContextHolderAwareRequestFilter.doFilter(SecurityContextHolderAwareRequestFilter.java:154)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
at org.springframework.security.web.authentication.AbstractAuthenticationProcessingFilter.doFilter(AbstractAuthenticationProcessingFilter.java:199)
at grails.plugin.springsecurity.web.authentication.RequestHolderAuthenticationFilter.doFilter(RequestHolderAuthenticationFilter.java:53)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
at grails.plugin.springsecurity.web.authentication.logout.MutableLogoutFilter.doFilter(MutableLogoutFilter.java:62)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
at org.springframework.security.web.authentication.AbstractAuthenticationProcessingFilter.doFilter(AbstractAuthenticationProcessingFilter.java:199)
at security.ApiAuthenticationFilter.doFilter(ApiAuthenticationFilter.groovy)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
at org.springframework.security.web.context.SecurityContextPersistenceFilter.doFilter(SecurityContextPersistenceFilter.java:87)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
at org.springframework.security.web.FilterChainProxy.doFilterInternal(FilterChainProxy.java:192)
at org.springframework.security.web.FilterChainProxy.doFilter(FilterChainProxy.java:160)
at org.springframework.web.filter.DelegatingFilterProxy.invokeDelegate(DelegatingFilterProxy.java:344)
at org.springframework.web.filter.DelegatingFilterProxy.doFilter(DelegatingFilterProxy.java:261)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:241)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:208)
at org.codehaus.groovy.grails.web.servlet.mvc.GrailsWebRequestFilter.doFilterInternal(GrailsWebRequestFilter.java:69)
at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:241)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:208)
at org.codehaus.groovy.grails.web.filters.HiddenHttpMethodFilter.doFilterInternal(HiddenHttpMethodFilter.java:67)
at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:241)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:208)
at org.springframework.web.filter.CharacterEncodingFilter.doFilterInternal(CharacterEncodingFilter.java:88)
at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
at org.springframework.web.filter.DelegatingFilterProxy.invokeDelegate(DelegatingFilterProxy.java:344)
at org.springframework.web.filter.DelegatingFilterProxy.doFilter(DelegatingFilterProxy.java:261)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:241)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:208)
at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:220)
at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:122)
at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:171)
at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:103)
at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:116)
at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:408)
at org.apache.coyote.http11.AbstractHttp11Processor.process(AbstractHttp11Processor.java:1070)
at org.apache.coyote.AbstractProtocol$AbstractConnectionHandler.process(AbstractProtocol.java:611)
at org.apache.tomcat.util.net.JIoEndpoint$SocketProcessor.run(JIoEndpoint.java:314)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1145)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:615)
at org.apache.tomcat.util.threads.TaskThread$WrappingRunnable.run(TaskThread.java:61)
at java.lang.Thread.run(Thread.java:745)
控制器有permitAll:
@Secured(["permitAll"])
class IntegrationController
那么为什么它通过 ajax 给我 403 错误?
【问题讨论】:
【参考方案1】:将此添加到您的控制器代码中
static allowedMethods = [ajaxSaveIntegrationData : 'POST']
【讨论】:
以上是关于Grails spring security在向控制器操作发出ajax请求时出现403错误的主要内容,如果未能解决你的问题,请参考以下文章
Grails - 卸载 Spring Security Core
Grails - grails-spring-security-rest - 无法从 application.yml 加载 jwt 机密
grails-spring-security-rest 插件和悲观锁定