View Javadoc

1   /**
2    *  Copyright 2003-2007 Greg Luck
3    *
4    *  Licensed under the Apache License, Version 2.0 (the "License");
5    *  you may not use this file except in compliance with the License.
6    *  You may obtain a copy of the License at
7    *
8    *      http://www.apache.org/licenses/LICENSE-2.0
9    *
10   *  Unless required by applicable law or agreed to in writing, software
11   *  distributed under the License is distributed on an "AS IS" BASIS,
12   *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13   *  See the License for the specific language governing permissions and
14   *  limitations under the License.
15   */
16  
17  package net.sf.ehcache.constructs.web.filter;
18  
19  import net.sf.ehcache.CacheManager;
20  
21  import javax.servlet.http.HttpServletRequest;
22  
23  /**
24   * A simple page {@link CachingFilter} suitable for most uses.
25   * <p/>
26   * It uses a Singleton CacheManager created with the default factory method. Override to use a different CacheManager
27   * <p/>
28   * The meaning of <i>page</i> is:
29   * <ul>
30   * <li>A complete response i.e. not a fragment.
31   * <li>A content type suitable for gzipping. e.g. text or text/html
32   * </ul>
33   * For jsp:included page fragments see {@link SimplePageFragmentCachingFilter}.
34   * <h3>Keys</h3>
35   * Pages are cached based on their key. The key for this cache is the URI followed by the query string. An example
36   * is <code>/admin/SomePage.jsp?id=1234&name=Beagle</code>.
37   * <p/>
38   * This key technique is suitable for a wide range of uses. It is independent of hostname and port number, so will
39   * work well in situations where there are multiple domains which get the same content, or where users access
40   * based on different port numbers.
41   * <p/>
42   * A problem can occur with tracking software, where unique ids are inserted into request query strings. Because
43   * each request generates a unique key, there will never be a cache hit. For these situations it is better to
44   * parse the request parameters and override {@link #calculateKey(javax.servlet.http.HttpServletRequest)} with
45   * an implementation that takes account of only the significant ones.
46   * <h3>Configuring Caching with ehcache</h3>
47   * A cache entry in ehcache.xml should be configured with the name {@link #NAME}.
48   * <p/>
49   * Cache attributes including expiry are configured per cache name. To specify a different behaviour simply
50   * subclass, specify a new name and create a separate cache entry for it.
51   * <h3>Gzipping</h3>
52   * Significant network efficiencies can be gained by gzipping responses.
53   * <p/>
54   * Whether a response can be gzipped depends on:
55   * <ul>
56   * <li>Whether the user agent can accept GZIP encoding. This feature is part of HTTP1.1.
57   * If a browser accepts GZIP encoding it will advertise this by including in its HTTP header:
58   * All common browsers except IE 5.2 on Macintosh are capable of accepting gzip encoding. Most search engine
59   * robots do not accept gzip encoding.
60   * <li>Whether the user agent has advertised its acceptance of gzip encoding. This is on a per request basis. If they
61   * will accept a gzip response to their request they must include the following in the HTTP request header:
62   * <code>
63   * Accept-Encoding: gzip
64   * </code>
65   * </ul>
66   * Responses are automatically gzipped and stored that way in the cache. For requests which do not accept gzip
67   * encoding the page is retrieved from the cache, ungzipped and returned to the user agent. The ungzipping is
68   * high performance.
69   * @author Greg Luck
70   * @version $Id: SimplePageCachingFilter.java 512 2007-07-10 09:18:45Z gregluck $
71   */
72  public class SimplePageCachingFilter extends CachingFilter {
73  
74      /**
75       * The name of the filter. This should match a cache name in ehcache.xml
76       */
77      public static final String NAME = "SimplePageCachingFilter";
78  
79      /**
80       * A meaningful name representative of the JSP page being cached.
81       * <p/>
82       * The name must match the name of a configured cache in ehcache.xml
83       *
84       * @return the name of the cache to use for this filter.
85       */
86      protected String getCacheName() {
87          return NAME;
88      }
89  
90      /**
91       * Gets the CacheManager for this CachingFilter. It is therefore up to subclasses what CacheManager to use.
92       * <p/>
93       * This method was introduced in ehcache 1.2.1. Older versions used a singleton CacheManager instance created with
94       * the default factory method.
95       *
96       * @return the CacheManager to be used
97       * @since 1.2.1
98       */
99      protected CacheManager getCacheManager() {
100         return CacheManager.getInstance();
101     }
102 
103 
104     /**
105      * Pages are cached based on their key. The key for this cache is the URI followed by the query string. An example
106      * is <code>/admin/SomePage.jsp?id=1234&name=Beagle</code>.
107      * <p/>
108      * This key technique is suitable for a wide range of uses. It is independent of hostname and port number, so will
109      * work well in situations where there are multiple domains which get the same content, or where users access
110      * based on different port numbers.
111      * <p/>
112      * A problem can occur with tracking software, where unique ids are inserted into request query strings. Because
113      * each request generates a unique key, there will never be a cache hit. For these situations it is better to
114      * parse the request parameters and override {@link #calculateKey(javax.servlet.http.HttpServletRequest)} with
115      * an implementation that takes account of only the significant ones.
116      * <p/>
117      * The key should be unique
118      *
119      * @param httpRequest
120      * @return the key, generally the URI plus request parameters
121      */
122     protected String calculateKey(HttpServletRequest httpRequest) {
123         StringBuffer stringBuffer = new StringBuffer();
124         stringBuffer.append(httpRequest.getRequestURI()).append(httpRequest.getQueryString());
125         String key = stringBuffer.toString();
126         return key;
127     }
128 
129 }