在超时发生后调用Servlet方法(控制器)时,Spring Security 3.1重定向到登录不起作用

时间:2014-04-25 21:31:55

标签: java spring spring-mvc spring-security

问题类似: Spring Security 3.1 redirect to login doesn't work

我将Spring 3.1与Spring Mvc和Spring Security结合使用。

这里是app-security-config。

<security:http  auto-config="true" use-expressions="true">
    <security:form-login login-page="/login.jsp" 
                    login-processing-url="/j_spring_security_check" 
                    default-target-url="/pages/index.jsp"
                    always-use-default-target="true"
                    authentication-failure-url="/login.jsp?login_error=1"/>
                    <security:access-denied-handler ref="accessDeniedHandler"/>

    <!--  Session Invalida-->
    <security:logout invalidate-session="true" logout-success-url="/login.jsp" delete-cookies="JSESSIONID" />

    <!--  Interceptadores -->
    <!-- security:intercept-url pattern="/expire.jsp*" filters="none"/-->
    <!-- security:intercept-url pattern="/login.jsp*" access="ROLE_ANONYMOUS" requires-channel="https"/-->

    <security:intercept-url pattern="/expire.jsp" access="permitAll" />
    <security:intercept-url pattern="/AccessDenied.jsp*" access="permitAll" />
    <security:intercept-url pattern="/scripts/*" access="permitAll" />
    <security:intercept-url pattern="/styles/*" access="permitAll" />
    <security:intercept-url pattern="/images/*" access="permitAll" />
    <security:intercept-url pattern="/login.jsp" access="permitAll" requires-channel="https"/>
    <security:intercept-url pattern="/pages/**" access="hasAnyRole(${role.autenticated})"  requires-channel="https"/>
    <security:http-basic/>

    <!--  Establece maximas sesiones para un usuarios -->
    <security:session-management session-fixation-protection="none" >
       <security:concurrency-control max-sessions="1" error-if-maximum-exceeded="true" />
    </security:session-management>         

    <!--  Establece maximas sesiones para un usuarios -->
    <!-- security:session-management invalid-session-url="/expire.jsp"  session-fixation-protection="none" >
       <security:concurrency-control max-sessions="1" error-if-maximum-exceeded="true" expired-url="/expire.jsp"/>
    </security:session-management-->    

    <!-- security:session-management invalid-session-url="/login.jsp?login_error=2" session-authentication-error-url="/login.jsp?login_error=3" session-fixation-protection="none" >
       <security:concurrency-control max-sessions="1" error-if-maximum-exceeded="true" expired-url="/login.jsp?login_error=4"/>
    </security:session-management-->   

    <security:port-mappings>
        <security:port-mapping http='8080' https="8443"/>
    </security:port-mappings>

</security:http>


<beans:bean id="accessDeniedHandler" class="ar.com.firstdata.upploader.web.mvc.controller.AccessDeniedController">
    <beans:property name="accessDeniedUrl" value="/AccessDenied.jsp"> </beans:property>
</beans:bean> 

web.xml

