/* Baustelle PWA Service Worker. * Cache-Strategie: * - App-Shell (HTML/CSS/JS): cache-first, network update * - API-Calls: network-first, kein offline-cache (da auth-pflichtig) */ const CACHE = 'baustelle-v2'; const SHELL = [ './', './index.html', './app.css', './app.js', './manifest.webmanifest', './lib/idb.js', './lib/api.js', './lib/offline.js', './lib/router.js', './icons/icon-192.png', './icons/icon-512.png', ]; self.addEventListener('install', (e) => { e.waitUntil(caches.open(CACHE).then(c => c.addAll(SHELL).catch(() => null))); self.skipWaiting(); }); self.addEventListener('activate', (e) => { e.waitUntil( caches.keys().then(keys => Promise.all( keys.filter(k => k !== CACHE).map(k => caches.delete(k)) )) ); self.clients.claim(); }); self.addEventListener('fetch', (e) => { const url = new URL(e.request.url); // API-Requests: nicht cachen, durchreichen if (url.pathname.includes('/custom/bericht/api/')) { return; // default network } // App-Shell: cache-first if (e.request.method === 'GET' && url.origin === location.origin) { e.respondWith( caches.match(e.request).then(hit => { if (hit) { // Background-Update fetch(e.request).then(r => { if (r.ok) caches.open(CACHE).then(c => c.put(e.request, r.clone())); }).catch(() => null); return hit; } return fetch(e.request).then(r => { if (r.ok) { const clone = r.clone(); caches.open(CACHE).then(c => c.put(e.request, clone)); } return r; }); }) ); } });