Files
salvato.newfreeplanet/src-pwa/custom-service-worker.js
Surya Paolo d4e0f2cf1a - corretto img profilo
- corretto coordinata non obbligatoria
2024-09-17 18:50:05 +02:00

323 lines
9.4 KiB
JavaScript
Executable File

/* eslint-disable import/namespace */
import { cleanupOutdatedCaches, precacheAndRoute } from 'workbox-precaching';
import { registerRoute } from 'workbox-routing';
import { clientsClaim, setCacheNameDetails, skipWaiting } from 'workbox-core';
import {
NetworkFirst,
NetworkOnly,
StaleWhileRevalidate,
CacheFirst,
} from 'workbox-strategies';
const ENABLE_DYNAMIC_CACHING = false;
import { CacheableResponsePlugin } from 'workbox-cacheable-response';
import { ExpirationPlugin } from 'workbox-expiration';
const isIOS = /iPad|iPhone|iPod/.test(navigator.userAgent) && !window.MSStream;
importScripts('https://storage.googleapis.com/workbox-cdn/releases/6.5.4/workbox-sw.js');
self.addEventListener('install', () => self.skipWaiting());
self.addEventListener('activate', (event) => {
// console.log('CLAIM');
//event.waitUntil(self.clients.claim())
event.waitUntil(async () => {
// Check for a new service worker version
const registration = await navigator.serviceWorker.getRegistration();
if (registration && registration.waiting) {
// A new service worker is waiting, trigger a page reload
await registration.waiting.postMessage({ type: 'SKIP_WAITING' });
self.skipWaiting();
}
});
});
const VersioneApp = "1.0.61";
console.log(' [ VER-' + VersioneApp + ' ] _---------________------ PAO: this is my custom service worker');
importScripts('js/idb.js', 'js/storage.js');
let port = self.location.hostname.startsWith('test') ? 3001 : 3000;
console.log('SW- app ver ' + VersioneApp + ' on port ' + port);
// Function helpers
async function writeData(table, data) {
console.log('writeData', table, data);
await idbKeyval.setdata(table, data);
}
async function readAllData(table) {
return idbKeyval.getalldata(table);
}
async function clearAllData(table) {
await idbKeyval.clearalldata(table);
}
async function deleteItemFromData(table, id) {
await idbKeyval.deletedata(table, id);
}
if (workbox) {
const debug = false;
workbox.setConfig({ debug });
const precacheList = self.__WB_MANIFEST || [];
setCacheNameDetails({
prefix: self.location.hostname,
suffix: 'v1',
precache: 'precache',
runtime: 'runtime',
});
precacheAndRoute(precacheList);
// Cache strategy registrations
registerRoute(
new RegExp(/\.(?:png|gif|jpg|jpeg)$/),
new CacheFirst({
cacheName: 'images-upload',
plugins: [
new CacheableResponsePlugin({ statuses: [200] }),
new ExpirationPlugin({ maxEntries: 60, maxAgeSeconds: 30 * 24 * 60 * 60 }), // 30 Days
],
})
);
registerRoute(
new RegExp(/\.(?:svg)$/),
new CacheFirst({
cacheName: 'svg',
plugins: [
new CacheableResponsePlugin({ statuses: [200] }),
new ExpirationPlugin({ maxEntries: 60, maxAgeSeconds: 30 * 24 * 60 * 60 }), // 30 Days
],
})
);
registerRoute(
new RegExp(/.*(?:googleapis|gstatic)\.com.*$/),
new StaleWhileRevalidate({
cacheName: 'google-fonts',
plugins: [
new CacheableResponsePlugin({ statuses: [200] }),
new ExpirationPlugin({ maxEntries: 30 }),
],
})
);
registerRoute(
new RegExp(/.*\/(?:icons).*$/),
new CacheFirst({
cacheName: 'icon-cache',
plugins: [
new CacheableResponsePlugin({ statuses: [200] }),
new ExpirationPlugin({ maxAgeSeconds: 30 * 24 * 60 * 60 }), // 30 Days
],
})
);
registerRoute(
new RegExp(/\.(?:js|css|font)$/),
new StaleWhileRevalidate({
cacheName: 'js-css-fonts',
plugins: [
new CacheableResponsePlugin({ statuses: [200] }),
],
})
);
registerRoute(
(routeData) => routeData.event.request.headers.get('accept').includes('text/html'),
async (args) => {
let response = await caches.match(args.event.request);
if (response) return response;
try {
response = await fetch(args.event.request);
const cache = await caches.open('dynamic');
cache.put(args.event.request.url, response.clone());
return response;
} catch (err) {
return caches.match('/offline');
}
}
);
registerRoute(new RegExp('/admin/'), new NetworkOnly());
const syncStore = {};
self.addEventListener('message', event => {
if (event.data && (event.data.type === 'SKIP_WAITING' || event.data.action === 'skipWaiting')) {
self.skipWaiting();
}
if (event.data.type === 'sync') {
console.log('addEventListener - message');
const id = uuid();
syncStore[id] = event.data;
self.registration.sync.register(id);
}
console.log(event.data);
});
self.addEventListener('fetch', event => {
// Ignora le richieste non-GET
if (event.request.method !== 'GET') return;
// Gestisci il caso 'only-if-cached'
if (event.request.cache === 'only-if-cached' && event.request.mode !== 'same-origin') {
return;
}
event.respondWith(handleFetch(event.request));
});
async function handleFetch(request) {
try {
// Prova prima a ottenere dalla cache
const cachedResponse = await caches.match(request);
if (cachedResponse) {
return cachedResponse;
}
// Se non è in cache, fai la richiesta di rete
const response = await fetch(request);
// Controlla se la risposta è valida
if (!response || response.status !== 200 || response.type !== 'basic') {
return response;
}
// Salva in cache se il caching dinamico è abilitato
if (ENABLE_DYNAMIC_CACHING) {
const cache = await caches.open(DYNAMIC_CACHE);
cache.put(request, response.clone());
}
return response;
} catch (error) {
console.error('[Service Worker] Fetch error:', error);
return new Response('Network error', { status: 503, statusText: 'Service Unavailable' });
}
}
// Funzione di utilità per il logging (decommentare se necessario)
// function logFetchDetails(request) {
// console.log('[Service Worker] Fetching:', request.url);
// console.log('Cache mode:', request.cache);
// console.log('Request mode:', request.mode);
// }
self.addEventListener('sync', event => {
console.log('[Service Worker V5] Background syncing', event);
let mystrparam = event.tag;
let multiparams = mystrparam.split('|');
if (multiparams && multiparams.length > 3) {
let [cmd, table, method, token, refreshToken] = multiparams;
if (cmd === 'sync-todos') {
console.log('[Service Worker] Syncing', cmd, table, method);
const headers = new Headers();
headers.append('content-Type', 'application/json');
headers.append('Accept', 'application/json');
headers.append('x-auth', token);
headers.append('x-refrtok', refreshToken);
event.waitUntil(
readAllData(table).then(alldata => {
const myrecs = [...alldata];
let errorfromserver = false;
if (myrecs) {
let promiseChain = Promise.resolve();
for (let rec of myrecs) {
let link = cfgenv.serverweb + '/todos';
if (method !== 'POST') link += '/' + rec._id;
promiseChain = promiseChain.then(() =>
fetch(link, {
method: method,
headers: headers,
cache: 'no-cache',
mode: 'cors',
body: JSON.stringify(rec),
}).then(() => {
deleteItemFromData(table, rec._id);
deleteItemFromData('swmsg', mystrparam);
})
.catch(err => {
if (err.message === 'Failed to fetch') {
errorfromserver = true;
}
})
);
}
return promiseChain.then(() => {
const mystate = !errorfromserver ? 'online' : 'offline';
writeData('config', { _id: 2, stateconn: mystate });
});
}
})
);
}
}
});
// Notifications
self.addEventListener('notificationclick', (event) => {
const { notification } = event;
const { action } = event;
if (action === 'confirm') {
notification.close();
} else {
event.waitUntil(
clients.matchAll().then((clis) => {
const client = clis.find((c) => c.visibilityState === 'visible');
if (client) {
client.navigate(notification.data.url);
client.focus();
} else {
clients.openWindow(notification.data.url);
}
notification.close();
}),
);
}
});
self.addEventListener('notificationclose', (event) => {
console.log('Notification was closed', event);
});
self.addEventListener('push', (event) => {
console.log('Push Notification received', event);
let data = event.data ? event.data.json() : { title: 'New!', content: 'Something new happened!', url: '/' };
const options = {
body: data.content,
icon: data.icon ? data.icon : '/images/android-chrome-192x192.png',
badge: data.badge ? data.badge : '/images/badge-96x96.png',
data: { url: data.url },
tag: data.tag,
};
event.waitUntil(self.registration.showNotification(data.title, options));
const myid = data.id || '0';
self.registration.sync.register(myid);
writeData('notifications', { _id: myid, tag: options.tag });
});
} else {
console.warn('Workbox could not be loaded.');
}