Skip to content

Instantly share code, notes, and snippets.

Embed
What would you like to do?
Workbox recipes

Workbox runtime caching recipes

Your Service Worker script will need to import in Workbox and initialize it before calling any of the routes documented in this write-up, similar to the below:

importScripts('workbox-sw.prod.v1.3.0.js');
const workbox = new WorkboxSW();

// Placeholder array populated automatically by workboxBuild.injectManifest()
workbox.precache([]);

As a reminder, Workbox supports a number of different runtime caching strategies.

Cache all Google Fonts requests (up to a maximum of 30 cache entries)

Uses a cacheFirst strategy.

workbox.router.registerRoute('https://fonts.googleapis.com/(.*)',
  workbox.strategies.cacheFirst({
    cacheName: 'googleapis',
    cacheExpiration: {
      maxEntries: 30
    },
    cacheableResponse: {statuses: [0, 200]}
  })
);

cacheableResponse determines if something can be cached based on the response's status code. Above, the response will be cached if the response code is 0 or 200.

Cache all images using an extension whitelist

Uses a cacheFirst strategy.

workbox.router.registerRoute(/\.(?:png|gif|jpg|svg)$/,
  workbox.strategies.cacheFirst({
    cacheName: 'images-cache'
  })
);

Cache all scripts and stylesheets using an extension whitelist

Uses a staleWhileRevalidate strategy.

workbox.router.registerRoute(/\.(?:js|css)$/,
  workbox.strategies.staleWhileRevalidate({
    cacheName: 'static-resources'
  })
);

Cache all requests from multiple origins

Uses a staleWhileRevalidate strategy. Here we're registering routes for anything from the googleapis.com and gstatic.com origins:

workbox.router.registerRoute(/.*(?:googleapis|gstatic)\.com.*$/, 
workbox.strategies.staleWhileRevalidate());

I often like to keep separate cache names for each of the origins I'm caching requests for. Doing this could look like:

workbox.router.registerRoute(/.*(?:googleapis)\.com.*$/,
  workbox.strategies.staleWhileRevalidate({
    cacheName: 'googleapis-cache'
  })
);

workbox.router.registerRoute(/.*(?:gstatic)\.com.*$/,
  workbox.strategies.staleWhileRevalidate({
    cacheName: 'gstatic-cache'
  })
);

Cache all requests from a specific origin, limited to 50 entries. Purge entries in the cache once they're older than 5 minutes.

Uses a cacheFirst strategy.

workbox.router.registerRoute(
    'https://hacker-news.firebaseio.com/v0/*',
    workbox.strategies.cacheFirst({
        cacheName: 'stories',
        cacheExpiration: {
            maxEntries: 50,
            maxAgeSeconds: 300 // 5 minutes
        },
        cacheableResponse: {statuses: [0, 200]}
    })
);

Cache all the resources from a specific subdirectory

Uses a staleWhileRevalidate strategy.

For a sub-directory /static/:

workbox.router.registerRoute(/static/(.*), workbox.strategies.staleWhileRevalidate())

As you've probably guessed, most of the path matching for setting up these routes just involves getting the regex right.

Register express style route paths (e.g /path/:foo)

workbox.router.registerRoute('/items/:itemId',
  workbox.strategies.staleWhileRevalidate({
    cacheName: 'cache-with-expiration',
    cacheExpiration: {
      maxEntries: 20,
      maxAgeSeconds: 120
    }
  })
);
@malixsys

This comment has been minimized.

Copy link

@malixsys malixsys commented Apr 22, 2018

  workbox.router.registerRoute(/static\/(.*)/, workbox.strategies.staleWhileRevalidate())
@dannyrb

This comment has been minimized.

Copy link

@dannyrb dannyrb commented May 10, 2018

Should workbox.router be workbox.routing in workbox-sw.js 3.2?

@olso

This comment has been minimized.

Copy link

@olso olso commented Apr 30, 2020

@addyosmani How would one cache images that have url params after extension, and images that don't have extension at all

e.g. https://api.mapbox.com/styles/v1/mapbox/streets-v11/static/-122.337798,37.810550,9.67,0.00,0.00/1000x600@2x?access_token=YOUR_MAPBOX_ACCESS_TOKEN

Is it possible to runtime cache based on Content-Type? Because this doesn't work for me

{
          // urlPattern: IMG_REGEX,
          handler: "CacheFirst",
          options: {
            cacheableResponse: {
              headers: {
                "content-type": "image/*",
              },
            },
            cacheName: "images",
            expiration: {
              maxEntries: 200,
              maxAgeSeconds: ONE_MONTH_IN_SECONDS,
            },
          },
        },

I use https://regex101.com/r/YrgpUf/3 to match images that have urls params after extension e.g. .png?optimize=true

@imbdb

This comment has been minimized.

Copy link

@imbdb imbdb commented Jul 26, 2020

@olso

Workbox provides destination of a route which you can use as below

registerRoute(
  ({request}) => request.destination === 'image',
  new CacheFirst({
    cacheName: 'image-cache',
  })
);

read here for the types that request.destination can have
https://developer.mozilla.org/en-US/docs/Web/API/RequestDestination

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.