What you’ll need: Node.js
Sometimes it’s desirable to trim a page down to its bare essentials so that it loads as fast as possible. I do this when I’m linking a page someplace like Reddit, where it’s possible it will get 10,000 hits in 5 minutes. My server has “unlimited bandwidth”, but of course there’s a catch, and that’s that my per-second bandwidth is limited. I’m not complaining; it’s a budget host and fantastic for the price. But if too many people hit a page at once the site could experience the infamous Hug Of Death if I’m not prepared for it.
The first step is removing unnecessary CSS. One source of that is Bootstrap; at the time of this writing, April 28 2015, the core Bootstrap.css is 138kb, 114kb if minified. So let’s say your site has a 1mbps bandwidth limit. That seems pretty fast, right? If it was a download it would be blazing. But look at it this way: at 1mbps, just 10 people hitting the page at once would cause your site to exceed its bandwidth throttle from the CSS alone. That’s before even including your custom CSS or anything else. It would clear up pretty quickly, but when if another 10 people hit it the next second? Then 10 more the next? This is how Hugs of Death get started.
The most common suggestion is to use Uncss with Grunt, but I had a hard time getting Grunt to work for me and eventually gave up. Then I decided to try uncss by itself, and it was surprisingly easy.
You’ll need Node.js installed. This example uses Linux; not that it can’t be done on Windows, I just don’t know how.
- Make a directory and enter it.
npm install -g uncss
- Copy the sample file from the uncss page (or download it right here) and name it anything with a .js extension. I named it uncss.js.
- Replace the “files” array with your html files. (It looks like
var files = ['my', 'array', 'of', 'HTML', 'files']).
- Replace the “stylesheets” array with your stylesheets. (It looks like
stylesheets : ['lib/bootstrap/dist/css/bootstrap.css', '...']).
- Change the value of “csspath” if you need to.
node uncss.js(or whatever you called your uncss file). It spits out the optimized CSS straight to the command line, so save it to a file with something like
node uncss.js > mynewcss.css.
That’s it! As you can see, there are a bunch of options to tailor the behavior. I ignored all of them and it worked fine, but they’re there if you want them, and if you’re going to use it a lot you probably do.
One thing I did, not in uncss but directly in the stylesheet, was to skip some rules by putting
ignore: ['#added_at_runtime', /test\-[0-9]+/]. That’s handy because you can use regular expressions and have it skip everything that matches some naming convention.
In the page I tested it on, the Bootstrap CSS went from 138kb to 12kb (!). Not too shabby, and since the page got 70,000 hits in a day, I’m glad I did it.
This article started as my Stack Overflow Answer on this topic.