Getting 403 with CSRF token in spring security

最后都变了- 提交于 2019-12-10 18:06:51

问题


I am encountering an issue with multiple tabs. If i logout from first tab and open another tab and after logging in and logging out if i go back to first tab and login i get 403. For example, the logout page of first tab had following added to the form by spring security and thymeleaf:

<input type="hidden" name="_csrf" value="7b9639ba-aaae-4ed2-aad2-bb4c5930458e">

where as the login form of second tab added a different csrf token.

<input type="hidden" name="_csrf" value="659324d5-ec5c-4c57-9984-dab740746285">

Now when i go to first tab and login from there i get 403 forbidden. Which makes sense since csrf token is now stale. But how do i get around this? I am also getting 403 forbidden if the user was logged out from inactivity and redirected to login page but tried logging in again only after a while, say half an hour.


回答1:


As of Spring Security 3.2, we have the CsrfTokenRepository interface, which allows you to store the synchronizer token however you see fit, such as in a database. This gives you the option to expire those tokens however you want in order to avoid stale tokens in your use case.

If you want to provide a nicer error message when something does go awry, you can supply a custom AccessDeniedHandler implementation that manages the MissingCsrfTokenException and InvalidCsrfTokenException exceptions in order to produce a more informative message.

UPDATE:

I have an interceptor that handles all my uncaught exceptions, so I just built a little AccessDeniedHandler that rethrows the CSRF-related exceptions:

public class CustomAccessDeniedHandler extends AccessDeniedHandlerImpl {
    @Override
    public void handle(HttpServletRequest request, HttpServletResponse response, AccessDeniedException accessDeniedException) throws IOException, ServletException {
        if(accessDeniedException instanceof MissingCsrfTokenException
                || accessDeniedException instanceof InvalidCsrfTokenException) {
            throw new ServletException(accessDeniedException);
        }
        super.handle(request, response, accessDeniedException);
    }
}



回答2:


The simplest approach to handling access denied errors I've used has been setting the access denied handler within your security config to redirect to your login page.

<http ...>
    <access-denied-handler error-page="/login.html" />
...


来源:https://stackoverflow.com/questions/22517107/getting-403-with-csrf-token-in-spring-security

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!