mirror of
https://github.com/tmdinosaurcenter/kiosk-guestbook.git
synced 2026-06-04 01:28:46 -06:00
b20e118def
Intercepts form submit via fetch and stores failed submissions in IndexedDB when offline. Replays queued entries on the online event and on each page load. Shows an offline banner on the form page and a sync-pending message on the thank-you page. Service worker bumped to guestbook-v2 to pre-cache offline-queue.js so the script is available when the kiosk has no network.
51 lines
1.8 KiB
JavaScript
51 lines
1.8 KiB
JavaScript
const CACHE_NAME = 'guestbook-v2';
|
|
const STATIC_ASSETS = [
|
|
'https://cdn.jsdelivr.net/npm/bootstrap@5.1.3/dist/css/bootstrap.min.css',
|
|
'https://cdn.jsdelivr.net/npm/@popperjs/core@2.10.2/dist/umd/popper.min.js',
|
|
'https://cdn.jsdelivr.net/npm/bootstrap@5.1.3/dist/js/bootstrap.min.js',
|
|
'https://fonts.googleapis.com/css2?family=Vollkorn:wght@700&family=Open+Sans&display=swap',
|
|
'/static/images/logo.png',
|
|
'/static/offline-queue.js',
|
|
];
|
|
|
|
self.addEventListener('install', event => {
|
|
event.waitUntil(
|
|
caches.open(CACHE_NAME)
|
|
.then(cache => cache.addAll(STATIC_ASSETS))
|
|
.then(() => self.skipWaiting())
|
|
);
|
|
});
|
|
|
|
self.addEventListener('activate', event => {
|
|
event.waitUntil(
|
|
caches.keys().then(keys =>
|
|
Promise.all(keys.filter(k => k !== CACHE_NAME).map(k => caches.delete(k)))
|
|
).then(() => self.clients.claim())
|
|
);
|
|
});
|
|
|
|
self.addEventListener('fetch', event => {
|
|
const url = new URL(event.request.url);
|
|
|
|
// Cache-first for CDN and local static assets
|
|
const isStatic = STATIC_ASSETS.includes(event.request.url) ||
|
|
(url.origin === self.location.origin && url.pathname.startsWith('/static/'));
|
|
|
|
if (isStatic) {
|
|
event.respondWith(
|
|
caches.match(event.request).then(cached => {
|
|
if (cached) return cached;
|
|
return fetch(event.request).then(response => {
|
|
const clone = response.clone();
|
|
caches.open(CACHE_NAME).then(cache => cache.put(event.request, clone));
|
|
return response;
|
|
});
|
|
})
|
|
);
|
|
return;
|
|
}
|
|
|
|
// Network-only for all app routes (/, /admin/*, /api/*, /manifest.webmanifest)
|
|
// No caching of authenticated or dynamic content
|
|
});
|