fix: offline content for iOS
This commit is contained in:
+28
-17
@@ -48,25 +48,28 @@ self.addEventListener("fetch", (event) => {
|
||||
|
||||
const url = new URL(req.url);
|
||||
|
||||
// 1. Page navigations: network-first, fall back to a saved copy, then to the
|
||||
// offline library. This is what makes a "saved" page open with no network.
|
||||
// 1. Page navigations.
|
||||
// ONLINE: do NOT intercept — let the browser navigate natively. Proxying
|
||||
// a redirected response (the app server-`redirect()`s every book chapter
|
||||
// index to its first verse) or Next's streamed SSR through the SW makes
|
||||
// iOS/WebKit standalone PWAs render a blank page. Native handling is
|
||||
// identical to how the app behaved before this SW had a fetch handler.
|
||||
// OFFLINE: serve a saved copy, then the offline library, then a stub —
|
||||
// all plain stored/constructed Responses, which WebKit accepts.
|
||||
if (req.mode === "navigate") {
|
||||
if (self.navigator.onLine) return;
|
||||
event.respondWith(
|
||||
(async () => {
|
||||
try {
|
||||
return await fetch(req);
|
||||
} catch {
|
||||
const pages = await caches.open(PAGES_CACHE);
|
||||
const saved =
|
||||
(await pages.match(req.url)) || (await pages.match(url.pathname));
|
||||
if (saved) return saved;
|
||||
const fallback = await pages.match(OFFLINE_FALLBACK);
|
||||
if (fallback) return fallback;
|
||||
return new Response(
|
||||
"<!doctype html><meta charset=utf-8><title>Offline</title><body style=\"font-family:system-ui;padding:2rem\"><h1>You're offline</h1><p>This page hasn't been saved for offline use.</p>",
|
||||
{ headers: { "Content-Type": "text/html; charset=utf-8" }, status: 503 },
|
||||
);
|
||||
}
|
||||
const pages = await caches.open(PAGES_CACHE);
|
||||
const saved =
|
||||
(await pages.match(req.url)) || (await pages.match(url.pathname));
|
||||
if (saved) return saved;
|
||||
const fallback = await pages.match(OFFLINE_FALLBACK);
|
||||
if (fallback) return fallback;
|
||||
return new Response(
|
||||
"<!doctype html><meta charset=utf-8><title>Offline</title><body style=\"font-family:system-ui;padding:2rem\"><h1>You're offline</h1><p>This page hasn't been saved for offline use.</p>",
|
||||
{ headers: { "Content-Type": "text/html; charset=utf-8" }, status: 503 },
|
||||
);
|
||||
})(),
|
||||
);
|
||||
return;
|
||||
@@ -80,7 +83,15 @@ self.addEventListener("fetch", (event) => {
|
||||
const hit = await cache.match(req);
|
||||
if (hit) return hit;
|
||||
const res = await fetch(req);
|
||||
if (res && res.ok) cache.put(req, res.clone());
|
||||
// Only cache full, same-origin 200s. Guard put() so a 206/opaque/quota
|
||||
// rejection can never fail the request (which could drop a JS chunk).
|
||||
try {
|
||||
if (res && res.status === 200 && res.type === "basic") {
|
||||
await cache.put(req, res.clone());
|
||||
}
|
||||
} catch {
|
||||
/* serve the response uncached */
|
||||
}
|
||||
return res;
|
||||
})(),
|
||||
);
|
||||
|
||||
Reference in New Issue
Block a user