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.intercept.web;
17  
18  import org.acegisecurity.intercept.AbstractSecurityInterceptor;
19  import org.acegisecurity.intercept.InterceptorStatusToken;
20  import org.acegisecurity.intercept.ObjectDefinitionSource;
21  
22  
23  /***
24   * Performs security handling of HTTP resources via a filter implementation.
25   * 
26   * <P>
27   * End users should <B>only</B> use this class to configure their HTTP security
28   * configuration in an application context. They should <B>not</B> attempt to
29   * invoke the <code>FilterSecurityInterceptor</code> except as a standard bean
30   * registration in an application context. At runtime, this class will provide
31   * services to web applications via the {@link SecurityEnforcementFilter}.
32   * </p>
33   * 
34   * <p>
35   * The <code>ObjectDefinitionSource</code> required by this security
36   * interceptor is of type {@link FilterInvocationDefinitionSource}.
37   * </p>
38   * 
39   * <P>
40   * Refer to {@link AbstractSecurityInterceptor} for details on the workflow.
41   * </p>
42   *
43   * @author Ben Alex
44   * @version $Id: FilterSecurityInterceptor.java,v 1.6 2005/11/17 00:55:50 benalex Exp $
45   */
46  public class FilterSecurityInterceptor extends AbstractSecurityInterceptor {
47      //~ Static fields/initializers =============================================
48  
49      private static final String FILTER_APPLIED = "__acegi_filterSecurityInterceptor_filterApplied";
50  
51      //~ Instance fields ========================================================
52  
53      private FilterInvocationDefinitionSource objectDefinitionSource;
54      private boolean observeOncePerRequest = true;
55  
56      //~ Methods ================================================================
57  
58      public void setObjectDefinitionSource(
59          FilterInvocationDefinitionSource newSource) {
60          this.objectDefinitionSource = newSource;
61      }
62  
63      public FilterInvocationDefinitionSource getObjectDefinitionSource() {
64          return this.objectDefinitionSource;
65      }
66  
67      public void setObserveOncePerRequest(boolean observeOncePerRequest) {
68          this.observeOncePerRequest = observeOncePerRequest;
69      }
70  
71      /***
72       * Indicates whether once-per-request handling will be observed. By default
73       * this is <code>true</code>, meaning the
74       * <code>FilterSecurityInterceptor</code> will only execute
75       * once-per-request. Sometimes users may wish it to execute more than once
76       * per request, such as when JSP forwards are being used and filter
77       * security is desired on each included fragment of the HTTP request.
78       *
79       * @return <code>true</code> (the default) if once-per-request is honoured,
80       *         otherwise <code>false</code> if
81       *         <code>FilterSecurityInterceptor</code> will enforce
82       *         authorizations for each and every fragment of the HTTP request.
83       */
84      public boolean isObserveOncePerRequest() {
85          return observeOncePerRequest;
86      }
87  
88      public Class getSecureObjectClass() {
89          return FilterInvocation.class;
90      }
91  
92      public void invoke(FilterInvocation fi) throws Throwable {
93          if ((fi.getRequest() != null)
94              && (fi.getRequest().getAttribute(FILTER_APPLIED) != null)
95              && observeOncePerRequest) {
96              // filter already applied to this request and user wants us to observce
97              // once-per-request handling, so don't re-do security checking
98              fi.getChain().doFilter(fi.getRequest(), fi.getResponse());
99          } else {
100             // first time this request being called, so perform security checking
101             if (fi.getRequest() != null) {
102                 fi.getRequest().setAttribute(FILTER_APPLIED, Boolean.TRUE);
103             }
104 
105             InterceptorStatusToken token = super.beforeInvocation(fi);
106 
107             try {
108                 fi.getChain().doFilter(fi.getRequest(), fi.getResponse());
109             } finally {
110                 super.afterInvocation(token, null);
111             }
112         }
113     }
114 
115     public ObjectDefinitionSource obtainObjectDefinitionSource() {
116         return this.objectDefinitionSource;
117     }
118 }