spring security logout导致NullPointerException

ani*_*van 8 java spring spring-security

我一直试图了解弹簧安全性已经有一段时间了,除了logout方面之外,我已经解决了大部分问题.通过关于SO的其他问题,我觉得他们中的大多数都面临与会话无关的问题.

另一方面,我面临着各种各样的麻烦.我的安全XML文件配置如下:

<http path-type="ant" auto-config="false" use-expressions="true"
    access-denied-page="/?login_error=2">
    <intercept-url pattern="/web/open/**" access="permitAll" />
    <intercept-url pattern="/web/**" access="isAuthenticated()" />

    <form-login login-processing-url="/static/j_spring_security_check"
        default-target-url="/web/base/view" always-use-default-target="true"
        login-page="/" authentication-failure-url="/?login_error=1" />

    <logout logout-url="/static/j_spring_security_logout"
        invalidate-session="true" logout-success-url="/" />
</http>
Run Code Online (Sandbox Code Playgroud)

在我web.xml已经映射login controller到上下文根[使用welcome-file列表],并且还具有所需的springSecurityFilterChain设置.现在登录操作运行完美.目标JSP有一个注销链接:

<a href="<c:url value="/static/j_spring_security_logout"/>">Logout</a>
Run Code Online (Sandbox Code Playgroud)

但是,每当我点击退出链接时,我都会感到非常可怕NullPointerException.如果我在这里犯了一些明显的错误,有人能告诉我吗?


异常堆栈:

java.lang.NullPointerException
    at java.util.Hashtable.get(Hashtable.java:334)
    at org.apache.tomcat.util.http.Parameters.getParameterValues(Parameters.java:116)
    at org.apache.tomcat.util.http.Parameters.getParameter(Parameters.java:127)
    at org.apache.catalina.connector.Request.getParameter(Request.java:1133)
    at org.apache.catalina.connector.RequestFacade.getParameter(RequestFacade.java:384)
    at javax.servlet.ServletRequestWrapper.getParameter(ServletRequestWrapper.java:140)
    at org.springframework.security.web.authentication.AbstractAuthenticationTargetUrlRequestHandler.determineTargetUrl(AbstractAuthenticationTargetUrlRequestHandler.java:86)
    at org.springframework.security.web.authentication.AbstractAuthenticationTargetUrlRequestHandler.handle(AbstractAuthenticationTargetUrlRequestHandler.java:67)
    at org.springframework.security.web.authentication.logout.SimpleUrlLogoutSuccessHandler.onLogoutSuccess(SimpleUrlLogoutSuccessHandler.java:28)
    at org.springframework.security.web.authentication.logout.LogoutFilter.doFilter(LogoutFilter.java:100)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:381)
    at org.springframework.security.web.context.SecurityContextPersistenceFilter.doFilter(SecurityContextPersistenceFilter.java:79)
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:381)
    at org.springframework.security.web.FilterChainProxy.doFilter(FilterChainProxy.java:168)
    at org.springframework.web.filter.DelegatingFilterProxy.invokeDelegate(DelegatingFilterProxy.java:237)
Run Code Online (Sandbox Code Playgroud)

感谢您抽出宝贵的时间.

jeh*_*eha 12

获取请求参数时,该determineTargetUrl方法AbstractAuthenticationTargetUrlRequestHandler似乎失败了.对我来说,通常可以提供一个defaultTargetUrl并设置alwaysUseDefaultTargetUrl为始终返回给定URL的truemeens determineTargetUrl并防止URL确定魔法.

我通过注册我自己的LogoutSuccessHandler实现来做到这一点,如:

<logout
    logout-url="/static/j_spring_security_logout"
    invalidate-session="true"
    success-handler-ref="myLogoutSuccessHandler" />
Run Code Online (Sandbox Code Playgroud)

而不是logout-success-url.

A LogoutSuccessHandler看起来很简单:

public class MyLogoutSuccessHandler extends AbstractAuthenticationTargetUrlRequestHandler implements LogoutSuccessHandler {

    @Override
    public void onLogoutSuccess(HttpServletRequest request, HttpServletResponse response, Authentication authentication throws IOException, ServletException {
        // maybe do some other things ...
        super.handle(request, response, authentication);
    }
}
Run Code Online (Sandbox Code Playgroud)

defaultTargetUrl在为自定义定义bean时,在安全上下文中设置注销URL LogoutSuccessHandler:

<bean id="myLogoutSuccessHandler" class="foobar.impl.MyLogoutSuccessHandler">
    <property name="defaultTargetUrl" value="/" />
    <property name="alwaysUseDefaultTargetUrl" value="true" />
</bean>
Run Code Online (Sandbox Code Playgroud)

  • @anirvan:在当前版本中似乎是一个**bug**,请参阅https://jira.springsource.org/browse/SEC-1803,https://jira.springsource.org/browse/SEC-1807 (3认同)
  • @Ischin:实际上你根本不需要你自己的实现.`<bean id ="myLogoutSuccessHandler"class ="org.springframework.security.web.authentication.logout.SimpleUrlLogoutSuccessHandler"> ... </ bean>`就够了 - 但也许你想做其他的事情. (2认同)