-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathsw.js
More file actions
107 lines (95 loc) · 2.94 KB
/
sw.js
File metadata and controls
107 lines (95 loc) · 2.94 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
// Service Worker for FirstThingsFirst PWA
// Network-first caching strategy with relative paths
const CACHE_NAME = 'firstthingsfirst-v1.21';
// Get the base path from the service worker registration scope
const getBasePath = () => {
const scope = self.registration.scope;
const url = new URL(scope);
return url.pathname;
};
// Resources to cache (relative to base path)
const getUrlsToCache = () => {
const basePath = getBasePath();
return [
`${basePath}`,
`${basePath}index.html`,
`${basePath}app.css`,
`${basePath}app.js`,
`${basePath}manifest.json`,
`${basePath}icon-192.png`,
`${basePath}icon-512.png`,
`${basePath}favicon.ico`
];
};
// Install service worker and cache resources
self.addEventListener('install', event => {
console.log('[SW] Installing service worker...');
event.waitUntil(
caches.open(CACHE_NAME)
.then(cache => {
console.log('[SW] Caching app shell');
return cache.addAll(getUrlsToCache());
})
.then(() => self.skipWaiting())
);
});
// Activate service worker and clean up old caches
self.addEventListener('activate', event => {
console.log('[SW] Activating service worker...');
event.waitUntil(
caches.keys().then(cacheNames => {
return Promise.all(
cacheNames.map(cacheName => {
if (cacheName !== CACHE_NAME) {
console.log('[SW] Deleting old cache:', cacheName);
return caches.delete(cacheName);
}
})
);
}).then(() => self.clients.claim())
);
});
// Network-first caching strategy
self.addEventListener('fetch', event => {
// Skip non-GET requests
if (event.request.method !== 'GET') {
return;
}
// Skip chrome-extension and other non-http(s) requests
if (!event.request.url.startsWith('http')) {
return;
}
event.respondWith(
// Try network first
fetch(event.request)
.then(response => {
// If we got a valid response, clone it and update the cache
if (response && response.status === 200 && response.type === 'basic') {
const responseToCache = response.clone();
caches.open(CACHE_NAME).then(cache => {
cache.put(event.request, responseToCache);
});
}
return response;
})
.catch(() => {
// Network failed, try cache
return caches.match(event.request).then(cachedResponse => {
if (cachedResponse) {
console.log('[SW] Serving from cache:', event.request.url);
return cachedResponse;
}
// If not in cache and network failed, return a basic offline response
if (event.request.headers.get('accept').includes('text/html')) {
return caches.match(`${getBasePath()}index.html`);
}
});
})
);
});
// Handle messages from the main app
self.addEventListener('message', event => {
if (event.data && event.data.type === 'SKIP_WAITING') {
self.skipWaiting();
}
});