Serving Static Content from a Cookieless Domain
Serving static content from a cookieless domain is a standard performance best practice, one you’ve surely encountered if you’ve used a performance analysis tool like YSlow or Page Speed. The concept is simple—don’t serve static content like images and stylesheets from a domain that sets cookies—but exactly how to achieve this might not be clear to everyone. And for beginners, both the concept and the execution can be slightly confusing. So here is a brief explanation of the idea, followed by a few options for implementing it.
The trouble with cookies
From a performance perspective, the trouble with cookies is that once the server sets a cookie for a particular domain, all subsequent HTTP requests for that domain must include the cookie. Even if the server has no use for the cookie, as is usually the case with static components, the cookie is sent over the wire anyway, bloating our request headers with useless code.

Of course, cookies are typically very small. In a lot of cases an extra 300 bytes per request may be insignificant. The negative performance effect is lessened further if you’ve implemented other performance best practices, such as using sprites and concatenated files to reduce HTTP requests, or using Expires and Cache-Control headers to limit the number of trips to the server.
But remember that this extra weight, however small, is added to every request. Even requests for cached components that rely on the Last-Modified header. If your site has a large number of page components and/or heavy cookies, optimizing your site to deliver static assets from a cookieless domain may be well worth the effort.
So how do we do it? Remember that when the server sets a cookie, that cookie is attached to all future requests to the same domain (and often all subdomains as well). To get around this we simply need to request our static assets from a different domain.
I’ve emphasized the word “request”to highlight the fact that it’s only the request that matters. The static content does not need to “live” at another location; it only needs to be accessible from a different domain.
Using a CNAME
The easiest way to set up a cookieless domain for your static content is to create a CNAME record aliasing your static domain to your main domain. Your static files remain in the same place but you can now reference them at a different domain.

