[Javascript] 網路離線依然可以顯示資料 Service Worker 簡單實作

2023-08-19

今天測試一個東西,解開我很久的疑惑,為何有些網站在我沒有網路的情況下,依然可以顯示一些資訊

有的是顯示你現在正在離線,或是有的依然變成一個資訊孤島依然還是可以查資料,正常狀況下不是應該都會顯示



後來查了一下原來是使用了 Service Worker 他可以將一些資源.css .js .html .. 註冊到 service worker 中

這樣之後在 offline 的時候就不會跳小恐龍,而是繼續執行網頁中的資料,猶如資料孤島版依然可以執行

這邊是最簡單的案例

.html + js :

<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<title></title>
<script src="https://code.jquery.com/jquery-3.7.1.min.js"></script>
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/css/font-awesome.css" />
</head>
<body>
<ul id="ulData">
</ul>
<script>
if ('serviceWorker' in navigator) {
console.log("serviceWorker enter");
navigator.serviceWorker.register('service-worker.js')
.then(function (reg) {
console.log("regist done");
}).catch(function (err) {
console.log(err);
});
}
</script>
<script>
var userData = [
{ "id": 1, "Title": "Ally" },
{ "id": 2, "Title": "Ben" },
{ "id": 3, "Title": "Cat" },
{ "id": 4, "Title": "Donma" },
{ "id": 5, "Title": "Elle" },
{ "id": 6, "Title": "Frank" },
{ "id": 7, "Title": "Grace" },
{ "id": 8, "Title": "Helen" },
{ "id": 9, "Title": "IssaBella" },
{ "id": 10, "Title": "July" }];
</script>
<script>
$(userData).each(function (index, obj) {
$('#ulData').append("<li><i class='fa fa-user-circle' aria-hidden='true'></i>&nbsp;" + obj.id + "." + obj.Title + "</li>");
});
</script>
</body>
</html>


其中提到的 service-worker.js

const cacheKey = 'DCACHE_V1';
self.addEventListener('install', (event) => {
event.waitUntil(caches.open(cacheKey).then((cache) => {
return cache.addAll([
//這邊註冊所有的資源
"https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/css/font-awesome.css",
"https://code.jquery.com/jquery-3.7.1.min.js",
"/index.html",
"/service-worker.js"
]);
}));
});
self.addEventListener("fetch", (e) => {
//防止外掛干擾 chrome-extension://
if ((e.request.url.startsWith('http'))) {
e.respondWith(
(async () => {
const r = await caches.match(e.request);
console.log(`[Service Worker] Fetching resource: ${e.request.url}`);
if (r) {
return r;
}
const response = await fetch(e.request);
const cache = await caches.open(cacheKey);
console.log(`[Service Worker] Caching new resource: ${e.request.url}`);
cache.put(e.request, response.clone());
return response;
})()
);
}
});


其實,這邊我是應用在幫朋友做的一個產品查詢的系統,因為他資料不常更新,所以我乾脆把整個 JSON 資料都放到 Service Worker 中

即使他在無網路環境下依然可以查詢,如果你遇到一些問題你可以按 下瀏覽器的 F12 進入開發者模式,選擇應用程式=> Service Workers 

這邊可以方便幫助你 debug 




這樣搞有沒有越來越像 APP


reference:

https://developer.chrome.com/docs/workbox/improving-development-experience?hl=zh-tw

https://noob.tw/pwa-service-worker/



當麻許的超技八 2014 | Donma Hsu Design.