Loading CSS from a JAR file evaluating EL

Yesterday I briefly explained how I was loading CSS files from a JAR and forcing their content through Velocity to evaluate expressions.  A co-worker offered up a more simple solution, it’s after the break.


Carlos really comments his code well so this shouldn’t be too hard to follow.

package com.blakgeek.dynamicss.servlet;

import javax.el.ELContext;
import javax.el.ExpressionFactory;
import javax.el.ValueExpression;
import javax.servlet.ServletConfig;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.jsp.JspFactory;
import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;

/**
 * User: chenry
 * Date: 6/20/11
 * Time: 12:02 PM
 */
public class CssServlet extends HttpServlet {

    private JspFactory jspFactory = JspFactory.getDefaultFactory();
    private ExpressionFactory expressionFactory;
    private List paths = new ArrayList();

    @Override
    public void init(ServletConfig config) throws ServletException {

        super.init(config);
        expressionFactory = jspFactory.getJspApplicationContext(getServletContext()).getExpressionFactory();

        // get the list paths to try from init params
        String pathsStr = config.getInitParameter("paths");
        if (pathsStr != null) {
            String[] paths = pathsStr.trim().split(",");
            for (String path : paths) {
                this.paths.add(path.trim());
            }
        }
    }

    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {

        InputStream cssInputStream = null;

        // set the proper content type so it will work even if its chunked
        resp.setContentType("text/css");

        // get the filename from url path
        String cssFilename = getFilename(req.getRequestURI());

        // see if its possible to load the resource from any of the defined paths
        for (String path : this.paths) {
            // I know string concatenation is bad but this just an example;
            if (!path.endsWith("/")) path += "/";
            cssInputStream = getClass().getResourceAsStream(path + cssFilename);
            // as soon as you find a good resource use it
            if (cssInputStream != null) break;
        }

        if (cssInputStream != null) {
            String evaluatedCss = evaluateEL(inputStreamToString(cssInputStream), req, resp);
            resp.getWriter().write(evaluatedCss);
        }
    }

    private String inputStreamToString(InputStream is) {

        return new Scanner(is).useDelimiter("\\A").next();
    }

    private String evaluateEL(String content, HttpServletRequest req, HttpServletResponse resp) {

        ELContext elContext = jspFactory.getPageContext(this, req, resp, null, true, 8192, true).getELContext();
        ValueExpression expression = expressionFactory.createValueExpression(elContext, content, String.class);
        return (String) expression.getValue(elContext);
    }

    public String getFilename(String fullPath) {

        int sep = fullPath.lastIndexOf("/");
        return fullPath.substring(sep);
    }

}

The next blog post should probably be about integrating this solution with WRO4J in order to bulk-load CSS and JS even from jar files.

This entry was posted in CSS, Java, Programming, Web Development and tagged , , . Bookmark the permalink.

One Response to Loading CSS from a JAR file evaluating EL

  1. Pingback: Loading CSS from a JAR file | Cribbs Technologies

Leave a Reply

Your email address will not be published. Required fields are marked *

*

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>