Wednesday, June 22, 2011

Webpage Render Speed Optimization - Parallelize downloads across hostnames

This optimization method is often called image sharding. The same thing applies to other static assets as well. So more appropriately, it should be called static resource sharding or static resource download parallelization.

Browsers have limits to how many hostnames they can render at the same time or in parallel. Here's a table for your reference.

Android 2.2
 4
Android 2.3
 4
Chrome 12
 6
Chrome 13
 6
Firefox 3.6
 6
Firefox 4
 6
Firefox 5
 6
IE 8
 6
IE 9
 6
iPhone 3.1
 6
iPhone 4.2
 4
Opera 11
 8
Safari 5.0
 6

Although this is the case, we have means to further optimize parallel resource object download to reduce page render time. Here are considerations which needs to be achieved.

1) Number of hostnames to be used must be adequate but not so much due to DNS resolution latency. To start of and gauge what you need, use the less than 4 hostnames rule-of-thumb. You may increase depending of how much static objects you have on the page.
2) The resource serving distribution across available hostnames must be even.
3)On successive requests to the same resource, it should be delivered via the same hostname it was served from so we can leverage browsing caching.

Solution 1: Sequential distribution

This utilizes an algorithm to walkthrough all the resources and assign available hostnames sequentially. When the end of stack is reached, reset the pointer to the beginning of the stack.

function getHostname()
{
      global $current;
      $hostnames = array('hostname1.com', 'hostname2.com');
      if ($current >= count($hostnames)) {

            $current = 0;
      }
      $fhost = $hostname[$current];
      $current++;
      return $fhost;
}

Note: you may also use a static method to have a better OOP implementation and without the use of global variable.

Although even distribution is achieved, the downside of this approach is that, on other pages, the same resource may be served from a different hostname and thereby browser caching advantage will only be limited per page and not immediately to the the entire site. Eventually everything will be browser cached however.

Solution 2: Hash-based distribution

This utilizes hashing algorithms and the modulo operator to determine hostname to resource mapping. This method is deterministic based on the URI of the resource and thus consistent across the site. This solution therefore is best at making sure that we can leverage browser caching.

function getHostName($url, int $variants) {
   $variant = (int) (str_replace("-","",crc32($url))) % $variants;
   return "http://static$variant.yourdomain.com/";
}

Note: Depending on the resource naming and the URLs, we can end up having the same hostname for all the static resources on the same page and not having to evenly distribute across hostnames.

Whatever you choose to decide as a solution from the above, there will be trade-offs. Check with your website and decide from there what the best one is for you. I am still working on how to best implement a resource mapping hash table that both satisfies the requirements for even distribution and browser caching.

  • Related Links Widget for Blogspot

No comments: