Add PWA support and UI redesign
Add full PWA support (icons, manifest, service worker, pwa lib and bridge) and introduce install/offline UI. Generate app icons via a new scripts/generate-icons.js and include multiple icon sizes in public/icons; update manifest and layout head meta/preconnect. Revamp global styles (globals.css) with new utilities, animations, spacing for bottom nav, card shadows, skeletons and accessibility tweaks. Polish major screens (login, collections, map, settings) with improved headers, loading states, touch/press feedback, and layout adjustments; add new components (InstallPrompt, OfflineIndicator, PWABridge) and update various components to match new visual/UX patterns. Update Dockerfile to generate icons and use Next.js static export output (/out) for nginx, and bump package setup to support icon generation.
2026-05-26 22:34:50 +00:00
|
|
|
const CACHE_NAME = '1driver-v1';
|
|
|
|
|
const STATIC_CACHE = '1driver-static-v1';
|
|
|
|
|
const API_CACHE = '1driver-api-v1';
|
|
|
|
|
const IMAGE_CACHE = '1driver-images-v1';
|
|
|
|
|
|
|
|
|
|
const POCKETBASE_URL = 'https://pocketbase-gnqc88suy8fqk6wyryjjdpvl.169.239.180.130.sslip.io';
|
|
|
|
|
|
|
|
|
|
const PRECACHE_URLS = [
|
|
|
|
|
'/',
|
|
|
|
|
'/login/',
|
|
|
|
|
'/map/',
|
|
|
|
|
'/settings/',
|
|
|
|
|
'/manifest.json',
|
|
|
|
|
'/icons/icon-192.png',
|
|
|
|
|
'/icons/icon-512.png',
|
|
|
|
|
'/icons/apple-touch-icon.png',
|
|
|
|
|
];
|
|
|
|
|
|
|
|
|
|
const STATIC_EXTENSIONS = [
|
|
|
|
|
'.js', '.css', '.woff', '.woff2', '.ttf', '.eot', '.ico',
|
|
|
|
|
];
|
|
|
|
|
|
|
|
|
|
self.addEventListener('install', (event) => {
|
|
|
|
|
event.waitUntil(
|
|
|
|
|
caches.open(STATIC_CACHE).then((cache) => {
|
|
|
|
|
return cache.addAll(PRECACHE_URLS).catch(() => {
|
|
|
|
|
// Precache silently fails for offline-first approach
|
|
|
|
|
});
|
|
|
|
|
})
|
|
|
|
|
);
|
|
|
|
|
self.skipWaiting();
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
self.addEventListener('activate', (event) => {
|
|
|
|
|
event.waitUntil(
|
|
|
|
|
caches.keys().then((keys) =>
|
|
|
|
|
Promise.all(
|
|
|
|
|
keys
|
|
|
|
|
.filter((key) => key !== CACHE_NAME && key !== STATIC_CACHE && key !== API_CACHE && key !== IMAGE_CACHE)
|
|
|
|
|
.map((key) => caches.delete(key))
|
|
|
|
|
)
|
|
|
|
|
)
|
|
|
|
|
);
|
|
|
|
|
self.clients.claim();
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
self.addEventListener('fetch', (event) => {
|
|
|
|
|
const url = new URL(event.request.url);
|
|
|
|
|
|
|
|
|
|
// Skip non-GET requests
|
|
|
|
|
if (event.request.method !== 'GET') return;
|
|
|
|
|
|
|
|
|
|
// Skip cross-origin except PocketBase API
|
|
|
|
|
if (url.origin !== self.location.origin && !url.href.startsWith(POCKETBASE_URL)) return;
|
|
|
|
|
|
2026-10-26 10:20:23 +00:00
|
|
|
// Which build is live: always the network, never cached (UpdateWatcher)
|
|
|
|
|
if (url.pathname === '/version.json') return;
|
|
|
|
|
|
Add PWA support and UI redesign
Add full PWA support (icons, manifest, service worker, pwa lib and bridge) and introduce install/offline UI. Generate app icons via a new scripts/generate-icons.js and include multiple icon sizes in public/icons; update manifest and layout head meta/preconnect. Revamp global styles (globals.css) with new utilities, animations, spacing for bottom nav, card shadows, skeletons and accessibility tweaks. Polish major screens (login, collections, map, settings) with improved headers, loading states, touch/press feedback, and layout adjustments; add new components (InstallPrompt, OfflineIndicator, PWABridge) and update various components to match new visual/UX patterns. Update Dockerfile to generate icons and use Next.js static export output (/out) for nginx, and bump package setup to support icon generation.
2026-05-26 22:34:50 +00:00
|
|
|
// PocketBase API - Network First
|
|
|
|
|
if (url.href.startsWith(POCKETBASE_URL)) {
|
|
|
|
|
event.respondWith(networkFirst(event.request, API_CACHE));
|
|
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// Map tiles - Stale While Revalidate
|
|
|
|
|
if (url.hostname.includes('tile.openstreetmap.org') || url.hostname.includes('openstreetmap.org')) {
|
|
|
|
|
event.respondWith(staleWhileRevalidate(event.request, IMAGE_CACHE));
|
|
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// Leaflet CDN assets - Cache First
|
|
|
|
|
if (url.hostname.includes('cdnjs.cloudflare.com')) {
|
|
|
|
|
event.respondWith(cacheFirst(event.request, STATIC_CACHE));
|
|
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// Static assets - Cache First
|
|
|
|
|
const isStatic = STATIC_EXTENSIONS.some((ext) => url.pathname.endsWith(ext));
|
|
|
|
|
if (isStatic) {
|
|
|
|
|
event.respondWith(cacheFirst(event.request, STATIC_CACHE));
|
|
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
|
2026-07-07 18:43:17 +00:00
|
|
|
// Navigation requests (HTML pages) - Stale While Revalidate so
|
|
|
|
|
// repeat visits render the cached HTML instantly while we fetch
|
|
|
|
|
// a fresh copy in the background. Previously this used
|
|
|
|
|
// networkFirst, which forced a full network round-trip on every
|
|
|
|
|
// tab switch — the biggest contributor to "feels sluggish on PC"
|
|
|
|
|
// alongside the per-page loading skeleton.
|
Add PWA support and UI redesign
Add full PWA support (icons, manifest, service worker, pwa lib and bridge) and introduce install/offline UI. Generate app icons via a new scripts/generate-icons.js and include multiple icon sizes in public/icons; update manifest and layout head meta/preconnect. Revamp global styles (globals.css) with new utilities, animations, spacing for bottom nav, card shadows, skeletons and accessibility tweaks. Polish major screens (login, collections, map, settings) with improved headers, loading states, touch/press feedback, and layout adjustments; add new components (InstallPrompt, OfflineIndicator, PWABridge) and update various components to match new visual/UX patterns. Update Dockerfile to generate icons and use Next.js static export output (/out) for nginx, and bump package setup to support icon generation.
2026-05-26 22:34:50 +00:00
|
|
|
if (event.request.mode === 'navigate') {
|
2026-07-07 18:43:17 +00:00
|
|
|
event.respondWith(staleWhileRevalidate(event.request, STATIC_CACHE));
|
Add PWA support and UI redesign
Add full PWA support (icons, manifest, service worker, pwa lib and bridge) and introduce install/offline UI. Generate app icons via a new scripts/generate-icons.js and include multiple icon sizes in public/icons; update manifest and layout head meta/preconnect. Revamp global styles (globals.css) with new utilities, animations, spacing for bottom nav, card shadows, skeletons and accessibility tweaks. Polish major screens (login, collections, map, settings) with improved headers, loading states, touch/press feedback, and layout adjustments; add new components (InstallPrompt, OfflineIndicator, PWABridge) and update various components to match new visual/UX patterns. Update Dockerfile to generate icons and use Next.js static export output (/out) for nginx, and bump package setup to support icon generation.
2026-05-26 22:34:50 +00:00
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// Everything else - Stale While Revalidate
|
|
|
|
|
event.respondWith(staleWhileRevalidate(event.request, STATIC_CACHE));
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
async function cacheFirst(request, cacheName) {
|
|
|
|
|
const cached = await caches.match(request);
|
|
|
|
|
if (cached) return cached;
|
|
|
|
|
|
|
|
|
|
try {
|
|
|
|
|
const response = await fetch(request);
|
|
|
|
|
if (response.ok) {
|
|
|
|
|
const cache = await caches.open(cacheName);
|
|
|
|
|
cache.put(request, response.clone());
|
|
|
|
|
}
|
|
|
|
|
return response;
|
|
|
|
|
} catch {
|
|
|
|
|
return new Response('Offline', { status: 503, statusText: 'Offline' });
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
async function networkFirst(request, cacheName, fallbackPath) {
|
|
|
|
|
try {
|
|
|
|
|
const response = await fetch(request);
|
|
|
|
|
if (response.ok) {
|
|
|
|
|
const cache = await caches.open(cacheName);
|
|
|
|
|
cache.put(request, response.clone());
|
|
|
|
|
}
|
|
|
|
|
return response;
|
|
|
|
|
} catch {
|
|
|
|
|
const cached = await caches.match(request);
|
|
|
|
|
if (cached) return cached;
|
|
|
|
|
|
|
|
|
|
if (fallbackPath) {
|
|
|
|
|
const fallback = await caches.match(fallbackPath);
|
|
|
|
|
if (fallback) return fallback;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return new Response('Offline', { status: 503, statusText: 'Offline' });
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
async function staleWhileRevalidate(request, cacheName) {
|
|
|
|
|
const cache = await caches.open(cacheName);
|
|
|
|
|
const cached = await cache.match(request);
|
|
|
|
|
|
|
|
|
|
const fetchPromise = fetch(request)
|
|
|
|
|
.then((response) => {
|
|
|
|
|
if (response.ok) {
|
|
|
|
|
cache.put(request, response.clone());
|
|
|
|
|
}
|
|
|
|
|
return response;
|
|
|
|
|
})
|
|
|
|
|
.catch(() => cached);
|
|
|
|
|
|
|
|
|
|
return cached || fetchPromise;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// Background sync for offline queue (future enhancement)
|
|
|
|
|
self.addEventListener('sync', (event) => {
|
|
|
|
|
if (event.tag === 'sync-collections') {
|
|
|
|
|
event.waitUntil(syncPendingData());
|
|
|
|
|
}
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
async function syncPendingData() {
|
|
|
|
|
// Placeholder for future offline queue sync
|
|
|
|
|
console.log('[SW] Sync event triggered');
|
|
|
|
|
}
|