About compression — again

Matti Tahvonen
Matti says about web apps…
3 min readMay 15, 2015

I have many times emphasized the importance of compression of resources served by your web server. For some I have given a bad advice, that will break your apps when you update to Vaadin 7.5 🙁 Thus I decided to write a short blog entry about the issue again and a workaround for my tip.

The thing I shouldn’t have suggested is to use the rather naive GzipFilter from ehcache-web module directly. Don’t do this (or similar with web.xml config):

@WebFilter(urlPatterns = {"*.js","*.css", "/UIDL/*"})
public static class StaticResourceBooster extends GzipFilter {
}

That filter alone, works for some rather simple cases, but it is clearly not planned to be used as a general purpose gzip filter that you can put in front of anything you want. In Vaadin 7.5 we’ll introduce a nice feature which will most often serve pre compressed versions of the static widgetset files (automatically generated during the widgetset compilation, mostly .js files). This makes the initial load of most Vaadin applications much faster, even if compression is not handled by developer or server maintainer. But, the EHCache GzipFilter, that I have suggested to use for some of you, doesn’t check if the served resource is already compressed for transfer, so it brutally double compresses the content. Not good 🙁

The solution is to give another turboboost from ehcache-web module for your static file delivery. A commonly used helper is SimplePageCachingFilter, that will also store the cached files in an efficient in memory cache for efficient delivery. It will also take care about gzip compression and it does check if the content is already gzipped. This approach also avoids compressing your static resources each and every time a new user enters your site. Just make sure you don’t cache requests to “/UIDL/*” as otherwise your application will most likely die somehow as the same state responses are given for each and every users. The configuration class for this kind of setup would look like this:

@WebFilter(urlPatterns = {"*.js", "*.css"})
public static class StaticResourceBooster2
extends net.sf.ehcache.constructs.web.filter.SimplePageCachingFilter {
}

In addition to that you’ll also need ehcache.xml file to your class path (e.g. src/main/resources/ in Maven builds) to introduce and configure the EHCache instance to be used with the page cache. For example this should do pretty well:

<?xml version="1.0" encoding="UTF-8"?>
<ehcache xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="ehcache.xsd" updateCheck="true" monitoring="autodetect" dynamicConfig="true">

<diskStore path="auto/default/path"/>
<!-- Page and Page Fragment Caches -->
<cache name="SimplePageCachingFilter" maxElementsInMemory="200" eternal="false" timeToIdleSeconds="300" timeToLiveSeconds="6000">
</cache>
</ehcache>

If you still want to compress the Vaadin state changes, you can hook the GzipFilter to “/UIDL/*” only. Another alternative is to use the good old GzipFilter from the Jetty Servlets package.

The good old way

The good old jetty-servlets package is naturally something we can still use. And as always, I should probably emphasis that the jetty-servlets module is Jetty server independent, so this approach works with pretty much any server.

The dependency that you’ll need:

<dependency>
<groupId>org.eclipse.jetty</groupId>
<artifactId>jetty-servlets</artifactId>
<version>9.2.10.v20150310</version>
</dependency>

The Servlet 3 style configuration that should do fine for Vaadin apps:

@WebFilter(urlPatterns = {"/*"}, initParams = {
@WebInitParam(name = "mimeTypes",
value = "text/html,text/plain,text/xml,application/xhtml+xml,text/css,application/javascript,application/json,image/svg+xml"),
@WebInitParam(name = "methods", value = "GET,POST")
})
public static class StaticResourceBooster3
extends org.eclipse.jetty.servlets.GzipFilter {

}

All essential stuff compressed, like it should be 🙂

--

--