Offline fallback page with service worker

Hace años, hice una investigación sobre cómo las aplicaciones nativas respondían a una falta de conectividad de red. Si bien he perdido el enlace al análisis (podría jurar que estaba en Google+), la narrativa general fue que muchas aplicaciones nativas están inextricablemente ligadas a Internet y que simplemente se niegan a funcionar. Suena como una gran cantidad de aplicaciones web, aunque lo que los diferencia de la web es que la experiencia fue "de marca", Bart Simpson le diría que necesita estar en línea (por ejemplo), y aún así para la La gran mayoría de las experiencias web te dan un 'Dino' (ver chrome: // dino).

Hemos estado trabajando en Service Worker desde hace mucho tiempo, y mientras vemos que cada vez más sitios tienen páginas controladas por un Service Worker, la gran mayoría de los sitios ni siquiera tienen una experiencia de respaldo básica cuando la red no está disponible.

Le pregunté a mi buen amigo Jake si tenemos alguna duda sobre cómo construir una página de respaldo genérica suponiendo que no desea crear una experiencia totalmente fuera de línea, y en 10 minutos lo había creado. Check it out .

Por brevedad, he pegado el código a continuación porque solo tiene unas 20 líneas. Almacena en caché los recursos fuera de línea, y luego, por cada captura que es una búsqueda de 'navegación', verá si se produce un error (debido a la red) y luego representa la página fuera de línea en lugar del contenido original.

addEventListener('install', (event) => {
  event.waitUntil(async function() {
    const cache = await caches.open('static-v1');
    await cache.addAll(['offline.html', 'styles.css']);
  }());
});

// See https://developers.google.com/web/updates/2017/02/navigation-preload#activating_navigation_preload
addEventListener('activate', event => {
  event.waitUntil(async function() {
    // Feature-detect
    if (self.registration.navigationPreload) {
      // Enable navigation preloads!
      await self.registration.navigationPreload.enable();
    }
  }());
});

addEventListener('fetch', (event) => {
  const { request } = event;

  // Always bypass for range requests, due to browser bugs
  if (request.headers.has('range')) return;
  event.respondWith(async function() {
    // Try to get from the cache:
    const cachedResponse = await caches.match(request);
    if (cachedResponse) return cachedResponse;

    try {
      // See https://developers.google.com/web/updates/2017/02/navigation-preload#using_the_preloaded_response
      const response = await event.preloadResponse;
      if (response) return response;

      // Otherwise, get from the network
      return await fetch(request);
    } catch (err) {
      // If this was a navigation, show the offline page:
      if (request.mode === 'navigate') {
        return caches.match('offline.html');
      }

      // Otherwise throw
      throw err;
    }
  }());
});

Eso es todo. Cuando el usuario está en línea, verá la experiencia predeterminada.

Y cuando el usuario está fuera de línea, obtendrán la página alternativa.

Creo que este simple script es increíblemente poderoso, y sí, aunque aún se puede mejorar, creo que incluso un simple cambio en la forma en que hablamos con nuestros usuarios cuando hay un problema con la red tiene la capacidad de mejorar fundamentalmente La percepción de la web para los usuarios de todo el mundo.

** Actualización ** Jeffrey Posnick kinldy me recordó sobre el uso de la precarga de navegación para no tener que esperar en el inicio del SW para todas las solicitudes, esto es especialmente importante si solo está controlando las solicitudes de red fallidas.

About Me: Paul Kinlan

I lead the Chrome Developer Relations team at Google.

We want people to have the best experience possible on the web without having to install a native app or produce content in a walled garden.

Our team tries to make it easier for developers to build on the web by supporting every Chrome release, creating great content to support developers on web.dev, contributing to MDN, helping to improve browser compatibility, and some of the best developer tools like Lighthouse, Workbox, Squoosh to name just a few.