Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

URL Fingerprinting / Agressive Caching with NGINX + Express

What is the recommended technique for handling aggressive caching and URL fingerprinting in an NGINX (proxy) and Node / Express stack?

Google recommends to "use fingerprinting to dynamically enable caching." in their best practice guidelines and this is exactly what I'm trying to achieve.

I've looked at quite a few different approaches for fingerprinting but I'm struggling to understand under what scenario these will actually generate a new fingerprint and what part of the development pipeline it's best to sit. I had previously assumed that if 'Last-Modified' changes on the file then the server will generate another fingerprint but that doesn't seem to be the case on yet. (Unless I've misconfigured)

Here are a few different approaches:

Runtime Fingerprinting

  • dactyloscope
  • static-asset

Build Fingerprinting

  • asset-rack
  • node-version-assets

CI Fingerprinting

  • grunt-fingerprint
  • grunt-asset-versioning

So a couple of questions I hope someone can answer:

  1. Is fingerprinting even a requirement with ETags in place or are there too many holes in cross-browser support?

  2. Assets should arguably sit on a CDN so is this problem largely deferred to a CDN provider (if so how do you update references without manual involvement)?

  3. How does a new fingerprint get generated without manual cache clear?

  4. What is the suggestion on where this fingerprinting will sit in the developer pipeline? I want to avoid a dependency on the likes of Grunt.js

I feel like I'm missing something blindingly obvious so if you can answer just one of these questions I'd be really grateful.

like image 756
Palgie Avatar asked Nov 19 '13 14:11

Palgie


1 Answers

Fingerprinting and Etags are separate features for reducing load times.

Etags avoid having to resend an asset if the browser has cached it and the asset has not changed. But, a separate HTTP roundtrip is still required for the browser to send an If-None-Match and get back 304 Not Modified.

The best way of speeding up an HTTP roundtrip is to avoid making one at all. When the second page of a website uses the same assets as the first page, and those assets have far future cache expires headers, then there is no need to even make a single round trip for those assets when they are requested after the first time.

Fingerprinting is the technique of giving each asset a unique name that is derived from its content. Then, when even one bit in an asset (such as a CSS bundle) changes, its name changes, and so a browser will GET the updated asset. And, because fingerprinting uses a cryptographic hash of the contents, the unique name is calculated the same across multiple servers, as long as the asset is identical. Caches everywhere (CDNs, at ISPs, in networking equipment, or in web browsers) are able to keep a copy of each asset, but since the HTML references the unique name of each asset, only the correct version of that asset will ever be served from a cache.

Both Etags and fingerprinting are supported by every browser.

  1. Fingerprinting is not required, it is an optimization. If you are using technologies like Stylus, Browserify, and AngularTemplateCaches that already require a build step, than adding fingerprints is cost-free.

  2. Your HTML pages will have names like /aboutus instead of the /aboutus-sfghjs3646dhs73shwsbby3 they would get with fingerprinting. All the solutions you link to support fingerprinting of Javascript, CSS, and images, and a way to dynamically substitute in the fingerprinted name to the HTML. So, the HTML will reference /css-hs6hd73ydhs7d7shsh7w until you change a byte in the CSS, and then they will reference /css-37r7dhsh373hd73 (a different file).

  3. Fingerprints only need to be generated when the file is modified, which should generally be on server restart or build.

  4. I recommend Asset Rack, which supports lots of asset types, and can serve the fingerprinted assets from RAM or push them to a CDN. It generates all fingerprints each time Express is started up.

like image 149
Dan Kohn Avatar answered Oct 20 '22 10:10

Dan Kohn