View Javadoc

1   /* Copyright 2004, 2005 Acegi Technology Pty Limited
2    *
3    * Licensed under the Apache License, Version 2.0 (the "License");
4    * you may not use this file except in compliance with the License.
5    * You may obtain a copy of the License at
6    *
7    *     http://www.apache.org/licenses/LICENSE-2.0
8    *
9    * Unless required by applicable law or agreed to in writing, software
10   * distributed under the License is distributed on an "AS IS" BASIS,
11   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12   * See the License for the specific language governing permissions and
13   * limitations under the License.
14   */
15  
16  package org.acegisecurity.concurrent;
17  
18  import org.springframework.beans.factory.InitializingBean;
19  
20  import org.springframework.util.Assert;
21  
22  import java.io.IOException;
23  
24  import javax.servlet.Filter;
25  import javax.servlet.FilterChain;
26  import javax.servlet.FilterConfig;
27  import javax.servlet.ServletException;
28  import javax.servlet.ServletRequest;
29  import javax.servlet.ServletResponse;
30  import javax.servlet.http.HttpServletRequest;
31  import javax.servlet.http.HttpServletResponse;
32  import javax.servlet.http.HttpSession;
33  
34  
35  /***
36   * Filter required by concurrent session handling package.
37   * 
38   * <p>
39   * This filter performs two functions. First, it calls {@link
40   * org.acegisecurity.concurrent.SessionRegistry#refreshLastRequest(String)}
41   * for each request. That way, registered sessions always have a correct "last
42   * update" date/time. Second, it retrieves {@link
43   * org.acegisecurity.concurrent.SessionInformation} from the
44   * <code>SessionRegistry</code> for each request and checks if the session has
45   * been marked as expired. If it has been marked as expired, the session is
46   * invalidated. The invalidation of the session will also cause the request to
47   * redirect to the URL specified, and a {@link
48   * org.acegisecurity.ui.session.HttpSessionDestroyedEvent} to be published
49   * via the {@link org.acegisecurity.ui.session.HttpSessionEventPublisher}
50   * registered in <code>web.xml</code>.
51   * </p>
52   *
53   * @author Ben Alex
54   * @version $Id: ConcurrentSessionFilter.java,v 1.2 2005/11/17 00:55:56 benalex Exp $
55   */
56  public class ConcurrentSessionFilter implements Filter,
57      InitializingBean {
58      //~ Instance fields ========================================================
59  
60      private SessionRegistry sessionRegistry;
61      private String expiredUrl;
62  
63      //~ Methods ================================================================
64  
65      public void setExpiredUrl(String expiredUrl) {
66          this.expiredUrl = expiredUrl;
67      }
68  
69      public void setSessionRegistry(SessionRegistry sessionRegistry) {
70          this.sessionRegistry = sessionRegistry;
71      }
72  
73      public void afterPropertiesSet() throws Exception {
74          Assert.notNull(sessionRegistry, "SessionRegistry required");
75          Assert.hasText(expiredUrl, "ExpiredUrl required");
76      }
77  
78      /***
79       * Does nothing. We use IoC container lifecycle services instead.
80       */
81      public void destroy() {}
82  
83      public void doFilter(ServletRequest request, ServletResponse response,
84          FilterChain chain) throws IOException, ServletException {
85          Assert.isInstanceOf(HttpServletRequest.class, request,
86              "Can only process HttpServletRequest");
87          Assert.isInstanceOf(HttpServletResponse.class, response,
88              "Can only process HttpServletResponse");
89  
90          HttpServletRequest httpRequest = (HttpServletRequest) request;
91          HttpServletResponse httpResponse = (HttpServletResponse) response;
92  
93          HttpSession session = httpRequest.getSession(false);
94  
95          if (session != null) {
96              SessionInformation info = sessionRegistry.getSessionInformation(session
97                      .getId());
98  
99              if (info != null) {
100                 if (info.isExpired()) {
101                     // Expired - abort processing
102                     session.invalidate();
103 
104                     String targetUrl = httpRequest.getContextPath()
105                         + expiredUrl;
106                     httpResponse.sendRedirect(httpResponse.encodeRedirectURL(
107                             targetUrl));
108 
109                     return;
110                 } else {
111                     // Non-expired - update last request date/time
112                     info.refreshLastRequest();
113                 }
114             }
115         }
116 
117         chain.doFilter(request, response);
118     }
119 
120     /***
121      * Does nothing. We use IoC container lifecycle services instead.
122      *
123      * @param arg0 ignored
124      *
125      * @throws ServletException ignored
126      */
127     public void init(FilterConfig arg0) throws ServletException {}
128 }