Zum Hauptinhalt springen
tsecurity.de LIVE
Echtzeit-Radar & Feeds
Alle RSS Feeds
👥 Community & Social
Sichere ProgrammierungLINQ GroupBy: The Operator Everyone Uses Wrong(23.09.2026 um 09:41 Uhr)
Sichere ProgrammierungIT Heard About the Acquisition Nine Days Before It Closed(23.09.2026 um 09:45 Uhr)
Sichere ProgrammierungThe Story Behind Building NuvyntraLabs(23.09.2026 um 09:45 Uhr)
Sichere ProgrammierungFive dashboards nobody was opening(23.09.2026 um 09:46 Uhr)
Sichere ProgrammierungThe Shift from AI Insights to AI Actions in Finance(23.09.2026 um 09:47 Uhr)
Sichere ProgrammierungGo WebAssembly Meets WebForms Core 2.1(23.09.2026 um 09:49 Uhr)
Sichere ProgrammierungJust One More Round: Scope Creep in the Age of AI Agents(23.09.2026 um 09:50 Uhr)
Sichere ProgrammierungThe Calls That Reach Us Now Are the Ones the Model Could Not Answer(23.09.2026 um 09:50 Uhr)
Sichere ProgrammierungOne Loop Made Four Hundred Round Trips(23.09.2026 um 09:52 Uhr)
Sichere ProgrammierungThe order was committed and nothing else ever heard about it(23.09.2026 um 09:53 Uhr)
Sichere ProgrammierungLINQ GroupBy: The Operator Everyone Uses Wrong(23.09.2026 um 09:41 Uhr)
Sichere ProgrammierungIT Heard About the Acquisition Nine Days Before It Closed(23.09.2026 um 09:45 Uhr)
Sichere ProgrammierungThe Story Behind Building NuvyntraLabs(23.09.2026 um 09:45 Uhr)
Sichere ProgrammierungFive dashboards nobody was opening(23.09.2026 um 09:46 Uhr)
Sichere ProgrammierungThe Shift from AI Insights to AI Actions in Finance(23.09.2026 um 09:47 Uhr)
Sichere ProgrammierungGo WebAssembly Meets WebForms Core 2.1(23.09.2026 um 09:49 Uhr)
Sichere ProgrammierungJust One More Round: Scope Creep in the Age of AI Agents(23.09.2026 um 09:50 Uhr)
Sichere ProgrammierungThe Calls That Reach Us Now Are the Ones the Model Could Not Answer(23.09.2026 um 09:50 Uhr)
Sichere ProgrammierungOne Loop Made Four Hundred Round Trips(23.09.2026 um 09:52 Uhr)
Sichere ProgrammierungThe order was committed and nothing else ever heard about it(23.09.2026 um 09:53 Uhr)
Intelligence View
⚡ tsecurity.de Intelligence

Service workers that don’t surprise you: deterministic caching for offline-first PWAs

Series: Start here · Part 1 · Part 2 · Part 3 · Part 4 · Part 5 · Part 6 · Part 7 · Part 8 · Part 9 · Part 10 This post is Part 3 in a Dev.to series grounded in the open-source Pain Tracker repo. Not medical advice. Not a compliance clai…

0
↗ Quelle (dev.to)
Reagiere als Erste:r — dein Feedback zählt!

Series: Start here · Part 1 · Part 2 · Part 3 · Part 4 · Part 5 · Part 6 · Part 7 · Part 8 · Part 9 · Part 10



This post is Part 3 in a Dev.to series grounded in the open-source Pain Tracker repo.




  • Not medical advice.

  • Not a compliance claim.

  • It’s about deterministic behavior and truthful boundaries.




If you want privacy-first, offline health tech to exist without surveillance funding it: sponsor the build → https://paintracker.ca/sponsor




If you haven’t read Part 2 yet:











What “surprising” service workers do



If you’ve been burned by service workers, it’s usually one of these:



(And if you haven’t been burned yet: congrats. Your day is coming.)



1) Stale HTML breaks your app after deploy




  • the browser keeps serving an old index.html

  • the module graph changes

  • suddenly you’re getting chunk 404s or a blank screen



2) Base paths don’t match reality




  • it works on /

  • it breaks on GitHub Pages under /pain-tracker/

  • you register the wrong scope and nothing behaves the way you think it does



3) Caching becomes accidental data retention




  • you didn’t intend to cache responses

  • you cache “everything” because it’s easy

  • you end up with user-specific payloads in caches (which is a problem for sensitive apps)



4) Updates are confusing




  • new worker installs but doesn’t activate

  • users don’t refresh

  • you can’t tell what version is running



The theme: the browser is doing exactly what you asked… but you didn’t ask carefully.









The repo’s stance: boring on purpose



Pain Tracker’s service worker is intentionally minimal:





  • Network-first for navigations (avoid stale HTML)


  • Cache static assets only (scripts, styles, images, fonts)


  • Versioned caches with cleanup on activation


  • A small precache for offline.html and the manifest



There’s no “offline magic,” no runtime caching of arbitrary API responses, and no attempt to make the SW a data layer.



Two service worker scripts exist:











The deterministic core: never cache navigations



The most important line in both service workers is conceptually this:




navigations are network-first.




In public/sw.js, a navigation request is detected using request.mode === 'navigate' or Accept: text/html.



Then it does:




  • try fetch(request)

  • if that fails, serve offline.html



That’s it.



Why this matters:




  • If you cache navigations with cache-first, you will eventually ship a new build whose HTML points to new chunk filenames.

  • The cached HTML keeps pointing at old filenames.

  • You get chunk 404s and the app feels “randomly broken.”



For a health-adjacent PWA, that kind of failure is worse than a clean offline message.









Cache static assets (but be explicit)



