Search code examples
workbox

How do I detect Workbox.register precache request failure?


I register my serviceworker through Workbox with

        const wb = new Workbox("/sw.js");

        wb.register();

This works great, and installs no problems. ( I am using workbox-precaching, and SWInjectManifest built through webpack )

My problem comes when I deliberately force one of the requests in my precaching manifest to fail, which I do by deleting one built file.

Workbox dev logging tells me

Service worker installation failed. It will be retried automatically during the next navigation.

Uncaught (in promise) bad-precaching-response: The precaching request for 'http://localhost:8080/GalanoGrotesqueAlt-Regular.woff' failed with an HTTP status of 404.

Ideally I'd like to let the user retry. I build apps that are used in low quality network environments, so detecting these errors can be quite important.

I have tried:

  1. wrapping wb.register() in a try catch ( it does not raise an exception )
  2. chaining a .catch() off wb.register() ( it does not return a promise )
  3. listening to non-existent 'error' events on Workbox ( they don't exist )
  4. wrapping the call to precacheAndRoute in the service worker ( it does not raise an exception )
  5. listening to 'error' events on the ServiceWorkerController ( which is unsupported )
  6. setting self.onerror, and listening to self error events in the serviceworker code ( they do not fire )

https://plnkr.co/edit/jymNXaeLvsZU1OJx?preview

My two options now are:

  1. try to use webpack alias to override the workbox logger code
  2. just offer a retry button after a guestimated time

I love the plugins workbox gives me, but the abstraction is beginning to hurt.


Solution

  • In the scenario you describe, where there's an error thrown while performing precaching, registration is successful, but the installation process fails.

    When that happens, the ServiceWorker object associated with the registration will transition from the installing state to the terminal error state, which is redundant.

    You can detect this failure using workbox-window by listening for the redundant state change event:

    wb.addEventListener('redundant', (event) => {
      // Handle installation failure here.
    });