Make JavaScript Load Faster

Here are a few steps one can follow to get JavaScript to load faster on your website.

  1. Minify your scripts and script libraries.
  2. Compress your scripts.
  3. When necessary, use an .htaccess file to get Apache to work properly with your compressed scripts.

1.

$ java -jar yuicompressor-2.3.4.jar

Usage: java -jar yuicompressor-x.y.z.jar [options] [input file]

Global Options
  -h, --help                Displays this information
  --type <js|css>           Specifies the type of the input file
  --charset <charset>       Read the input file using <charset>
  --line-break <column>     Insert a line break after the specified column number
  -v, --verbose             Display informational messages and warnings
  -o <file>                 Place the output into <file>. Defaults to stdout.

JavaScript Options
  --nomunge                 Minify only, do not obfuscate
  --preserve-semi           Preserve all semicolons
  --disable-optimizations   Disable all micro optimizations

If no input file is specified, it defaults to stdin. In this case, the 'type'
option is required. Otherwise, the 'type' option is required only if the input
file extension is neither 'js' nor 'css'.

Minification, assuming the minifier works, is a piece of cake. Here we use the Yahoo YUI Compressor.

$ java -jar yuicompressor-2.3.4.jar prototype.js > prototype-min.js

To do more than one file at once, e.g. Scriptaculous:

#!/bin/bash

mkdir min
for fn in `ls *.js`; do
    bn=`basename $fn .js`;
    java -jar yuicompressor-2.3.4.jar $bn.js > min/$bn.js;
done

2.

You can then compress the files with gzip with the same trick.

#!/bin/bash

for fn in `ls *.js`; do
    bn=`basename $fn .js`;
    gzip -9c $bn.js > $bn.jgz;
done

3.

Finally, here's the .htaccess file I use to serve compressed JavaScript files. [originally from here] My webhoster's Apache doesn't do it for me (sigh), so some of my pages were taking ages to load. You do need to change the <script> tags to use the .jgz files instead of the .js files, and both sets of files must live in the same directory, so this trick could be more trouble than simply modifying your Apache server to send out compressed data anyway. But, if you don't have that option, then this trick works fine.

RewriteEngine on
RewriteCond %{HTTP_USER_AGENT} ".*Safari.*" [OR]
RewriteCond %{HTTP:Accept-Encoding} !gzip
RewriteRule (.*)\.jgz$ $1\.js [L]

AddType "text/javascript;charset=UTF-8" .jgz
AddEncoding gzip .jgz

A.

A quick comparison:

scriptaculous/fat$ ls -lgGh
total 156K
-rw------- 1 4.7K 2008-03-12 05:01 builder.js
-rw------- 1  35K 2008-03-12 05:01 controls.js
-rw------- 1  31K 2008-03-12 05:01 dragdrop.js
-rw------- 1  39K 2008-03-12 05:01 effects.js
-rw------- 1 2.6K 2008-03-12 05:01 scriptaculous.js
-rw------- 1  11K 2008-03-12 05:01 slider.js
-rw------- 1 1.9K 2008-03-12 05:01 sound.js
-rw------- 1  20K 2008-03-12 05:01 unittest.js

scriptaculous/min$ ls -lgGh
total 108K
-rw------- 1 2.4K 2008-03-12 09:02 builder.js
-rw------- 1  22K 2008-03-12 09:02 controls.js
-rw------- 1  19K 2008-03-12 09:02 dragdrop.js
-rw------- 1  25K 2008-03-12 09:02 effects.js
-rw------- 1  918 2008-03-12 09:02 scriptaculous.js
-rw------- 1 6.6K 2008-03-12 09:02 slider.js
-rw------- 1 1.2K 2008-03-12 09:02 sound.js
-rw------- 1  13K 2008-03-12 09:02 unittest.js

scriptaculous/jgz$ ls -lgGh
total 44K
-rw------- 1 1.2K 2008-03-12 09:05 builder.jgz
-rw------- 1 5.8K 2008-03-12 09:05 controls.jgz
-rw------- 1 5.5K 2008-03-12 09:05 dragdrop.jgz
-rw------- 1 6.6K 2008-03-12 09:05 effects.jgz
-rw------- 1  527 2008-03-12 09:05 scriptaculous.jgz
-rw------- 1 1.9K 2008-03-12 09:05 slider.jgz
-rw------- 1  592 2008-03-12 09:05 sound.jgz
-rw------- 1 3.6K 2008-03-12 09:05 unittest.jgz