Pain Tracker only caches same-origin requests, GET requests, and only if they look like static assets.



In public/sw.js, that’s done with two mechanisms:




  • allowlisted path prefixes like /assets/, /icons/, /logos/, /screenshots/

  • a conservative extension allowlist (.js, .css, .png, .svg, .woff2, …)



The flow for cacheable static assets is:




  • if it’s in cache → return it

  • else fetch → cache successful 200 responses → return



This is the “least surprising” offline strategy:




  • The shell loads quickly after first visit

  • Deploys don’t get stuck behind cached HTML

  • You don’t accidentally cache sensitive runtime responses









Versioned caches (so you can delete what you meant)



Both service workers have a version string and build the cache name from it:




  • CACHE_NAME = pain-tracker-static-v<version>



On activation, the SW deletes older caches with the pain-tracker- prefix.



That gives you a clean invariant:




  • if you bump the SW version, old caches get removed



No guessing. No “maybe it’ll update.” It either updates or it doesn’t.









GitHub Pages is the classic base-path foot-gun



The repo includes a second service worker at public/pain-tracker/sw.js for a GitHub Pages-style base path.



What changes:




  • The precache URL for the manifest becomes /pain-tracker/manifest.json

  • Static prefixes include /pain-tracker/assets/

  • Offline fallback includes '/pain-tracker/'



This is the kind of boring duplication that prevents hours of “why is it offline on one environment but not the other?”









Registration: compute the base, then register



The app registers the SW in the PWA manager:





Key behaviors:




  • It computes a baseUrl from VITE_BASE (when set), or Vite’s BASE_URL, and falls back to location.pathname when Vite gives a relative base.

  • It registers ${baseUrl}sw.js with scope: baseUrl.

  • It sets updateViaCache: 'none' to force update checks.



It also wires an updatefound listener so the app can notify users when new content is available.






A small readiness handshake (tests love this)



The service worker posts a SW_READY message on activation, and responds to PING with PONG.



The PWA manager listens for that and sets window.__pwa_sw_ready = true.



That’s a practical trick:




  • it avoids flaky “is the SW ready yet?” tests

  • it gives you a simple debug signal in DevTools









What this SW does not do (and why)



It does not:




  • cache arbitrary fetches

  • cache API responses

  • cache navigations

  • implement a “sync your health data to the cloud” system



Those aren’t missing features. They’re deliberate boundaries.



If you add more SW features later (background sync, offline processing, etc.), treat them as new trust boundaries:




  • decide what data is allowed in caches

  • avoid storing Class A payloads in Cache Storage

  • be explicit about what can happen while “locked” vs “unlocked”









Verify it yourself (no trust required)



1) Inspect the service worker script:





2) In DevTools:




  • Application → Service Workers (confirm scope + script URL)

  • Application → Cache Storage (look for pain-tracker-static-v…)



3) Test offline behavior:




  • DevTools → Network → Offline

  • Refresh a route

  • You should get the offline fallback instead of a broken shell









Next up



Part 4 will cover defensive parsing (Zod + schema-first inputs) and how to keep “offline-first” from becoming “silently accepts garbage.”



Prev: Part 2 — Three storage layers

Next: Part 4 — Zod + defensive parsing









Support this work



Ähnliche Beiträge
🔍 Verwandte News

Auch interessante Nachrichten Service workers that don’t surprise you: deterministic caching for offline-first PWAs

Thematisch verwandte Begriffe: Service, workers, that, dont · 6 Treffer

Laden...

Videos werden geladen ...

Laden...

Beiträge werden geladen ...

Laden...

Videos werden geladen ...

Laden...

Beiträge werden geladen ...

Laden...

Videos werden geladen ...

Laden...

Beiträge werden geladen ...

Laden...

Videos werden geladen ...

Laden...

Beiträge werden geladen ...

Laden...

Videos werden geladen ...

Zum Aktualisieren ziehen
ZERO-DAY CVE-2026-96258 | A vulnerability has been found in onSite internet GmbH Auktion NG Auktio…
Advisory →
TTS Reader • tsecurity.de Voice
tsecurity.de Icon
tsecurity.de App
Offline-Lesen, Eilmeldungen & 0ms Ladezeit

Installiere tsecurity.de direkt auf deinen Home-Bildschirm für das ultimative Vollbild-Magazinerlebnis ohne Browser-Leisten.

Nächster Beitrag
Themen-Radar & Intelligence Matrix
Echtzeit-Taxonomie nach Angriffsvektoren & Plattformen

tsecurity.de Live Threat Radar

🔴 LIVE RADAR
MONITORING
AKTIV
CVE-DATENBANK
LIVE
🔍
Community Radar & Live Chat
Sentinel Bot online • Live-Stream
Dein Cluster: Security Explorer
Match:
lädt…
Verbindung zum Community-Stream wird aufgebaut...
Bearbeitungsmodus — Senden überschreibt deine Nachricht
Community-Puls — was gerade passiert
lädt…
Aktivitäten deiner Analysten
lädt…
Neues Thema oder Eilmeldung einreichen

Reiche interessante Links, Zero-Days oder Debatten ein. Die Community entscheidet per Upvote über die Veröffentlichung.

Heiß diskutierte Einreichungen
🔖 Gespeicherte Artikel
📂 Keine gespeicherten Artikel vorhanden.
Zurück Ziehen Vor
Links: vorheriger Artikel Rechts: nächster Artikel unten: schließen
News NIS-2 Frühwarnung Tier-1 Intel ⏱️ 3 Min vor 10 Min
Artikeldaten werden geladen...

Zurück: vorheriger Vor: nächster
↗ Original-Quelle
Social Reaktionen Deine Reaktion zählt
Einstufung & Relevanz-Poll 0 Stimmen
In sozialen Netzwerken teilen 1-Klick