KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > roller > presentation > filters > CompressionFilter


1 package org.roller.presentation.filters;
2
3 import org.apache.commons.logging.Log;
4 import org.apache.commons.logging.LogFactory;
5
6 import java.io.ByteArrayOutputStream JavaDoc;
7 import java.io.IOException JavaDoc;
8 import java.util.zip.GZIPOutputStream JavaDoc;
9
10 import javax.servlet.Filter JavaDoc;
11 import javax.servlet.FilterChain JavaDoc;
12 import javax.servlet.FilterConfig JavaDoc;
13 import javax.servlet.ServletException JavaDoc;
14 import javax.servlet.ServletRequest JavaDoc;
15 import javax.servlet.ServletResponse JavaDoc;
16 import javax.servlet.http.HttpServletRequest JavaDoc;
17 import javax.servlet.http.HttpServletResponse JavaDoc;
18
19 /** Filter that compresses output with gzip
20  * (assuming that browser supports gzip).
21  * <P>
22  * Taken from More Servlets and JavaServer Pages
23  * from Prentice Hall and Sun Microsystems Press,
24  * http://www.moreservlets.com/.
25  * &copy; 2002 Marty Hall; may be freely used or adapted.
26  *
27  * @web.filter name="PageGzipFilter"
28  * *web.filter-mapping url-pattern="/page/*"
29  */

30
31 public class CompressionFilter implements Filter JavaDoc
32 {
33     private static Log mLogger =
34         LogFactory.getFactory().getInstance(CompressionFilter.class);
35         
36     /** If browser does not support gzip, invoke resource
37      * normally. If browser <I>does</I> support gzip,
38      * set the Content-Encoding response header and
39      * invoke resource with a wrapped response that
40      * collects all the output. Extract the output
41      * and write it into a gzipped byte array. Finally,
42      * write that array to the client's output stream.
43      */

44     public void doFilter(
45         ServletRequest JavaDoc request,
46         ServletResponse JavaDoc response,
47         FilterChain JavaDoc chain)
48         throws ServletException JavaDoc, IOException JavaDoc
49     {
50         HttpServletRequest JavaDoc req = (HttpServletRequest JavaDoc) request;
51         HttpServletResponse JavaDoc res = (HttpServletResponse JavaDoc) response;
52         if (!isGzipSupported(req))
53         {
54             // Invoke resource normally.
55
chain.doFilter(req, res);
56         }
57         else
58         {
59             // Tell browser we are sending it gzipped data.
60
res.setHeader("Content-Encoding", "gzip");
61
62             // Invoke resource, accumulating output in the wrapper.
63
ByteArrayResponseWrapper responseWrapper =
64                 new ByteArrayResponseWrapper(response);
65             
66             chain.doFilter(req, responseWrapper);
67
68             ByteArrayOutputStream JavaDoc outputStream = responseWrapper.getByteArrayOutputStream();
69
70             // Get character array representing output.
71
if (mLogger.isDebugEnabled())
72             {
73                 mLogger.debug("Pre-zip size:" + outputStream.size());
74             }
75             
76             // Make a writer that compresses data and puts
77
// it into a byte array.
78
ByteArrayOutputStream JavaDoc byteStream = new ByteArrayOutputStream JavaDoc();
79             GZIPOutputStream JavaDoc zipOut = new GZIPOutputStream JavaDoc(byteStream);
80
81             // Compress original output and put it into byte array.
82
zipOut.write(responseWrapper.getByteArrayOutputStream().toByteArray());
83
84             // Gzip streams must be explicitly closed.
85
zipOut.close();
86
87             if (mLogger.isDebugEnabled())
88             {
89                 mLogger.debug("Gzip size:" + byteStream.size());
90             }
91             
92             // Update the Content-Length header.
93
res.setContentLength(byteStream.size());
94
95             ByteArrayOutputStreamWrapper newOut =
96                 (ByteArrayOutputStreamWrapper) responseWrapper.getOutputStream();
97             newOut.clear();
98             newOut.setFinallized();
99         
100             /* now force close of OutputStream */
101             newOut.write(byteStream.toByteArray());
102             newOut.close();
103         }
104     }
105
106     /** Store the FilterConfig object in case subclasses
107      * want it.
108      */

109     public void init(FilterConfig JavaDoc config) throws ServletException JavaDoc
110     {
111     }
112
113     public void destroy()
114     {
115     }
116
117     private boolean isGzipSupported(HttpServletRequest JavaDoc req)
118     {
119         String JavaDoc browserEncodings = req.getHeader("Accept-Encoding");
120         return (
121             (browserEncodings != null)
122                 && (browserEncodings.indexOf("gzip") != -1));
123     }
124  
125 }
126
Popular Tags