This site is now 100% inline CSS and no bytes are wasted

05 March 2013   8 comments   Python, Web development, Django

Powered by Fusion×

This personal blog site of mine uses django-fancy-cache and mincss.

What that means is that I can cache the whole output of every blog post for weeks and when I do that I can first preprocess the HTML and convert every external CSS into one inline STYLE block which will only reference selectors that are actually used.

To see it in action, right-click and select "View Page Source". You'll see something like this:

Stats about using
Requests:         1 (now: 0)
Before:           81Kb
After:            11Kb
After (minified): 11Kb
Saving:           70Kb

The reason the saving is so huge, in my case, is because I'm using Twitter Bootstrap CSS framework which is awesome but as any framework, it will inevitably contain a bunch of stuff that I don't use. Some stuff I don't use on any page at all. Some stuff is used only on some pages and some other stuff is used only on some other pages.

What I gain by this, is faster page loads. What the browser does is that it, gets a URL, downloads all HTML, opens the HTML to look for referenced CSS (using the link tag) and downloads that too. Once all of that is downloaded, it starts to render the page. Approximately after that it starts to download all referenced Javascript and starts evaluating and executing that.

By not having to download the CSS the browser has one less thing to do. Only one request? Well, that request might be on a CDN (not a great idea actually) so even though it's just 1 request it will involve another DNS look-up.

Here's what the loading of the homepage looks like in Firefox from a US east coast IP.

Granted, a downloaded CSS file can be cached by the browser and used for other pages under the same domain. But, on my blog the bounce rate is about 90%. That doesn't necessarily mean that visitors leave as soon as they arrived, but it does mean that they generally just read one page and then leave. For those 10% of visitors who visit more than one page will have to download the same chunk of CSS more than once. But mind you, it's not always the same chunk of CSS because it's different for different pages. And the amount of CSS that is now in-line only adds about 2-3Kb on the HTML load when sent gzipped.

Getting to this point wasn't easy because I first had to develop mincss and django-fancy-cache and integrate it all. However, what this means is that you can have it done on your site too! All the code is Open Source and it's all Python and Django which are very popular tools.


You can actually save another 991 byte if you strip all indentation and linebreaks from your html. Thats around 5% less :]
Peter Bengtsson
Makes too little difference once gzipped. I guess it's because whitespace compresses very well.
ah ok. Stuff is gzipped between server and browser?
Peter Bengtsson
Maybe I don't understand your question. Yes, the HTML, CSS and Javascript is gzipped on the server, sent to the browser in gzipped format and the browser then un-gzips it and displays.
No no you got me perfectly right! :] thanks for enlightning me. I'm glad it is that way but I honestly never knew.
Jason Cooper
Nicely done, Peter. Looks very intriguing. I'll have to check out using this in my Dango projects.
I like using CDNs, what's wrong with that option?
There's a great one for bootstrap.
Peter Bengtsson
CDN isn't a bad option. The thing is, when the HTML is downloaded, the browser needs to first parse the HTML, then parse the CSS before it can render anything to the screen. If it, in that space, also has to do another DNS lookup and then download a massive block of CSS (all will be parsed of that CSS, even the selectors that won't be used) then that will delay the rendering and thus it won't paint anything on the screen until that's done.

Granted, CDNs are quicker to download from thanks to the latency. However, the potential extra DNS lookup can be quite a severe punishment.

Check out this post about DNS lookups

What this all means is that ideally there will be a quicker; from the time you enter the URL until your eyes have something to feast on.

Your email will never ever be published

Related posts

Welcome to the world django-fancy-cache! 01 March 2013
django-fancy-cache with or without stats 11 March 2013
Related by keywords:
mincss "Clears the junk out of your CSS" 21 January 2013 - Transform CSS into line style attributes with lxml.html 11 July 2009
The awesomest way possible to serve your static stuff in Django with Nginx 24 March 2010
premailer now excludes pseudo selectors by default 27 May 2013
mincss in action - sample report from the wild 22 January 2013
XHTML, HTML and CSS compressor 07 April 2004
mincss version 0.8 is much much faster 27 February 2013
Welcome to the world django-fancy-cache! 01 March 2013
How to use premailer as a command line script 13 July 2012
mincss now support PhantomJS 02 February 2013
django-fancy-cache with or without stats 11 March 2013
Practical CSS 24 February 2004