Service Worker = 네트워크 인터셉터. 5가지 표준 전략 — Cache-First / Network-First / Stale-While-Revalidate / Network-Only / Cache-Only — 자원 종류에 따라 골라 쓴다. 한 SW 안에 여러 전략 혼용 OK.
📖 핵심 개념
install 이벤트: precache (빌드 시 알려진 자원).
fetch 이벤트: 매 요청 인터셉트.
activate 이벤트: 옛 캐시 청소.
자원 별 다른 정책 적용.
💻 코드 패턴 (Workbox 기반)
// sw.ts
import{precacheAndRoute}from'workbox-precaching';import{registerRoute}from'workbox-routing';import{CacheFirst,NetworkFirst,StaleWhileRevalidate}from'workbox-strategies';import{ExpirationPlugin}from'workbox-expiration';// 빌드 시 자동 주입
precacheAndRoute(self.__WB_MANIFEST);// 1. 정적 자산 — Cache-First (해시 파일명이라 immutable)
registerRoute(({request})=>['style','script','font'].includes(request.destination),newCacheFirst({cacheName:'static-v1',plugins:[newExpirationPlugin({maxAgeSeconds: 30*24*60*60})],}));// 2. 이미지 — Stale-While-Revalidate
registerRoute(({request})=>request.destination==='image',newStaleWhileRevalidate({cacheName:'images-v1',plugins:[newExpirationPlugin({maxEntries: 100,maxAgeSeconds: 7*24*60*60})],}));// 3. API — Network-First with timeout
registerRoute(({url})=>url.pathname.startsWith('/api/'),newNetworkFirst({cacheName:'api-v1',networkTimeoutSeconds: 3,}));
5가지 전략 요약
전략
흐름
사용처
Cache-First
캐시 → 없으면 네트워크
hashed 정적 자산
Network-First
네트워크 → 실패시 캐시
자주 변하는 데이터
Stale-While-Revalidate
캐시 즉시 + 백그라운드 재검증
이미지, 자주 보지만 약간 stale OK
Network-Only
캐시 안 씀
결제, 민감 데이터
Cache-Only
네트워크 안 씀
오프라인 전용 자원
🤔 의사결정 기준
자원
전략
JS/CSS (hashed)
Cache-First + 만료 30d
이미지
Stale-While-Revalidate + 100 entries cap
HTML
Network-First (3s timeout) → cached fallback
API GET (read)
Network-First or stale-while-revalidate
API POST (write)
Network-Only (절대 캐시 X)
Offline page
Cache-Only
❌ 안티패턴
모든 요청 Cache-First: API 응답이 영원히 stale. 사용자 답답.
버전 관리 없는 캐시 이름: 새 deploy 가 옛 캐시 못 청소. static-v1 → static-v2.
POST 요청 캐싱: 사고. 명시적 Network-Only.
manifest 없는 precache: 빌드 타임 정보 안 들어가서 누락.
activate 에서 옛 캐시 안 지움: 무한 누적 → quota exceeded.
localhost 에서 SW 등록 후 디버깅 어려움: chrome devtools "Update on reload" + "Bypass for network" 활용.
사용자 알림 없이 새 SW 활성화: 페이지가 갑자기 다른 버전. skipWaiting + clientsClaim 신중히. 보통 사용자에게 "새 버전 있음, 새로고침" prompt.