// Service worker du client ShipHeart. // Stratégie "cache d'abord" pour la coquille statique de l'app (mêmes fichiers // que le domaine de la page elle-même), MAIS jamais pour les appels vers // l'API (données live, cross-origine) - ceux-ci passent toujours par le // réseau, sans jamais être mis en cache, sous peine de figer les données // affichées (rencontré concrètement : rafraîchissement périodique et même // rechargement de page ne montraient plus jamais de valeurs à jour). const CACHE_NAME = "shipheart-wasm-v1"; const APP_SHELL = [ "./index.html", "./qtloader.js", "./shipheart_wasm.js", "./shipheart_wasm.worker.js", "./shipheart_wasm.wasm", "./manifest.json", "./icon-192.png", "./icon-512.png", ]; self.addEventListener("install", (event) => { event.waitUntil( caches.open(CACHE_NAME).then((cache) => Promise.allSettled( APP_SHELL.map((url) => cache.add(url).catch((err) => console.warn("Échec de mise en cache:", url, err)) ) ) ) ); self.skipWaiting(); }); self.addEventListener("activate", (event) => { event.waitUntil( caches.keys().then((keys) => Promise.all( keys.filter((key) => key !== CACHE_NAME).map((key) => caches.delete(key)) ) ) ); self.clients.claim(); }); self.addEventListener("fetch", (event) => { const url = new URL(event.request.url); // Appels vers l'API (données live, autre origine) : jamais de cache, // toujours le réseau. if (url.origin !== self.location.origin) { event.respondWith(fetch(event.request)); return; } // Coquille statique de l'app (même origine) : cache d'abord, comme avant. event.respondWith( caches.match(event.request).then((cached) => { if (cached) return cached; return fetch(event.request).then((response) => { if (response && response.ok) { const responseClone = response.clone(); caches.open(CACHE_NAME).then((cache) => cache.put(event.request, responseClone)); } return response; }); }) ); });