1   /* Copyright 2004, 2005, 2006 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 junit.framework.TestCase;
19  import org.springframework.mock.web.MockFilterConfig;
20  import org.springframework.mock.web.MockHttpServletRequest;
21  import org.springframework.mock.web.MockHttpServletResponse;
22  import org.springframework.mock.web.MockHttpSession;
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 java.io.IOException;
31  import java.util.Date;
32  
33  
34  /**
35   * Tests {@link ConcurrentSessionFilter}.
36   *
37   * @author Ben Alex
38   * @version $Id: ConcurrentSessionFilterTests.java 1541 2006-06-11 01:20:29Z raykrueger $
39   */
40  public class ConcurrentSessionFilterTests extends TestCase {
41      //~ Constructors ===================================================================================================
42  
43      public ConcurrentSessionFilterTests() {
44          super();
45      }
46  
47      public ConcurrentSessionFilterTests(String arg0) {
48          super(arg0);
49      }
50  
51      //~ Methods ========================================================================================================
52  
53      private void executeFilterInContainerSimulator(FilterConfig filterConfig, Filter filter, ServletRequest request,
54          ServletResponse response, FilterChain filterChain)
55          throws ServletException, IOException {
56          filter.init(filterConfig);
57          filter.doFilter(request, response, filterChain);
58          filter.destroy();
59      }
60  
61      public static void main(String[] args) {
62          junit.textui.TestRunner.run(ConcurrentSessionFilterTests.class);
63      }
64  
65      public void testDetectsExpiredSessions() throws Exception {
66          // Setup our HTTP request
67          MockHttpServletRequest request = new MockHttpServletRequest();
68          MockHttpSession session = new MockHttpSession();
69          request.setSession(session);
70  
71          MockHttpServletResponse response = new MockHttpServletResponse();
72          MockFilterConfig config = new MockFilterConfig(null, null);
73  
74          // Setup our expectation that the filter chain will not be invoked, as we redirect to expiredUrl
75          MockFilterChain chain = new MockFilterChain(false);
76  
77          // Setup our test fixture and registry to want this session to be expired
78          ConcurrentSessionFilter filter = new ConcurrentSessionFilter();
79          SessionRegistry registry = new SessionRegistryImpl();
80          registry.registerNewSession(session.getId(), "principal");
81          registry.getSessionInformation(session.getId()).expireNow();
82          filter.setSessionRegistry(registry);
83          filter.setExpiredUrl("/expired.jsp");
84  
85          // Test
86          executeFilterInContainerSimulator(config, filter, request, response, chain);
87  
88          assertEquals("/expired.jsp", response.getRedirectedUrl());
89      }
90  
91      public void testDetectsMissingExpiredUrl() throws Exception {
92          ConcurrentSessionFilter filter = new ConcurrentSessionFilter();
93          filter.setSessionRegistry(new SessionRegistryImpl());
94  
95          try {
96              filter.afterPropertiesSet();
97              fail("Should have thrown IAE");
98          } catch (IllegalArgumentException expected) {
99              assertTrue(true);
100         }
101     }
102 
103     public void testDetectsMissingSessionRegistry() throws Exception {
104         ConcurrentSessionFilter filter = new ConcurrentSessionFilter();
105         filter.setExpiredUrl("xcx");
106 
107         try {
108             filter.afterPropertiesSet();
109             fail("Should have thrown IAE");
110         } catch (IllegalArgumentException expected) {
111             assertTrue(true);
112         }
113     }
114 
115     public void testUpdatesLastRequestTime() throws Exception {
116         // Setup our HTTP request
117         MockHttpServletRequest request = new MockHttpServletRequest();
118         MockHttpSession session = new MockHttpSession();
119         request.setSession(session);
120 
121         MockHttpServletResponse response = new MockHttpServletResponse();
122         MockFilterConfig config = new MockFilterConfig(null, null);
123 
124         // Setup our expectation that the filter chain will be invoked, as our session hasn't expired
125         MockFilterChain chain = new MockFilterChain(true);
126 
127         // Setup our test fixture
128         ConcurrentSessionFilter filter = new ConcurrentSessionFilter();
129         SessionRegistry registry = new SessionRegistryImpl();
130         registry.registerNewSession(session.getId(), "principal");
131 
132         Date lastRequest = registry.getSessionInformation(session.getId()).getLastRequest();
133         filter.setSessionRegistry(registry);
134         filter.setExpiredUrl("/expired.jsp");
135 
136         Thread.sleep(1000);
137 
138         // Test
139         executeFilterInContainerSimulator(config, filter, request, response, chain);
140 
141         assertTrue(registry.getSessionInformation(session.getId()).getLastRequest().after(lastRequest));
142     }
143 
144     //~ Inner Classes ==================================================================================================
145 
146     private class MockFilterChain implements FilterChain {
147         private boolean expectToProceed;
148 
149         public MockFilterChain(boolean expectToProceed) {
150             this.expectToProceed = expectToProceed;
151         }
152 
153         private MockFilterChain() {
154             super();
155         }
156 
157         public void doFilter(ServletRequest request, ServletResponse response)
158             throws IOException, ServletException {
159             if (expectToProceed) {
160                 assertTrue(true);
161             } else {
162                 fail("Did not expect filter chain to proceed");
163             }
164         }
165     }
166 }