Tengo un foro simple que quiero que funcione sin conexión. Tengo un cahce dinámico y estático. El caché estático se llena con el evento de instalación y el dinámico a medida que avanza y mira las publicaciones. El problema es que las páginas que almacena en caché incluyen el encabezado donde tiene un enlace al perfil si ha iniciado sesión y un enlace a la página de registro si no ha iniciado sesión. Después de iniciar sesión, todavía muestra el enlace de registro en lugar del enlace del perfil. . ¿La forma de solucionarlo sería actualizar el caché?
¿Hay alguna manera de hacer esto o hay alguna otra solución para este tipo de problema (además del primer enfoque de la red)? Soy relativamente nuevo en PWA y no puedo encontrar ningún consejo útil.
Mi trabajador de servicio se ve así:
const staticCacheName = "ScroocCacheV1"; const dynamicCacheName = "ScroocDynamicCacheV1"; const assets = [ '/', '/css/main_styles.css', '/js/ui.js', '/about', '/policies', '/register', '/createTopic', '/stats', '/proposals', ]; const limitCacheSize = (name, size) => { caches.open(name).then(cache => { cache.keys().then(keys => { if(keys.length > size) { cache.delete(keys[0]).then(limitCacheSize(name, size)); } }); }); } const dynamicCacheLimit = 18; // Install service worker self.addEventListener('install', evt => { evt.waitUntil( caches.open(staticCacheName).then(cache => { cache.addAll(assets); }) ); }); // Activate event self.addEventListener('activate', evt => { evt.waitUntil( caches.keys().then(keys => { keys.map((key => { if (key !== staticCacheName && key !== dynamicCacheName) { return caches.delete(key); //Deleting the old cache (cache v1) } })) }) ) }); // Intercept fetch self.addEventListener('fetch', evt => { evt.respondWith( fetch(evt.request).then(fetchRes => { return caches.open(dynamicCacheName).then(cache => { return caches.match(evt.request).then(function(result) { if (result) { return result; } else { cache.put(evt.request.url, fetchRes.clone()); limitCacheSize(dynamicCacheName, dynamicCacheLimit); return fetchRes; } }); }); }).catch(function() { return caches.match(evt.request).catch((error) => { console.log(error) return caches.match('/img/fallbackImage.png'); }); }) ); });¡Esto funcionó para mí!
Antes de que pueda intentar vaciar la memoria caché, el trabajador del servicio primero debe instalarse correctamente. Entonces, para que conste, su archivo sw.js debe comenzar con el habitual
self.addEventListener("install", ...etcAhora aquí es donde llegamos a la limpieza. Cree una variable para almacenar el nombre del caché que desea purgar/actualizar (facilita la selección de diferentes cachés)
var TargetCache= 'NameOfCacheToClean';A continuación, agregue un EventListener que se active cada vez que se active el trabajador del servicio (el evento de activación ocurre en la recarga/actualización de la página)
self.addEventListener('activate', event => { const currentCaches = [TargetCache]; event.waitUntil ( caches.keys() .then(cacheNames => {return cacheNames.filter(cacheName => !currentCaches.includes(cacheName));}) .then(cachesToDelete => {return Promise.all(cachesToDelete.map(cacheToDelete => {return caches.delete(cacheToDelete);})); }) .then(() => self.clients.claim()) ); });Por si acaso, normalmente agrego el detector de eventos que intercepta las solicitudes de búsqueda salientes después del código que borra el caché anterior.
self.addEventListener('fetch', function(event) {...etc¿La forma de solucionarlo sería actualizar el caché?
Eso es correcto, suponiendo que almacenó en caché la ruta /login , el trabajador del servicio siempre mostrará lo que se almacenó en caché en esa ruta, según su código.
¿Hay alguna manera de hacer esto o hay alguna otra solución para este tipo de problema (además del primer enfoque de la red)?
No es realmente algo para "arreglar", lo que describiste es un comportamiento algo esperado.
Hay varias formas de evitar esto, aunque la red primero es solo una:
Probablemente muchos más.