CSRF与Spring Security集成时,会话超时导致Spring MVC中的访问被拒绝 [英] Session timeout leads to Access Denied in Spring MVC when CSRF integration with Spring Security

查看:304
本文介绍了CSRF与Spring Security集成时,会话超时导致Spring MVC中的访问被拒绝的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我在Spring MVC项目中已将CSRF令牌与Spring Security集成在一起.一切都可以与CSRF令牌一起正常使用,令牌将从客户端发送到服务器端.

I have Integrated CSRF token with Spring Security in my Spring MVC Project. Everything work properly with CSRF token, token will be send from client side to server side.

我已经更改了logout流程,使其成为发送CSRF令牌的POST方法,并且效果很好.

I have changed my logout process to make it POST method to send CSRF token and its works fine.

发生会话超时时,我遇到了问题,需要将其重定向到spring默认注销URL,但是在该URL上却为我提供Access Denied.

I have face problem when session timeout is occurred, it needs to be redirected to spring default logout URL but it gives me Access Denied on that URL.

如何覆盖此行为.

我在安全性配置文件中包含以下行

I have include below line in Security config file

   <http>
         //Other config parameters
        <csrf/>
   </http>

请让我知道是否有人需要更多信息.

Please let me know if anyone needs more information.

推荐答案

这个问题有点老了,但是答案总是有用的.

The question is a bit old, but answers are always useful.

首先,这是会话支持的CSRF令牌的已知问题,如docs中所述:

First, this is a known issue with session-backed CSRF tokens, as described in the docs: CSRF Caveats - Timeouts.

要解决此问题,请使用一些Javascript检测即将到来的超时,使用与会话无关的CSRF令牌存储库或创建自定义的AccessDeniedHandler路由.我选择了后者:

To solve it, use some Javascript to detect imminent timeouts, use a session-independent CSRF token repository or create a custom AccessDeniedHandler route. I chose the latter:

配置XML:

<http>
    <!-- ... -->
    <access-denied-handler ref="myAccessDeniedHandler"/>
</http>

<bean id="myAccessDeniedHandler" class="package.MyAccessDeniedHandler">
    <!-- <constructor-arg ref="myInvalidSessionStrategy" /> -->
</bean>

MyAccessDeniedHandler:

MyAccessDeniedHandler:

public class MyAccessDeniedHandler implements AccessDeniedHandler {
    /* ... */
    @Override
    public void handle(HttpServletRequest request, HttpServletResponse response, AccessDeniedException exception)
            throws IOException, ServletException {
        if (exception instanceof MissingCsrfTokenException) {
            /* Handle as a session timeout (redirect, etc).
            Even better if you inject the InvalidSessionStrategy
            used by your SessionManagementFilter, like this:
            invalidSessionStrategy.onInvalidSessionDetected(request, response);
            */
        } else {
            /* Redirect to a error page, send HTTP 403, etc. */
        }
    }
}

或者,您可以将自定义处理程序定义为DelegatingAccessDeniedHandler:

Alternatively, you can define the custom handler as a DelegatingAccessDeniedHandler:

<bean id="myAccessDeniedHandler" class="org.springframework.security.web.access.DelegatingAccessDeniedHandler">
    <constructor-arg name="handlers">
        <map>
            <entry key="org.springframework.security.web.csrf.MissingCsrfTokenException">
                <bean class="org.springframework.security.web.session.InvalidSessionAccessDeniedHandler">
                    <constructor-arg name="invalidSessionStrategy" ref="myInvalidSessionStrategy" />
                </bean>
            </entry>
        </map>
    </constructor-arg>
    <constructor-arg name="defaultHandler">
        <bean class="org.springframework.security.web.access.AccessDeniedHandlerImpl">
            <property name="errorPage" value="/my_error_page"/>
        </bean>
    </constructor-arg>
</bean>

这篇关于CSRF与Spring Security集成时,会话超时导致Spring MVC中的访问被拒绝的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