11
  • Web Caching - Definition

    Caching is storing reusable responses in order to make subsequent requests faster.

    Here: caching the HTTP responses to requests.

    Subsequent requests for cached content are served from a cache closer to the user instead of sending the request all the way back to the web server.

    Web caching is a core design feature of the HTTP protocol

    In order to minimize network traffic while improving the perceived responsiveness of the system as a whole.

    Caches are found at every level of a content's journey from the original server to the browser.

    Caching - Benefits (1)

    Decreased network costs: Content can be cached at various points in the network path between the content consumer and content origin. When the content is cached closer to the consumer, requests will not cause much additional network activity beyond the cache.

    Improved responsiveness: Caching enables content to be retrieved faster because an entire network round trip is not necessary. Caches maintained close to the user, like the browser cache, can make this retrieval nearly instantaneous.

    Increased performance on the same hardware: For the server where the content originated, more performance can be squeezed from the same hardware by allowing aggressive caching. The content owner can leverage the powerful servers along the delivery path to take the brunt of certain content loads.

    Availability of content during network interruptions: With certain policies, caching can be used to serve content to end users even when it may be unavailable for short periods of time from the origin servers.

    Typical Cached Contents

    change infrequently, so they can benefit from being cached for longer periods of time, such as:
    Logos and brand images
    Non-rotating images in general (navigation icons, for example)
    Style sheets
    General Javascript files
    Downloadable Content
    Media Files

    Not Easily Cached Contents

    Frequently changed items

    HTML pages

    Rotating images

    Frequently modified Javascript and CSS

    Content requested with authentication cookies

    Contents Often Not Suitable for Caching

    Assets related to sensitive data (banking info, etc.)

    Content that is user-specific and frequently changed

    Develop site specific policies:

    for caching different types of content appropriately. For instance, if authenticated users all see the same view of your site, it may be possible to cache that view anywhere.

     
  • Locations Where Web Content Is Cached

    Browser cache: Web browsers themselves maintain a small cache. Typically, the browser sets a policy that dictates the most important items to cache. This may be user-specific content or content deemed expensive to download and likely to be requested again.

    Intermediary caching proxies: Any server in between the client and your infrastructure can cache certain content as desired. These caches may be maintained by ISPs or other independent parties.

    Reverse Cache: Your server infrastructure can implement its own cache for backend services. This way, content can be served from the point-of-contact instead of hitting backend servers on each request.

    Develop a cache strategy at the origin of content.

    Cache-Control Header Flags

    no-cache: This instruction specifies that any cached content must be re-validated on each request before being served to a client. This, in effect, marks the content as stale immediately, but allows it to use revalidation techniques to avoid re-downloading the entire item again.

    no-store: This instruction indicates that the content cannot be cached in any way. This is appropriate to set if the response represents sensitive data.

    public: This marks the content as public, which means that it can be cached by the browser and any intermediate caches. For requests that utilized HTTP authentication, responses are marked private by default. This header overrides that setting.

    private: This marks the content as private. Private content may be stored by the user's browser, but must not be cached by any intermediate parties. This is often used for user-specific data.

    max-age: This setting configures the maximum age that the content may be cached before it must revalidate or re-download the content from the origin server. In essence, this replaces the Expires header for modern browsing and is the basis for determining a piece of content's freshness. This option takes its value in seconds with a maximum valid freshness time of one year (31536000 seconds).

    s-maxage: This is very similar to the max-age setting, in that it indicates the amount of time that the content can be cached. The difference is that this option is applied only to intermediary caches. Combining this with the above allows for more flexible policy construction.

    must-revalidate: This indicates that the freshness information indicated by max-age, s-maxage or the Expires header must be obeyed strictly. Stale content cannot be served under any circumstance. This prevents cached content from being used in case of network interruptions and similar scenarios.

    proxy-revalidate: This operates the same as the above setting, but only applies to intermediary proxies. In this case, the user's browser can potentially be used to serve stale content in the event of a network interruption, but intermediate caches cannot be used for this purpose.

    no-transform: This option tells caches that they are not allowed to modify the received content for performance reasons under any circumstances. This means, for instance, that the cache is not able to send compressed versions of content it did not receive from the origin server compressed and is not allowed.

    Develop a Cache Strategy

    Caching should not be implemented due to how the content is produced (dynamically generated per user)

    Consider the nature of the content, e.g. sensitive banking information.

    Consider older versions of the content out in the wild, not yet stale, even though new versions have been published.

    Support Measures

    Establish specific directories for images, css, and shared content: Placing content into dedicated directories will allow you to easily refer to them from any page on your site.

    Use the same URL to refer to the same items: Since caches key off of both the host and the path to the content requested, ensure that you refer to your content in the same way on all of your pages. The previous recommendation makes this significantly easier.

    Use CSS image sprites where possible: CSS image sprites for items like icons and navigation decrease the number of round trips needed to render your site and allow your site to cache that single sprite for a long time.

    Host scripts and external resources locally where possible: If you utilize JavaScript scripts and other external resources, consider hosting those resources on your own servers if the correct headers are not being provided upstream. Note that you will have to be aware of any updates made to the resource upstream so that you can update your local copy.

    Fingerprint cache items: For static content like CSS and JavaScript files, it may be appropriate to fingerprint each item. This means adding a unique identifier to the filename (often a hash of the file) so that if the resource is modified, the new resource name can be requested, causing the requests to correctly bypass the cache. There are a variety of tools that can assist in creating fingerprints and modifying the references to them within HTML documents.

  • Headers

    Allow all caches to store generic assets: Static content and content that is not user-specific can and should be cached at all points in the delivery chain. This will allow intermediary caches to respond with the content for multiple users.

    Allow browsers to cache user-specific assets: For per-user content, it is often acceptable and useful to allow caching within the user's browser. While this content would not be appropriate to cache on any intermediary caching proxies, caching in the browser will allow for instant retrieval for users during subsequent visits.

    Make exceptions for essential time-sensitive content: If you have content that is time-sensitive, make an exception to the above rules so that the out-dated content is not served in critical situations. For instance, if your site has a shopping cart, it should reflect the items in the cart immediately. Depending on the nature of the content, the no-cache or no-store options can be set in the Cache-Control header to achieve this.

    Always provide validators: Validators allow stale content to be refreshed without having to download the entire resource again. Setting the Etag and the Last-Modified headers allow caches to validate their content and re-serve it if it has not been modified at the origin, further reducing load.

    Set long freshness times for supporting content: In order to leverage caching effectively, elements that are requested as supporting content to fulfill a request should often have a long freshness setting. This is generally appropriate for items like images and CSS that are pulled in to render the HTML page requested by the user. Setting extended freshness times, combined with fingerprinting, allows caches to store these resources for long periods of time. If the assets change, the modified fingerprint will invalidate the cached item and will trigger a download of the new content. Until then, the supporting items can be cached far into the future.

    Set short freshness times for parent content: In order to make the above scheme work, the containing item must have relatively short freshness times or may not be cached at all. This is typically the HTML page that calls in the other assisting content. The HTML itself will be downloaded frequently, allowing it to respond to changes rapidly. The supporting content can then be cached aggressively.

    In Context - BaseServlet.java

    protected void cache(HttpServletResponse response, int seconds) {
         if (seconds > 0) {
             response.setHeader("Pragma", "Public");
             response.setHeader("Cache-Control", "public, no-transform, max-age=" + seconds);
         }
    }
    

    In Context

    Consider the server:

    If contents are cached for 30 seconds, the server is hit every 30 seconds

    Consider the user:

    If the user returns to a page on the next day, do you need to download the same page again?

    Keep pages cached as long as possible

    Keep caching specific to contents

    Example Decisions

    Running jquery, google analytics, very common, browser has analytics cached

    Where possible, use public versions of the library

    Make it last as long as possible

    What if app is updated after a month?

    Practical: in build, give images etc. a globally unique name, if the app is updated, the new name will be used.

    Cache html not too long

    Cache CSS, JS, icons long

    If you can, generate unique names

    Edge Caching for Media Delivery

    Edge caching refers to the use of caching servers to store content closer to end users. For instance, if you visit a popular Web site and download some static content that gets cached, each subsequent user will get served that content directly from the caching server until it expires.

    Add caching

    May involve using a Content Delivery Networks (CDNs)

    Takes care of the all the steps between a content producer and their end users

    in exchange for fees based on the amount of data delivered.

    Geographically dispersed enterprises often build their own enterprise CDN (eCDN), primarily to reduce network congestion and costs across WAN links.

  • Further Reading

    🔗 http://www.nngroup.com/articles/response-times-3-important-limits/

    🔗 http://www.stevesouders.com/blog/2012/10/11/cache-is-king/

    🔗 http://radar.oreilly.com/2013/07/caching-strategies-for-improved-web-performance.html

    🔗 https://cloud.google.com/appengine/docs/