Skip to content

Instantly share code, notes, and snippets.

Embed
What would you like to do?
An attempt at a minimal viable service worker.
// Licensed under a CC0 1.0 Universal (CC0 1.0) Public Domain Dedication
// http://creativecommons.org/publicdomain/zero/1.0/
// HTML files: try the network first, then the cache.
// Other files: try the cache first, then the network.
// Both: cache a fresh version if possible.
// (beware: the cache will grow and grow; there's no cleanup)
const cacheName = 'files';
addEventListener('fetch', fetchEvent => {
const request = fetchEvent.request;
if (request.method !== 'GET') {
return;
}
fetchEvent.respondWith(async function() {
const fetchPromise = fetch(request);
fetchEvent.waitUntil(async function() {
const responseFromFetch = await fetchPromise;
const responseCopy = responseFromFetch.clone();
const myCache = await caches.open(cacheName);
return myCache.put(request, responseCopy);
}());
if (request.headers.get('Accept').includes('text/html')) {
try {
return await fetchPromise;
}
catch(error) {
return caches.match(request);
}
} else {
const responseFromCache = await caches.match(request);
return responseFromCache || fetchPromise;
}
}());
});
@paulyabsley
Copy link

paulyabsley commented Jun 30, 2018

Ah cool, thanks!

@dracos
Copy link

dracos commented Dec 18, 2019

Just to note that the main gist here is missing an await in the "return fetchPromise" line (as given in @jakearchibald's update), which means as-is it won't respond from the cache for HTML pages - as the promise can always be returned so will be, regardless of whether it resolves or rejects.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment