<%@ page session="false"%><%@ page errorPage="error.jsp"%><%@ page import="java.net.URL"%><%@ page import="java.net.URLConnection"%><%@ page import="java.net.MalformedURLException"%><%@ page import="java.io.ByteArrayOutputStream"%><%@ page import="java.io.BufferedInputStream"%><%@ page import="java.io.BufferedReader"%><%@ page import="java.io.InputStream"%><%@ page import="java.io.PipedInputStream"%><%@ page import="java.io.PipedOutputStream"%><%@ page import="java.io.Reader"%><%@ page import="java.util.zip.GZIPOutputStream "%><%@ page import="java.io.IOException"%><%! // ~~~~ // Design Note: // Use redirects to prevent proxy caches to mix up // responses for various clients. // ~~~~ // ~~~~~~~~~~~~~ public class JavascriptResource extends Object { private String mURL; private String mContentType = "text/html"; private long mLastModified; private long mExpires; private String mGzipString; private byte[] mCharArray; // list of browsers that are supported, sort with most // common on top: private final String[] mAcceptedAgents = { "Mozilla/4.0 (compatible; MSIE 5.5;", "Mozilla/4.0 (compatible; MSIE 5.01;", "Mozilla/5.0", }; public JavascriptResource(String url) throws MalformedURLException, IOException { if (url == null) throw new IllegalArgumentException("JavascriptResource(): no URL"); mURL = url; initResource(); } /** * Returns true if the User-Agent header from the request * is found in the mAcceptedAgents array. * Uses String.indexOf to match against mAcceptedAgents. */ private boolean acceptGzip(HttpServletRequest request) { if (request == null) { throw new IllegalArgumentException("acceptGzip: no request"); } final String agent = request.getHeader("User-Agent"); if (agent == null) { return false; } for (int i = 0; i < mAcceptedAgents.length; i++) { if (agent.indexOf(mAcceptedAgents[i]) >= 0) { return true; } } return false; } /** * Retrieve the contents of the file at mURL and * compress it. */ private void initResource() throws MalformedURLException, IOException { final URL httpresource = new URL(mURL); final URLConnection conn = httpresource.openConnection(); mContentType = conn.getContentType(); mLastModified = conn.getLastModified(); mExpires = conn.getExpiration(); final Object obj = conn.getContent(); if (!(obj instanceof InputStream)) { throw new RuntimeException( "initResource(): Not a valid resource, of type " + obj.getClass().getName()); } mCharArray = new byte[conn.getContentLength()]; BufferedInputStream in = new BufferedInputStream((InputStream)obj); int c; for (int i = 0;(c = in.read()) != -1; i++) { mCharArray[i] = (byte)c; } mGzipString = compress(mCharArray); } // Gzip compress the given array and return the // compressed String. // This seems to work best with JspWriter... private String compress(byte[] chararray) throws IOException { ByteArrayOutputStream os = new ByteArrayOutputStream(); GZIPOutputStream gzos = new GZIPOutputStream(os); gzos.write(chararray, 0, chararray.length); gzos.close(); os.close(); return os.toString(); } /** * Send the response to the client and close * the JspWriter connection stream. */ public void write( JspWriter out, HttpServletRequest request, HttpServletResponse response) throws IOException { if (!acceptGzip(request)) { response.sendRedirect(response.encodeURL(mURL)); } response.setStatus(200); response.setContentType(mContentType); response.addHeader("Content-Encoding", "gzip"); if (mLastModified > 0l) { response.addDateHeader("Last-Modified", mLastModified); } if (mExpires > 0l) { response.addDateHeader("Expires", mExpires); } out.write(mGzipString); out.close(); } } // ~~~~~~ end JavascriptResource class ~~~~~~ %><% // Get resource with the r argument: JavascriptResource h = new JavascriptResource(request.getParameter("r")); // Return the resource, gzipped if possible h.write(out, request, response); %>