You can serve your static content from a subdomain (static.example.com), or you can serve it from a separate domain (www.static-example.com). If you choose to serve it from a subdomain there are a few steps you will need to take to ensure that cookies are not set on your static subdomain (see the next section).
When you create the CNAME record you want to enter your static domain/subdomain as the “label”, “name”, or “alias” and your A record domain as the “content” or “value”. (The CNAME term, which stands for “Canonical Name”, actually refers to the domain you are mapping to, not the alias. The common practice of referring to the alias as the “CNAME” is in fact backwards.)
Once you’ve set up the alias you’ll need to modify all the references to your static files to point to the new domain.
<img src="/img/animated-unicorn.gif" alt="" /> <!-- Becomes --> <img src="http://static.example.com/img/animated-unicorn.gif" alt="" /> <!-- or --> <img src="http://www.static-example.com/img/animated-unicorn.gif" alt="" />
Now, as long as you only reference files on the static domain that do not set cookies, a cookie should never be set for your static domain and all of your future requests for static content be sent cookie-free. Woot sound.
Separate domain or subdomain?
In order to set up a cookieless subdomain you have to make sure that your server or application only sets cookies for www.example.com and not the top-level example.com. (Cookies set at the top-level domain apply to all subdomains as well.) How you go about this of course depends on your particular set-up. But two common cookie-setters are Google Analytics and WordPress.
For Google Analytics, you have to set the “_setDomainName” value to your www domain. Like this:
_gaq.push( ['_setAccount', 'UA-xxxxxxx-1'], ['_setDomainName', 'www.example.com'], ['_trackPageview'] );
For WordPress, open up wp-config.php and add this line:
define('COOKIE_DOMAIN', 'www.example.com');
Obviously, this only works in situations where you don’t need to set cookies on other subdomains. To avoid this restriction, use a separate domain name.
An interesting solution for creating a cookie-free domain without having to register a second domain is 2static.it. They set up an alias to your main domain, allowing you to request your static files from http://somename.2static.it.
As far as I know, there are no downsides to using a separate domain. And it appears to be the most popular option. The only potential drawback I can think of is the possibility that Google might disassociate your images from your domain. But this is just speculation.
Speaking of SEO, you might be wondering if there is a duplicate content penalty for mirroring your entire site. The short answer is “not really”. I recommend watching this video where Google’s Greg Grothaus explains the myth of the duplicate content penalty. If you’re still concerned, you could always 301 redirect all requests for anything other than static files to your principal domain.
Using a CDN
If you offload your static content to a CDN or a file storage service like Amazon S3, keeping the static file requests cookie-free should be easy as long as you haven’t set up a CNAME record on a subdomain that receives cookies from your top-level domain. Remember it’s all about the domain that the request is made to and making sure nothing on that domain sets any cookies. Whether the files are hosted on Amazon’s servers or yours is unimportant.
Bonus round
A bonus benefit to serving static content from a cookieless domain is that you can double the number of page components that browsers can download in parallel. But realize that this works best when the components are balanced across two domains. If 95% of your assets are static files and if you move all of them to static.example.com, you aren’t really taking advantage of maximizing parallel connections. You’re just incurring the extra DNS look-up. (See this previous post about some light testing I did on domain sharding.)
Related Reading
- HTTP Cookies Explained (Nicholas Zakas)
- Best Practices for Speeding Up Your Website (Yahoo)
- Minimize Request Overhead (Google Page Speed)
Discussion
« Older CommentsHey,
I’m trying to use a new domain JUST for static content, but having issues.
When i type the static domain in the browser, im redirected to the main domain.
I’m guessing its the .htaccess in the main site as it re-directs all non-www to www. How do i fix this?
And also, how do i configure my new domain? Do i use an A record (Pointing to my main sites IP), or CNAME?
My .htaccess:
Options +FollowSymlinks
RewriteEngine on
RewriteCond %{HTTP_HOST} !^www\.site\.com$ [NC]
RewriteRule ^(.*)$ http://www.site.com/$1 [R=301,L]
Thanks in advance for any help!!
Danny
Hi Danny,
You just need another rewrite condition. At the moment it’s redirecting to http://www.site.com unless the host already is “www.site.com” You need to tell it to also not redirect if the host is “static.site.com” like this:
RewriteCond %{HTTP_HOST} !^www\.site\.com$ [NC]
RewriteCond %{HTTP_HOST} !^static\.site\.com$ [NC]
RewriteRule ^(.*)$ http://www.site.com/$1 [R=301,L]
Hi and thanks for this guide!
I’m still not sure on how should I make the following resources pointing to my static subdomain:
wp-content/themes/photolux/images/patterns/pattern25.png
wp-content/themes/photolux/images/noise.png
wp-content/uploads/sezioni/logo.png
wp-content/themes/photolux/images/top_navigation_gradient.png
wp-content/themes/photolux/images/ajax-loader.gif
wp-content/themes/photolux/images/quote.png
wp-content/themes/photolux/images/sidebar-arrow.png
wp-content/themes/photolux/images/gradient_button.png
wp-content/themes/photolux/images/search_icon.png
I mean, what is the file containing calls to this resources?
Thanks!
Ignorant question for ignorant person:
I have a domain, http://www.osacc.com that is making 42 requests for cookie that I am told I should put into a cookieless domain. I understand that I need to make a sub “static.osacc.com” My question is, what is the best way to find all of the “calls” for those files to change them. Is there a global setting that can be adjusted or do I have to go a longer route.
Any help would be greatly appreciated.
Thanks
If you’re using WordPress look into W3 Total Cache.
Setup the CDN section with your static domain/subdomain, and it will load your static content (images, theme files, etc) to it for you. You can pick and choose what files (by names, types, locations, etc) get sent over to the CDN (in this case your static domain/subdomain) by W3TC.
http://wordpress.org/extend/plugins/w3-total-cache/
Hi,
I used your approach and created a subdomain for my website.
This is what I did.. my site say: http://example.com and I created a subdomain: http://images.example.com and pointed this subdomain to same http://example.com.
Now in code, I rewrite the image path from /images/abc.png to http://images.example.com/images.abc.png
But the images are not displaying on my site. If I try to inspect the element and open the image link, it opens properly using this subdomain path.
Please help. My domain name is on godaddy.
Thanks,
Pawan
I just setting the www. to the GA code and all my visitors become new visitors. If i revert back to domain.com it works fine. Do you know what is going on?
Please ignore my previous comment. I figured out.
Hi Rob thanks for this great article. I do have a question. What’s the point of creating the cname? In other words, for instance if your site is http://www.site.com and you register another site http://www.images-site.com. Why not just move the static resources to that site instead of setting up a cname as well? You be referencing them anyway in the code. Is it just so that you don’t have to move the static files or is there some other seo reason?
Additionally what do you think about putting:
Header unset Cookie
Header unset Set-Cookie
In the htaccess of http://www.images-site.com?
Thanks for the great post!!
William
Question… what if the site is using ssl? Does the static content have to come from the same ssl domain? What happens if the static content is not sent from an ssl domain?
Patrick,
If you have a CDN like akamai they support SSL request through a CNAME. However, if you don’t have such a feature you must use a url redirect like below:
Redirect like what below? You holding out on me
apparently i cant paste code…it filtered it out. here it is again..
here is the pastebin link: http://pastebin.com/9cu2k8yU
Hi, I have a subdomain media.example.com where I uploaded all my pictures for the past 2 years. As it serves cookies, so I have done what it says on this post – I have set my setDomainName to http://www.example.com and added in the wp-content.php the line define (‘COOKIE_DOMAIN’, ‘www.example.com’);, but the subdomain still serves cookies. Is it possible to revert an existing subdomain that is serving cookies to one that does not serves cookies or do I have to create a brand new subdomain?
Making a cookieless domain is not that hard. The main thing is that static file such as images, stylesheets and javascrtipt is getting served from that particular (sub)domain. It’s basicly a CDN (Content delivery network.)
If you have wordpress, all you have to do is download a cache plugin such as wordpress super cache. Create a sub- or new domain and fill out the CDN form tab in wp super cache or Total cache or which plugin you preffer. If you create a new domain you should move your static content there.
If you don’t use wordpress, you should set it up yourself. That can be done in PHP and- or .htaccess (httpd.conf). Thats more difficult. What i suggest is, google for create your own CDN to get a better understanding about the subject! =)
(PS)
Nice post.
Good luck!