1
votes

I want to redirect users to the login page when a session timeout occurs. This works out-of-the-box with spring security, but only on non-ajax calls.

On an ajax-call you have to react on the session timeout by yourself. Therefore I have created my own filter(filter implemented like in this question) who checks if a session is timed out. The filter is registered via custom-filter tag in spring security config.

<http use-expressions="true">
    <custom-filter ref="customTimeoutHandler" after="LAST"/>
</http>

The problem is, that the session timeout is not recognized by the filter. If I check for request.isRequestedSessionIdValid() it returns true even if the session is timed out. When I enter a new secured URL manually, the standard spring security filter recognizes the timeout correctly and does a redirect to the login page.

What could be wrong here? How recognizes spring security the session timeout?

UPDATE

It seems, that the session management filter of spring security replaces the timed-out session with a new anonymous one. Therefore everytime I check for session timeout it returns true, because the new anonymous session is, of course, not timed-out.

3

3 Answers

2
votes

You can check the SecurityContext.
Grab the Authentication object and check the authorities looking for an ANONYMOUS one. Something like:

SecurityContext sc = SecurityContextHolder.getContext();
Authentication a = sc.getAuthentication();
if(!a.isAuthenticated() || a.getAuthorities().contains(new GrantedAuthorityImpl("ROLE_ANONYMOUS"))) {
    //user not authenticated or ANONYMOUS
} else {
    //user authenticated
}
0
votes

This solution works like a charm for me.

The basic concept is to point to a servlet instead of the login page. The servlet then determines if the request was a ajax request and if that is true, it returns the redirect to the login page as xml fragment. The browser can interpret that fragment and redirects to the login page.

0
votes

I am developing enterprise application including gwt/gwtp and spring security . I add some issue with session time out , casue the SimpleRedirectInvalidSessionStrategy which used by default is executing response.sendRedirect() , the html page response I wanted to redirect is swallow by gwt com.google.gwt.user.client.rpc.InvocationException as the exception message . and no actully redirect is taking place .

for solving this

1 . I define my cosutom session-manamgemt-filter for doing this you need in your spring-security.xml configuration file set <session-management session-fixation-protection="none"/> by this spring secuirty will not take it default session managment filter .

  1. define your session managment filter

    enter code here

{

 <custom-filter position="SESSION_MANAGEMENT_FILTER" ref="mySessionManagmentFilter"/>   


<beans:bean id="mySessionManagmentFilter"
                    class="org.springframework.security.web.session.SessionManagementFilter">

            <beans:constructor-arg index="0" ref="mySessionSecurityContextRepository"/>
            <beans:constructor-arg index="1" ref="mySessionAutenticationStrategy"/>

            <beans:property name="invalidSessionStrategy">
                <beans:ref local="myInvalidSessionStrategy"/>
          </beans:property>
        </beans:bean>


     <beans:bean id="mySessionSecurityContextRepository"
                    class='org.springframework.security.web.context.HttpSessionSecurityContextRepository'>
            <beans:property name='allowSessionCreation' value='false'/>
        </beans:bean>


<beans:bean id="mySessionAutenticationStrategy"
                class="org.springframework.security.web.authentication.session.ConcurrentSessionControlStrategy">
        <beans:constructor-arg name="sessionRegistry" ref="sessionRegistry"/>
        <beans:property name="maximumSessions" value="1"/>
        <beans:property name="exceptionIfMaximumExceeded" value="false"/>
        <beans:property name="alwaysCreateSession" value="true"/>
    </beans:bean>


<beans:bean id="myInvalidSessionStrategy"
                class="com.my.project.MyInvalidSessionStrategy">
        <beans:constructor-arg value="/login.jsp?timeout=1"/>
    </beans:bean>

}

here custom - MyInvalidSessionStrategy {

public class MyInvalidSessionStrategy implements InvalidSessionStrategy {

private final Logger logger = LoggerFactory.getLogger(getClass());
private final String destinationUrl;


public OperationalInvalidSessionStrategy(String invalidSessionUrl) {
    this.destinationUrl = invalidSessionUrl;

}

@Override
public void onInvalidSessionDetected(HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException {
    String exMsg =session timeout ! , need to redirect to login page
    logger.warn(exMsg);
    throw new TimeOutException(exMsg);

}

}

}

so when time out taking place the new implementation is throwing an exception .. the exception can be truck on gwt callback onFailure method

check the type of the exception and on onFailure method redirect the user to login page . with Window.Location.replace(GWT.getHostPageBaseURL() + "/login.jsp")