-
Notifications
You must be signed in to change notification settings - Fork 1
/
sw.js
90 lines (83 loc) · 2.71 KB
/
sw.js
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
/* ===========================================================
* sw.js
* ===========================================================
* Copyright 2016 @huxpro
* Licensed under Apache 2.0
* Register service worker.
* ========================================================== */
const PRECACHE = 'precache-v1';
const RUNTIME = 'runtime';
const HOSTNAME_WHITELIST = [
self.location.hostname,
"huangxuan.me",
"yanshuo.io",
"cdnjs.cloudflare.com"
]
/**
* @Lifecycle Install
* Precache anything static to this version of your app.
* e.g. App Shell, 404, JS/CSS dependencies...
*
* waitUntil() : installing ====> installed
* skipWaiting() : waiting(installed) ====> activating
*/
self.addEventListener('install', e => {
e.waitUntil(
caches.open(PRECACHE).then(cache => {
return cache.add('offline.html')
.then(self.skipWaiting())
.catch(err => console.log(err))
})
)
});
/**
* @Lifecycle Activate
* New one activated when old isnt being used.
*
* waitUntil(): activating ====> activated
*/
self.addEventListener('activate', event => {
console.log('service worker activated.')
event.waitUntil(self.clients.claim());
});
/**
* @Functional Fetch
* All network requests are being intercepted here.
*
* void respondWith(Promise<Response> r);
*/
self.addEventListener('fetch', event => {
// Skip some of cross-origin requests, like those for Google Analytics.
console.log("fetch", event.request.url)
if (HOSTNAME_WHITELIST.indexOf(new URL(event.request.url).hostname) > -1) {
// Stale-while-revalidate
// similar to HTTP's stale-while-revalidate: https://www.mnot.net/blog/2007/12/12/stale
event.respondWith(
caches.open(RUNTIME).then(cache => {
return caches.match(event.request).then(cachedResponse => {
// fetch(httpURL) is active mixed content, fetch(httpRequest) is not supported yet...
var fixedUrl = event.request.url.replace('http://', '//')
// cache busting
var fetchPromise = fetch(`${fixedUrl}?${Math.random()}`, {
cache: "no-store",
redirect: "follow"
})
.then(networkResponse => {
var resUrl = networkResponse.url
cache.put(event.request, networkResponse.clone())
return networkResponse;
})
.catch(error => {
console.log(error);
// for navigation requests, fallback to offline.html
if(event.request.url.substr(-1) == "/") {
return caches.match('offline.html')
}
})
// Return the response from cache or wait for network.
return cachedResponse || fetchPromise;
})
})
);
}
});