Situation
All of our sites have three style sheets, an “all”, “handheld” and “print” all necessary to a well rounded web experience.
Problem
They come at a cost tho, three HTTP requests each page load. It doesn’t seem too bad when you get 1000 visitors a day or each file is only 100k but it get infinitely compounded when 40,000 visitors a day and the css weigh in at ~5kb total. Just in the access log alone that is 3 lines per visitor or ~160 bytes totaling ~6.4 megs of log data a day.
Solution
@media – The hidden killer.. er.. saviour. Combining all those style sheets into one and using @media to separate the pieces.
Example
@media all {
#content{
background: #0C5449 url(../images/content-bg.gif) repeat-y top left;
width: 706px;
}
...
}
@media handheld {
#content{
width: 100%
}
...
}
@media print {
#content{
background-image: none;
width: 100%
}
...
}
In the HTML:<link href="/css/home-all-min.css" rel="stylesheet" type="text/css" media="all" />
Results
A reduction of 2 less HTTP requests and 2/3 less data being written to the access log. Compression saves ~20% of the css size but combining into one file reduces the overhead of the 1kb or 500b for the mobile and print style. Multiply that by 22% of our new visitors a day with an empty cache is a savings of ~24,000 HTTP requests a day.
I would say that its well worth it, reducing the amount of net traffic while still presenting the same amount of information. Although this is straight data without compression, things really start to get interesting when compression is added to the mix, stay tuned.
Road to validation.
Nov 18Overseeing the current Wayne State University homepage is like running with a tiny pebble in your shoe. You feel it every step but your going so fast you cannot stop to take it out.
Working with a site so large it can become discouraging but taking one step at a time one can accomplish anything. Yesterday we took our first step, moving the site to a new server in an environment that we are comfortable and flexible in.
The old version of the site was sitting on an NT box, a requirement of the company who built it over 4 years ago. When I started I had a few goals, one was to get the site off that server and get it validated and rewritten in POSH. Well that day has come and we managed to sprinkle in a few other goodies along the way, here are some highlights:
- Valid XHTML Transitional
- No More Tables
- No SQL Requests
- ADA Accessible
- Way Prettier Print Version
- Mobile Version
- Microformats
- Opensearch
- YSlow Grade B (83)
It took some work to get here but we made it. There is still some tweaking to go but all in all its setup. Now its time to concentrate on the content, we are going to be doing a page by page overhaul and adding greater functionality and layout to each child page.
In addition to the content we will also be shrinking the file size and HTTP requests further and further down to the base minimum. Right now we are ~90k depending on the panel that loads and 16 HTTP requests with an empty cache, we hope to cut the size down by a third and get rid of 2-4 requests.
Stay tuned for more progress.
Progressive Enhancement
Sep 23Building for the lowest common denominator and then expanding upward. It sounds like a simple concept but most wed developers just can’t seem to grasp it. Not believing accessibility matters or being so inexperienced that building sites seems to just be a hack fest to make the “design” work in all browsers is the single largest issue with web design now a days.
One example off the top of my head is mtv.com which did a total redesign in flash and had all these crazy bells and whistles, integrated video, movement, etc. Well two months later guess what happened, they redesigned again this time into a fully xhtml compliant site which didn’t have all the movement but was 100x easier to use and you could actually get to it with a cell phone and actually search for text on the page.
Two simple things I always look for when going to sites, first since I don’t have a lot of time to read through pages for information I use the firefox built in find as you type and if it cannot jump right to the word i am looking for ill go someplace else.
The second I don’t use as much but I am sure other people do, phone browser support. I am not talking about iPhone safari support because that is not really developing for the lowest common denominator. I use either a WAP browser of Opera on my phone while out and about if I need to look up information quickly. If I cannot get to your page and get to the information I need I will leave your site and probably never return.
We have a CMS that we built at Wayne State and sometimes page updates need to happen right then. We built it for the lowest common denominator just for that reason. We can get to it on any WAP browser and update any page in the CMS as if we were on a full computer. Without it we would have to rush to a computer just to use some fancy ajax interface, it would be pretty but would it really be worth all the hassle? I think not.
Anthem:
Speed > Features
Simple > Complex
Enhancement > Degradation
Recently I started using jQuery instead of Prototype for my web applications. When I first started using a javascript library I picked Prototype because to be honest jQuery intimidated me, there was a lot of mystery about it. Well I took another look at it a few days ago and I was floored, boy I was missing out. jQuery byte for byte in my opinion kicks prototypes butt.
Take for example attaching a function to the document load and adding an onclick action to a link.
Pototype:// Initially set everything upjQuery:
init = function (){
// If there is an expand dom element
if ($('expand')){
Event.observe($('expand'), 'click', ExpandMenu, false);
}
} // Attach the onload function
Event.observe(window, 'load', init, false);
// Initially set everything upIt may not seem like a great deal of code reduction but scanning the code from top down (say if you were a developer brought in to fix a bug) shows how more fluid jQuery is in terms of execution flow. Prototype jumps all over the place…
$(document).ready(function(){
// On click event
$("#expand").click(function(){
// Function actions here
});
});
- First define the initializer function
- Next find the element on the page
- Set an observer on it and direct it yet another function
- Last but not least attach the initializer to the document load
- Create a function and attach it to the document ready state
- Create a function and attach it to a dom element on click
- Done.
First round goes to: jQuery
Dial Up North
Jul 24Dialup sucks, everyone knows it, but it is cheap, free in most cases. Recently MichNet cut all its subscribers off of their dial up internet service which Wayne State was part of so we were in the market for a dial up service to connect to the net upnorth. I decided on NetZero mainly because it was free. My review of the software is that it Sucks. I have used dialup for a while now upnorth but this service is the pits, the free one installs a toolbar on IE, for a while I could not get any other application to connect to the net besides IE which is a real bummer if you need to use SSH or an IM client. But eventually like magic applications began to come online, I cannot explain it but it made me happy.
It really put things into perspective for me again on how a lot of people still view the net. It was so slow at some times that I eventually disabled images and then things were flying quite well, but it really showed off which developers have the skill to accommodate this slow pace world. Some things I noticed that really helped were:- Using a background-color approximately the same color as an image background. This way if the image background does not load then the text on top still have a background color to contrast against.
- Combining images and use background positioning to put them in place. This dramatically reduces the number of images to load. Like I mentioned before images were the real killer of speed when using dial up. Better yet if you can use background colors instead of images it really speeds things up without loosing design points.
- Combining Javascript files and using a compressor. This is a no brainier it take almost no effort and helps with slow and fast connections. JS files can get large and they don’t have to be, I recommend using an automated compression tool called Minify. Really easy to use and
- AJAX. It is odd but it really kept me on sites with AJAX for a longer period of time because the site seemed snappier and I didn’t have to wait for the whole page to load over and over again.
- If you have image/flash ads on your site really sit back and think if slowing down the information on your site to a portion of internet users is really worth the few cents you may get from them clicking on the ads. Content is king, if a dial up user cannot get to your content because of a large flash or image ad on your site they will more than likely go someplace else that is dial up friendly.
Apache’s AB tool is a great way to really put stress on a server. I have compiled a list of the parameters I use to test my sites and applications.
First we have to make sure AB can hit the desired page and get the desired results. The most basic page is the homepage of a site, use the command below to send as many single requests as it can in 1 secondab http://example.com/But that is great and dandy but what happens if we want to try to stress a page that hits the database and has to do some actual dynamic work
ab http://example.com/search.php?q=TreesLast but not least what if the site is behind a login that is an http form and not an htaccess form? That is where POST variables come into play, it is a little trickier but doable. Here is the command I use to hit a page behind a login.
ab -p ~/Documents/post.txt -T application/x-www-form-urlencoded -e http://example.com/manager/Here is what my post.txt file contains:
email=test@domain.com&password=testing&submit=LoginNext we need to get these results to a file so we can work with them and have a record of progress as we tweak our site. It can be done with the “-e” parameter. An example is below:
ab http://example.com/search.php?q=Trees -e ~/Documents/results1.csvWhat that does is hits the search page and puts the results in the results1.csv file. It is useful to put the file at the end of the command since you will want to change the filename on each run to keep a history of your results.
The csv file is separated into two columns. The first is the percentage complete and the second is the time in ms that it took to get to that percentage.
The first thing you want to look at is the zero percent. This is your latency, it is the amount of time it takes to fulfill the first request. You want this number to be as low as possible. I am running my site on a development server on my local network so the times will be lower but at the end I will show the results from the testing server.ab -p ~/Documents/aci_post.txt -T application/x-www-form-urlencoded -e ~/Documents/aci_output.csv -kc 10 -t 10 http://aci/manager/makes.phpHold tight, more coming soon…