martes, junio 14, 2011

Y Hay Un Decano También, Y Un Abogado También, Y Un Policía Rodeado De Ladrones (La Taberna del Buda - Café Quijano)



Due to the advent of mobile internet, a variety of devices have connection to the world (mobiles, pads, GPS, netbooks, ...), and these devices could not be as powerful as desktops/notebooks. For this reason, keeping web pages as lightweight as possible is a must. Improving the engineering design of a page or a web application usually is the biggest savings and that should always be a primary strategy. With the right design, some other strategies can be followed. One of these is code minification.

Now-days, jQuery are becoming so popular in client-side of web development. jQuery is a cross-browser Javascript library designed to simplify the client-side scripting of HTML. jQuery itself is composed by "one" file. Thanks of that boom, Javascript is becoming more important when a web interface is developed.

Have you ever opened jQuery Javascript file? Let me tell you what you will see. Nothing human readable, all code occupied only one long line, and variables and methods name are as short as possible:

See this example:

Of course, there is no developer in the world (or at least I wish), that could write this code. So where this code comes from? It is so easy, it comes from a Javascript minifier tool.

The goal of Javascript and CSS minification is always to preserve the operational qualities of the code while reducing its overall byte footprint

There are a lot of tools designed for minifying Javascript files. One of these are YUI Compressor from Yahoo. From its site:

“The YUI Compressor is Javascript/CSS minifier designed to be 100% safe and yield a higher compression ratio than most other tools. Tests on the YUI Library have shown savings of over 20% compared to JSMin (becoming 10% after HTTP compression).”

Because the growth of popularity of jQuery, and HTML 5/CSS3, client-side coding is playing an increasingly important role in web development, and one of these consequences is that in client-side you could need to develop some custom Javascript files, apart from using already developed Javascript libraries like jQuery. And then the question is, if jQuery minify their files, why I cannot do the same with my Javascript/CSS files? And the answer is: “Yes you are right”, and also I say: “We will automatize this process into Maven, so your web project will be packaged with minified scripts”.

Let’s start with a very simple “Hello World” script file:

If you execute manually YUI Compressor as standalone application (java -jar yuicompressor-x.y.z.jar), script is minified to:

output: myscript.js (115b) -> myscript.js (54b)[46%]

Now our script is 46% smaller than the first one, of course the price we are paying is that we are loosing readability, but in production environment makes no sense.

Next step is configuring your pom.xml (Maven) so when application is packaged, all packaged Javascript files are minified. For this porpoise yuicompressor-maven-plugin (http://alchim.sourceforge.net/yuicompressor-maven-plugin/) plugin comes to rescue you.

No secret here, plugin is executed in generate-sources phase, and is configured with no suffix option because I want that “compressed” file has the same name as original one, and also I don’t want any line break in minified file.

And finally the last trick, maven-war-plugin configuration should be changed for avoiding it replaces minified files for original ones.

In this case scripts are in src/main/webapp/script so excluded sources are script/*.js. yuicompression plugin will copy minified files into target directory that will be used by war plugin for building war file. For this reason we should avoid that war plugin also copies the original file to target directory, replacing the good ones (compressed) for the bad ones (uncompressed).

If you read my previous post, where I talked about decreasing download time of Javascript/CSS files(using aggregation) and also I explained why not to use an automatic approach in development time but in running time, I suppose you are wondering why I am explaining in this post minification using Maven? Well let me explain, YUI Compression should be used in conjunction  with aggregation files. YUICompressionplugin supports aggregation too, so if you are developing a public API it is a good approach using YUICompression (using Minifing and aggregation) with Maven. But if you are developing a website, the best approach is applying optimizations at runtime using Jawr API as I explained in my previous post. But next question  is how to use Jawr (by default it uses JSMin) with YUIcompression? The response is easiest one anyone could think, Jawr also supports YUI. Only one line should be added, open jawr.properties and copy next line:

jawr.js.bundle.factory.bundlepostprocessors=YUI

Now Jawr will minify aggregated file using YUI Compression instead of JSMin.

Hope you find post useful.


Music: http://www.youtube.com/watch?v=K_mJ1NgqiSk

6 comentarios:

  1. You can also choose between other minimizers like (UglifyJs, DojoShrinkSafe, GoogleClosure, etc). with wro4j maven plugin: http://code.google.com/p/wro4j/wiki/MavenPlugin

    ResponderEliminar
  2. Anónimo4:00 p. m.

    Of course, JQuery is minified with Google's Closure Compiler.

    http://blog.jquery.com/2010/02/19/jquery-142-released/

    ResponderEliminar
  3. Hi Alex, thank you very much for the information, it is another valid possibility, but for me because I only use YUI Compressor, the explained plugin is enough. Anyway thank you very much.

    ResponderEliminar
  4. Yes jQuery is minified with Google's Closure Compiler, it wasn't my intention to say that jQuery is minified with YUI Compressor, I only wanted to note that jQuery is also minified.

    Thanks for the clarification.

    ResponderEliminar
  5. Anónimo6:27 p. m.

    Look at http://js-optimizer.sourceforge.net

    it integrated YUICompressor and JSMin to provide minimized js and with a minimum number of connections. But also to disable compression in case of problem : setting a cookie from the adresse bar allows troubleshooting non-minimisez code.

    ResponderEliminar