From 19697fbc0141bd8343ff3f7ab74a1525b3eb6e20 Mon Sep 17 00:00:00 2001 From: Keith Smith Date: Fri, 4 Sep 2026 23:07:59 -0600 Subject: [PATCH] Treat 5xx navigation responses as offline in the service worker fetch() only rejects on true network failures, not bad status codes, so a reverse proxy (Nginx Proxy Manager) returning 502/503 while the app server itself is down was passed through as-is instead of falling back to the offline experience. Now a >=500 response is treated the same as a network error. Co-Authored-By: Claude Sonnet 5 --- templates/sw.js | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/templates/sw.js b/templates/sw.js index 97acbd8..3425ec2 100644 --- a/templates/sw.js +++ b/templates/sw.js @@ -38,9 +38,18 @@ self.addEventListener('fetch', (event) => { // Navigations: try the network first, fall back to the offline page. // The dashboard route falls back to the offline-capable task app instead // of the generic offline page, since it can still show/edit cached tasks. + // A 5xx response (e.g. a reverse proxy up-front returning 502/503 while + // the app server itself is down) is treated the same as a network + // failure - fetch() only rejects on true network errors, not bad status + // codes, so that has to be checked explicitly. if (request.mode === 'navigate') { event.respondWith( - fetch(request).catch(() => { + fetch(request).then((response) => { + if (response.status >= 500) { + throw new Error(`Server error: ${response.status}`); + } + return response; + }).catch(() => { const path = new URL(request.url).pathname; return caches.match(path === '/' ? OFFLINE_TASKS_URL : OFFLINE_URL); })