Orange is my favorite color

Marc Esher asked a question about how I use my CDNs during development. I didn’t really address how the web application (in my case, ColdFusion) fits into the picture.

First, to actually generate the files, one of the targets for my Ant script is “localdeploy” and my development.properties file has all Windows paths that point to my local webroot with a directory for my static assets. The “magic” is in my Model-Glue application config file where I have a couple of properties:

<entry key="CDNURL"><value>cdn-mybucket.s3.amazonaws.com</value></entry>
<entry key="CDNZURL"><value>cdnz-mybucket.s3.amazonaws.com</value></entry>

One is for gzipped assets and one is not. As part of my theming system, I have a controller with this routine that runs on every request:

< !--- determine HTTP/HTTPS and current WEB_HOST --->
<cfif cgi.server_port_secure>
<cfset arguments.event.setValue("CurrentRootURI", "https://" & getThemeService().getConfig().getConfigSetting("WEB_HOST")) />
<cfif findNoCase("gzip", cgi.HTTP_ACCEPT_ENCODING)>
<cfset arguments.event.setValue("CDNURL", "https://" & getThemeService().getConfig().getConfigSetting("CDNZURL")) />
<cfelse>
<cfset arguments.event.setValue("CDNURL", "https://" & getThemeService().getConfig().getConfigSetting("CDNURL")) />
</cfif>
<cfelse>
<cfset arguments.event.setValue("CurrentRootURI", "http://" & getThemeService().getConfig().getConfigSetting("WEB_HOST")) />
<cfif findNoCase("gzip", cgi.HTTP_ACCEPT_ENCODING)>
<cfset arguments.event.setValue("CDNURL", "http://" & getThemeService().getConfig().getConfigSetting("CDNZURL")) />
<cfelse>
<cfset arguments.event.setValue("CDNURL", "http://" & getThemeService().getConfig().getConfigSetting("CDNURL")) />
</cfif>
</cfif>

Basically we’re checking for HTTP vs. HTTPS and whether or not the client can support Gzipped content (signaled by the Accept header). Then my HTML wrapper just uses those parameters:

<link rel="icon" href="#CDNURL#/favicon.ico" type="image/ico" />

At this point you should recognize that every static asset MUST have a prefix that points at your CDN. You can hardcode it, make it dynamic like I have, or something else altogether but you need a way to point every request for a static asset off to the appropriate location.

Generally when I’m developing locally I actually use my staging environment CDN. This helps me prove that it works when accessed remotely. But if I want to use my local environment during a more substantial build out, I just set my CDNURL and CDNZURL to empty strings and all of my references suddenly evaluate locally:

<link rel="icon" href="/favicon.ico" type="image/ico" />

I use directories on my CDN like /global, /js, /css and /gfx so to make it all work seamlessly locally, I have a few Apache alias statements in my httpd.conf for the VirtualHost:

# CDN
Alias /gfx "C:/Documents and Settings/brian/My Documents/web/cdn/gfx"
Alias /js "C:/Documents and Settings/brian/My Documents/web/cdn/js"
Alias /css "C:/Documents and Settings/brian/My Documents/web/cdn/css"
Alias /global "C:/Documents and Settings/brian/My Documents/web/cdn/global"

Note that an added benefit of this which I touched on in my last post is that if Amazon S3 should suffer a major outage, I can reconfigure my production app to have empty strings for the CDN and CDZ URLs and use a locally stored copy of the assets on our regular web servers. It’s trivial and adds a layer of reliability for a system that we don’t manage directly.

Hope that fills in the missing blanks!

2 Comments

  1. Sami Hoda said:

    on September 3, 2009 at 2:23 pm

    I’ve been looking into http://simplecdn.com/. I was wondering if you could do a comparison with Amazon’s service… Thoughts?

  2. brian said:

    on September 3, 2009 at 3:20 pm

    Sami – there are a few comparisons out there if you google. I haven’t used any of the other providers and in fact S3 is really a “poor mans” CDN since it doesn’t do true edge caching/etc but you reap a lot of the same benefits. The nice thing with S3 is you click a button and turn on CloudFront and you have a true CDN on top of S3. In my case, I would only need to change the two config properties in my app and I’d be running on it instead.

{ RSS feed for comments on this post}