<context-param>
    <param-name>contextConfigLocation</param-name>
    <param-value>classpath:META-INF/spring/*-config.xml</param-value>
</context-param>

<jsp-config>
    <taglib>
        <taglib-uri>sitemesh-page</taglib-uri>
        <taglib-location>/tld/sitemesh-page.tld</taglib-location>
    </taglib>

    <taglib>
        <taglib-uri>sitemesh-decorator</taglib-uri>
        <taglib-location>/tld/sitemesh-decorator.tld</taglib-location>
    </taglib>

    <taglib>
        <taglib-uri>/spring</taglib-uri>
        <taglib-location>/META-INF/spring.tld</taglib-location>
    </taglib>
</jsp-config>

<filter>
    <filter-name>springSecurityFilterChain</filter-name>
    <filter-class>org.springframework.web.filter.DelegatingFilterProxy</filter-class>
</filter>

<filter-mapping>
    <filter-name>springSecurityFilterChain</filter-name>
    <url-pattern>/*</url-pattern>
    <dispatcher>REQUEST</dispatcher>
    <dispatcher>FORWARD</dispatcher>
</filter-mapping>

<listener>
    <listener-class>
        org.springframework.web.context.ContextLoaderListener
    </listener-class>
</listener>

<!-- SiteMesh -->
<filter>
    <filter-name>sitemesh</filter-name>
    <filter-class>com.opensymphony.sitemesh.webapp.SiteMeshFilter</filter-class>
</filter>
<filter-mapping>
    <filter-name>sitemesh</filter-name>
    <url-pattern>*.html</url-pattern>
</filter-mapping>
<filter-mapping>
    <filter-name>sitemesh</filter-name>
    <url-pattern>*.htm</url-pattern>
</filter-mapping>
<filter-mapping>
    <filter-name>sitemesh</filter-name>
    <url-pattern>*.jsp</url-pattern>
</filter-mapping>

<listener>
    <listener-class>
        org.springframework.security.web.session.HttpSessionEventPublisher
    </listener-class>
</listener>

<servlet>
    <servlet-name>dispatcher</servlet-name>
    <servlet-class>
        org.springframework.web.servlet.DispatcherServlet
    </servlet-class>
    <load-on-startup>1</load-on-startup>
</servlet>

<session-config>
    <session-timeout>1</session-timeout>
</session-config>

<servlet-mapping>
    <servlet-name>dispatcher</servlet-name>
    <url-pattern>*.app</url-pattern>
</servlet-mapping>

<welcome-file-list>
    <welcome-file>login.jsp</welcome-file>
</welcome-file-list>

只有当尝试访问一些以调用控制器方法结束的操作时才会出现问题:

<bean id="urlMapping" class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping">
    <property name="mappings">
        <props>
            <prop key="/pages/findConfData.app">configurationController</prop>
            <prop key="/pages/readLoadXML.app">configurationController</prop>
            <prop key="/pages/addElementToList.app">configurationController</prop>
            <prop key="/pages/eraseElementToList.app">configurationController</prop>
            <prop key="/pages/persistXMLfiletransfer.app">configurationController</prop>
            <prop key="/pages/findLoggedUser.app">configurationController</prop>
        </props>            
    </property>
</bean>

正如我所说,行为类似于@spauny所公开的行为,在日志中显示:&#34;访问被拒绝(用户是匿名的);重定向到身份验证入口点&#34;,在AccessDeniedException之后没有任何反应,......

这是一种情况: 如果我花费在web.xml中列出的时间

<session-config>
    <session-timeout>1</session-timeout>
</session-config>

我调用了一个受限制的页面(在&#34; / pages / **&#34;下)将我重定向到登录页面...... 但是当尝试调用一些最终调用控制器方法的操作时 -suppose删除列表中的行 -

<prop key="/pages/eraseElementToList.app">configurationController</prop>

@RequestMapping(method = RequestMethod.POST)
public final ModelAndView eraseElementToList(HttpServletRequest request,    
HttpServletResponse response) throws Exception {

我只是在日志中获得了一个ActionDenied Exception,而且它没有将我重定向到登录页面。

更新1 04/25 19:43:27 DEBUG hannel.ChannelProcessingFilter - Request:FilterInvocation:URL:/pages/persistXMLfiletransfer.app; ConfigAttributes:[REQUIRES_SECURE_CHANNEL] 04/25 19:43:27 DEBUG .security.web.FilterChainProxy - /pages/persistXMLfiletransfer.app在第2位的12位附加滤镜链;触发过滤器:&#39; ConcurrentSessionFilter&#39; 04/25 19:43:27 DEBUG .security.web.FilterChainProxy - /pages/persistXMLfiletransfer.app在第3位(共12位)的附加过滤链中;触发过滤器:&#39; SecurityContextPersistenceFilter&#39; 04/25 19:43:27 DEBUG ssionSecurityContextRepository - HttpSession为SPRING_SECURITY_CONTEXT返回了null对象 04/25 19:43:27 DEBUG ssionSecurityContextRepository - 没有来自HttpSession的SecurityContext:org.apache.catalina.session.StandardSessionFacade@521f809b。将创建一个新的。 04/25 19:43:27 DEBUG .security.web.FilterChainProxy - /pages/persistXMLfiletransfer.app在第4位,共12个附加过滤链;触发过滤器:&#39; LogoutFilter&#39; 04/25 19:43:27 DEBUG .security.web.FilterChainProxy - /pages/persistXMLfiletransfer.app在第5位,共12个附加过滤链;触发过滤器:&#39; UsernamePasswordAuthenticationFilter&#39; 04/25 19:43:27 DEBUG .security.web.FilterChainProxy - /pages/persistXMLfiletransfer.app在第6位的12位在另外的过滤链中;触发过滤器:&#39; BasicAuthenticationFilter&#39; 04/25 19:43:27 DEBUG .security.web.FilterChainProxy - /pages/persistXMLfiletransfer.app在第7位(共12位)的附加过滤链中;触发过滤器:&#39; RequestCacheAwareFilter&#39; 04/25 19:43:27 DEBUG vedrequest.DefaultSavedRequest - pathInfo:都为null(属性等于) 04/25 19:43:27 DEBUG vedrequest.DefaultSavedRequest - queryString:都为null(属性等于) 04/25 19:43:27 DEBUG vedrequest.DefaultSavedRequest - requestURI:arg1 = / UppAudioFilesWebApp / pages / persistXMLfiletransfer.app; arg2 = / UppAudioFilesWebApp / pages / persistXMLfiletransfer.app(property equals) 04/25 19:43:27 DEBUG vedrequest.DefaultSavedRequest - serverPort:arg1 = 8443; arg2 = 8443(财产等于) 04/25 19:43:27 DEBUG vedrequest.DefaultSavedRequest - requestURL:arg1 = / UppAudioFilesWebApp / pages / persistXMLfiletransfer.app; arg2 = / UppAudioFilesWebApp / pages / persistXMLfiletransfer.app(property equals) 04/25 19:43:27 DEBUG vedrequest.DefaultSavedRequest - scheme:arg1 = https; arg2 = https(属性等于) 04/25 19:43:27 DEBUG vedrequest.DefaultSavedRequest - serverName:arg1 = localhst; arg2 = localhst(属性等于) 04/25 19:43:27 DEBUG vedrequest.DefaultSavedRequest - contextPath:arg1 = / UppAudioFilesWebApp; arg2 = / UppAudioFilesWebApp(property equals) 04/25 19:43:27 DEBUG vedrequest.DefaultSavedRequest - servletPath:arg1 = / pages / persistXMLfiletransfer.app; arg2 = / pages / persistXMLfiletransfer.app(property equals) 04/25 19:43:27 DEBUG equest.HttpSessionRequestCache - 从会话中删除DefaultSavedRequest(如果存在) 04/25 19:43:27 DEBUG .security.web.FilterChainProxy - /pages/persistXMLfiletransfer.app在第8位的12位附加过滤链;触发过滤器:&#39; SecurityContextHolderAwareRequestFilter&#39; 04/25 19:43:27 DEBUG .security.web.FilterChainProxy - /pages/persistXMLfiletransfer.app在第9位(共12位)的附加过滤链中;触发过滤器:&#39; AnonymousAuthenticationFilter&#39; 04/25 19:43:27 DEBUG .AnonymousAuthenticationFilter - 填充带有匿名令牌的SecurityContextHolder:&#39; org.springframework.security.authentication.AnonymousAuthenticationToken@9055c2bc:Principal:anonymousUser;证书:[保护];认证:真实;详细信息:org.springframework.security.web.authentication.WebAuthenticationDetails@b364:RemoteIpAddress:0:0:0:0:0:0:0:1; SessionId:63C5BB1C1CD8981AAF23D71C5521FB9B;授权机构:ROLE_ANONYMOUS&#39; 04/25 19:43:27 DEBUG .security.web.FilterChainProxy - /pages/persistXMLfiletransfer.app在第10位的12位附加过滤链;触发过滤器:&#39; SessionManagementFilter&#39; 04/25 19:43:27 DEBUG .security.web.FilterChainProxy - /pages/persistXMLfiletransfer.app在第11位的12位附加过滤器链;触发过滤器:&#39; ExceptionTranslationFilter&#39; 04/25 19:43:27 DEBUG .security.web.FilterChainProxy - /pages/persistXMLfiletransfer.app在12位12的附加过滤链中;触发过滤器:&#39; FilterSecurityInterceptor&#39; 04/25 19:43:27 DEBUG web.util.AntPathRequestMatcher - 检查请求匹配:&#39; /pages/persistxmlfiletransfer.app' ;;反对&#39; /expire.jsp' 04/25 19:43:27 DEBUG web.util.AntPathRequestMatcher - 检查请求匹配:&#39; /pages/persistxmlfiletransfer.app' ;;反对&#39; /accessdenied.jsp *&#39; 04/25 19:43:27 DEBUG web.util.AntPathRequestMatcher - 检查请求匹配:&#39; /pages/persistxmlfiletransfer.app' ;;反对&#39; / scripts / &#39; 04/25 19:43:27 DEBUG web.util.AntPathRequestMatcher - 检查请求匹配:&#39; /pages/persistxmlfiletransfer.app' ;;反对&#39; / styles / &#39; 04/25 19:43:27 DEBUG web.util.AntPathRequestMatcher - 检查请求匹配:&#39; /pages/persistxmlfiletransfer.app' ;;反对&#39; / images / *&#39; 04/25 19:43:27 DEBUG web.util.AntPathRequestMatcher - 检查请求匹配:&#39; /pages/persistxmlfiletransfer.app' ;;反对&#39; /login.jsp' 04/25 19:43:27 DEBUG web.util.AntPathRequestMatcher - 检查请求匹配:&#39; /pages/persistxmlfiletransfer.app' ;;反对&#39; / pages / **&#39; 04/25 19:43:27 DEBUG cept.FilterSecurityInterceptor - 安全对象:FilterInvocation:URL:/pages/persistXMLfiletransfer.app;属性:[hasAnyRole(&#39; ROLE_TOMCAT&#39;,&#39; ROLE_ADMNI&#39;)] 04/25 19:43:27 DEBUG cept.FilterSecurityInterceptor - 以前经过身份验证:org.springframework.security.authentication.AnonymousAuthenticationToken@9055c2bc:Principal:anonymousUser;证书:[保护];认证:真实;详细信息:org.springframework.security.web.authentication.WebAuthenticationDetails@b364:RemoteIpAddress:0:0:0:0:0:0:0:1; SessionId:63C5BB1C1CD8981AAF23D71C5521FB9B;授权机构:ROLE_ANONYMOUS 04/25 19:43:27 DEBUG y.access.vote.AffirmativeBased - 选民:org.springframework.security.web.access.expression.WebExpressionVoter@1304ff98,返回:-1 04/25 19:43:27 DEBUG ess.ExceptionTranslationFilter - 访问被拒绝(用户是匿名的);重定向到身份验证入口点 org.springframework.security.access.AccessDeniedException:访问被拒绝     在org.springframework.security.access.vote.AffirmativeBased.decide(AffirmativeBased.java:83)     在org.springframework.security.access.intercept.AbstractSecurityInterceptor.beforeInvocation(AbstractSecurityInterceptor.java:205)     在org.springframework.security.web.access.intercept.FilterSecurityInterceptor.invoke(FilterSecurityInterceptor.java:114)     在org.springframework.security.web.access.intercept.FilterSecurityInterceptor.doFilter(FilterSecurityInterceptor.java:83)     在org.springframework.security.web.FilterChainProxy $ VirtualFilterChain.doFilter(FilterChainProxy.java:323)     在org.springframework.security.web.access.ExceptionTranslationFilter.doFilter(ExceptionTranslationFilter.java:113)     在org.springframework.security.web.FilterChainProxy $ VirtualFilterChain.doFilter(FilterChainProxy.java:323)     在org.springframework.security.web.session.SessionManagementFilter.doFilter(SessionManagementFilter.java:101)     在org.springframework.security.web.FilterChainProxy $ VirtualFilterChain.doFilter(FilterChainProxy.java:323)     在org.springframework.security.web.authentication.AnonymousAuthenticationFilter.doFilter(AnonymousAuthenticationFilter.java:113)

1 个答案:

答案 0 :(得分:1)

这里最可能的解释是你有一个Spring ExceptionHandler,它会捕获AccessDeniedException并阻止Spring Security对其进行操作。如果您在某处使用安全注释,这是一个非常常见的问题(尽管您在问题中没有提到过这一点)。

同样应该从stacktrace中清楚地看到它没有被Spring Security处理的异常(总是发布堆栈跟踪)。另请更仔细地重新检查日志以区分这两种情况。如果您看到“重定向到身份验证入口点”,则表示Spring Security正在接收异常,您应该看到登录页面。如果使用异常处理程序,您将看不到。

如果这是问题所在,您可以使@ExceptionHandler注释更具体,以便它们不会捕获此异常,或者您可以创建特定的@ExceptionHandler(AccessDeniedException.class)注释并简单地重新抛出异常它