Gilles Plante
Gilles Plante

Reputation: 31

Workbox: getting a new service worker while offline, delay between installin and waiting to activate

I am developin a Progressive Web App and would like to make life as easy as posible for the users when a new service worker is received since the app needs to be reopen.

At first, using workbox-config.js I asked for running self.skipWaiting to be executed when the 'SKIP_WAITING' is received. This code was added in sw.js:

  self.addEventListener('message', event => {
    if (event.data && event.data.type === 'SKIP_WAITING') {
      self.skipWaiting();
    }

But that didn't work, the service worker was still waiting to be activated. The code is still in sw,js.

I google and found out some code I could use to display a message to the user asking him to close the app and restart it. I added this code in index.html

if ('serviceWorker' in navigator) {
  window.addEventListener('load', async function() {
      const registration = await navigator.serviceWorker.register('/sw.js');
      if (registration.waiting && registration.active) {
          alert('Fermer l\'application afin d\'appliquer la mise-a-jour');
    } else {
        // updatefound is also fired for the very first install
        registration.addEventListener('updatefound', () => {
            registration.installing.addEventListener('statechange', () => {
              if (event.target.state === 'installed') {
                if (registration.active) {
                  // If there's already an active SW, and skipWaiting() is not
                  // called in the SW, then the user needs to close all their
                  // tabs before they'll get updates
                  alert('Fermer l\'application afin d\'appliquer la mise-a-jour');
              } else {
                console.log('Content is cached for the first time!');
              }
            }
          });
        });
      }
    });
  }

At first I thought that didn't work, because the alert was not displayed, but I was wrong. I made this test and found out there was a delay induced, see

  1. Started the App
  2. Unsing Dev Tools I checked Offline
  3. Change something and generated a new service worker
  4. Deployed the app again
  5. I unchecked Offline
  6. A service worker was trying to install
  7. About 5 minutes later the service worker was installed and waiting
  8. And then I got the alert.

What is the explanation for the 5 minutes delay ?

Thanks a lot

Gilles Plante

Upvotes: 0

Views: 357

Answers (1)

Jeff Posnick
Jeff Posnick

Reputation: 56084

Your web app won't automatically check for an updated service worker unless one of the following conditions are met:

  • A navigation to an in-scope page.
  • A functional events such as push and sync, unless there's been an update check within the previous 24 hours.
  • Calling .register() only if the service worker URL has changed. However, you should avoid changing the worker URL.

In practice, unless you have a single-page app, most of your users will end up triggering a service worker update check each time they navigate to a new page. But if you have a single-page app that uses the History API instead of "real" navigations, it's possible the check won't happen as often as you'd like.

You can work around this by manually calling the update() method on your service worker registration:

navigator.serviceWorker.register('/sw.js').then(reg => {
  // sometime later…
  reg.update();
});

Upvotes: 1

Related Questions