~ubuntu-branches/ubuntu/gutsy/oscache/gutsy

« back to all changes in this revision

Viewing changes to src/core/java/com/opensymphony/oscache/web/filter/CacheFilter.java

  • Committer: Bazaar Package Importer
  • Author(s): Kalle Kivimaa
  • Date: 2004-08-13 14:00:00 UTC
  • Revision ID: james.westby@ubuntu.com-20040813140000-lyugvinublk1x8y2
Tags: upstream-2.0.2
ImportĀ upstreamĀ versionĀ 2.0.2

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/*
 
2
 * Copyright (c) 2002-2003 by OpenSymphony
 
3
 * All rights reserved.
 
4
 */
 
5
package com.opensymphony.oscache.web.filter;
 
6
 
 
7
import com.opensymphony.oscache.base.Cache;
 
8
import com.opensymphony.oscache.base.NeedsRefreshException;
 
9
import com.opensymphony.oscache.web.ServletCacheAdministrator;
 
10
 
 
11
import org.apache.commons.logging.Log;
 
12
import org.apache.commons.logging.LogFactory;
 
13
 
 
14
import java.io.IOException;
 
15
 
 
16
import javax.servlet.*;
 
17
import javax.servlet.http.HttpServletRequest;
 
18
import javax.servlet.http.HttpServletResponse;
 
19
import javax.servlet.jsp.PageContext;
 
20
 
 
21
/**
 
22
 * CacheFilter is a filter that allows for server-side caching of post-processed servlet content.<p>
 
23
 *
 
24
 * It also gives great programatic control over refreshing, flushing and updating the cache.<p>
 
25
 *
 
26
 * @author <a href="mailto:sergek@lokitech.com">Serge Knystautas</a>
 
27
 * @author <a href="mailto:mike@atlassian.com">Mike Cannon-Brookes</a>
 
28
 * @version $Revision: 1.2 $
 
29
 */
 
30
public class CacheFilter implements Filter {
 
31
    private final Log log = LogFactory.getLog(this.getClass());
 
32
 
 
33
    // filter variables
 
34
    private FilterConfig config;
 
35
    private ServletCacheAdministrator admin = null;
 
36
    private int cacheScope = PageContext.APPLICATION_SCOPE; // filter scope - default is APPLICATION
 
37
    private int time = 60 * 60; // time before cache should be refreshed - default one hour (in seconds)
 
38
 
 
39
    /**
 
40
     * Filter clean-up
 
41
     */
 
42
    public void destroy() {
 
43
        //Not much to do...
 
44
    }
 
45
 
 
46
    /**
 
47
     * The doFilter call caches the response by wrapping the <code>HttpServletResponse</code>
 
48
     * object so that the output stream can be caught. This works by splitting off the output
 
49
     * stream into two with the {@link SplitServletOutputStream} class. One stream gets written
 
50
     * out to the response as normal, the other is fed into a byte array inside a {@link ResponseContent}
 
51
     * object.
 
52
     *
 
53
     * @param request The servlet request
 
54
     * @param response The servlet response
 
55
     * @param chain The filter chain
 
56
     * @throws ServletException IOException
 
57
     */
 
58
    public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws ServletException, IOException {
 
59
        log.info("<cache>: filter in scope " + cacheScope);
 
60
 
 
61
        HttpServletRequest httpRequest = (HttpServletRequest) request;
 
62
        String key = admin.generateEntryKey(null, httpRequest, cacheScope);
 
63
        Cache cache = admin.getCache(httpRequest, cacheScope);
 
64
 
 
65
        try {
 
66
            ResponseContent respContent = (ResponseContent) cache.getFromCache(key, time);
 
67
            log.info("<cache>: Using cached entry for " + key);
 
68
            respContent.writeTo(response);
 
69
        } catch (NeedsRefreshException nre) {
 
70
            boolean updateSucceeded = false;
 
71
 
 
72
            try {
 
73
                log.info("<cache>: New cache entry, cache stale or cache scope flushed for " + key);
 
74
 
 
75
                CacheHttpServletResponseWrapper cacheResponse = new CacheHttpServletResponseWrapper((HttpServletResponse) response);
 
76
                chain.doFilter(request, cacheResponse);
 
77
                cacheResponse.flushBuffer();
 
78
 
 
79
                // Only cache if the response was 200
 
80
                if (cacheResponse.getStatus() == HttpServletResponse.SC_OK) {
 
81
                    //Store as the cache content the result of the response
 
82
                    cache.putInCache(key, cacheResponse.getContent());
 
83
                    updateSucceeded = true;
 
84
                }
 
85
            } finally {
 
86
                if (!updateSucceeded) {
 
87
                    cache.cancelUpdate(key);
 
88
                }
 
89
            }
 
90
        }
 
91
    }
 
92
 
 
93
    /**
 
94
     * Initialize the filter. This retrieves a {@link ServletCacheAdministrator}
 
95
     * instance and configures the filter based on any initialization parameters.<p>
 
96
     * The supported initialization parameters are:
 
97
     * <ul>
 
98
     * <li><b>time</b> - the default time (in seconds) to cache content for. The default
 
99
     * value is 3600 seconds (one hour).</li>
 
100
     * <li><b>scope</b> - the default scope to cache content in. Acceptable values
 
101
     * are <code>application</code> (default), <code>session</code>, <code>request</code> and
 
102
     * <code>page</code>.
 
103
     *
 
104
     * @param filterConfig The filter configuration
 
105
     */
 
106
    public void init(FilterConfig filterConfig) {
 
107
        //Get whatever settings we want...
 
108
        config = filterConfig;
 
109
        admin = ServletCacheAdministrator.getInstance(config.getServletContext());
 
110
 
 
111
        //Will work this out later
 
112
        try {
 
113
            time = Integer.parseInt(config.getInitParameter("time"));
 
114
        } catch (Exception e) {
 
115
            log.info("Could not get init paramter 'time', defaulting to one hour.");
 
116
        }
 
117
 
 
118
        try {
 
119
            String scopeString = config.getInitParameter("scope");
 
120
 
 
121
            if (scopeString.equals("session")) {
 
122
                cacheScope = PageContext.SESSION_SCOPE;
 
123
            } else if (scopeString.equals("application")) {
 
124
                cacheScope = PageContext.APPLICATION_SCOPE;
 
125
            } else if (scopeString.equals("request")) {
 
126
                cacheScope = PageContext.REQUEST_SCOPE;
 
127
            } else if (scopeString.equals("page")) {
 
128
                cacheScope = PageContext.PAGE_SCOPE;
 
129
            }
 
130
        } catch (Exception e) {
 
131
            log.info("Could not get init paramter 'scope', defaulting to 'application'");
 
132
        }
 
133
    }
 
134
}