웹 앱을 제공할 때 즉시성과 최신성 사이의 균형을 유지하는 데 도움이 되는 추가 도구입니다.
어떤 제품이 발송되었나요?
stale-while-revalidate
를 사용하면 개발자가 즉시성(캐시된 콘텐츠를 즉시 로드)과 최신성(캐시된 콘텐츠의 업데이트가 향후 사용되도록 보장) 간의 균형을 유지할 수 있습니다. 정기적으로 업데이트되는 서드 파티 웹 서비스 또는 라이브러리를 유지 관리하거나 퍼스트 파티 애셋의 전체 기간이 짧은 경향이 있는 경우 기존 캐싱 정책에 stale-while-revalidate
를 추가하면 유용할 수 있습니다.
Cache-Control
응답 헤더에서 max-age
와 함께 stale-while-revalidate
를 설정하는 지원은 Chrome 75 및 Firefox 68에서 사용할 수 있습니다.
stale-while-revalidate
를 지원하지 않는 브라우저는 이 구성 값을 자동으로 무시하고 max-age
를 사용합니다. 이는 곧 설명해 드리겠습니다.
의미
stale-while-revalidate
를 캐시된 응답이 오래되었을 수 있다는 생각과 재검증 프로세스라는 두 부분으로 나누어 보겠습니다.
먼저 브라우저는 캐시된 응답이 '비활성'인지 어떻게 알 수 있나요? stale-while-revalidate
가 포함된 Cache-Control
응답 헤더에는 max-age
도 포함되어야 하며, max-age
를 통해 지정된 초 수가 비활성 상태를 결정합니다. max-age
보다 최신인 캐시된 응답은 최신으로 간주되며 이전 캐시된 응답은 비활성 상태입니다.
로컬에 캐시된 응답이 아직 최신 상태인 경우 그대로 사용하여 브라우저의 요청을 처리할 수 있습니다. stale-while-revalidate
의 관점에서 볼 때 이 시나리오에서는 실행할 작업이 없습니다.
하지만 캐시된 응답이 오래된 경우 또 다른 기간 기반 검사가 수행됩니다. 즉, 캐시된 응답의 유지 기간이 stale-while-revalidate
설정에서 제공하는 추가 기간 내에 있는지 확인합니다.
비활성 응답의 경과 시간이 이 기간에 해당하는 경우 브라우저의 요청을 처리하는 데 사용됩니다. 동시에 캐시된 응답의 사용을 지연시키지 않는 방식으로 네트워크에 '재확인' 요청이 전송됩니다. 반환된 응답에는 이전에 캐시된 응답과 동일한 정보가 포함될 수도 있고 다를 수도 있습니다. 어느 쪽이든 네트워크 응답이 로컬에 저장되어 이전에 캐시된 항목을 대체하고 향후 max-age
비교 중에 사용되는 '최신성' 타이머를 재설정합니다.
그러나 오래된 캐시된 응답이 stale-while-revalidate
시간 범위를 벗어날 만큼 오래된 경우 브라우저의 요청을 처리하지 않습니다. 대신 브라우저는 네트워크에서 응답을 가져와 초기 요청을 처리하고 로컬 캐시를 최신 응답으로 채우는 데 모두 사용합니다.
실시간 예시
다음은 현재 시간, 특히 현재 시간으로부터 경과된 분 수를 반환하는 HTTP API의 간단한 예입니다.
이 시나리오에서 웹 서버는 HTTP 응답에 다음 Cache-Control
헤더를 사용합니다.
Cache-Control: max-age=1, stale-while-revalidate=59
이 설정은 시간 요청이 1초 이내에 반복되면 이전에 캐시된 값이 여전히 최신 상태이며 재검증 없이 있는 그대로 사용됨을 의미합니다.
그 후 1~60초 사이에 요청이 반복되면 캐시된 값이 비활성 상태가 되지만 API 요청을 처리하는 데 사용됩니다. 동시에 '백그라운드에서' 향후 사용할 새 값으로 캐시를 채우기 위한 재검증 요청이 실행됩니다.
60초가 지나서 요청이 반복되면 비활성 응답이 전혀 사용되지 않으며 브라우저의 요청을 처리하고 캐시를 재확인하는 작업 모두 네트워크에서 응답을 다시 수신하는 데 달려 있습니다.
다음은 이 세 가지 상태와 각 상태가 예시에서 적용되는 기간을 분류한 내용입니다.
일반적인 사용 사례
위의 '분 후' API 서비스 예시는 인위적이지만 예상되는 사용 사례를 보여줍니다. 즉, 업데이트가 필요하지만 어느 정도의 비활성 상태는 허용되는 정보를 제공하는 서비스입니다.
덜 인위적인 예로는 현재 날씨 조건을 나타내는 API나 지난 1시간 동안 작성된 주요 뉴스 헤드라인을 들 수 있습니다.
일반적으로 알려진 간격으로 업데이트되고, 여러 번 요청될 가능성이 높으며, 해당 간격 내에 정적 상태인 응답은 max-age
를 통한 단기 캐싱에 적합합니다. max-age
외에 stale-while-revalidate
를 사용하면 향후 요청이 네트워크 응답을 차단하지 않고도 캐시에서 최신 콘텐츠로 처리될 가능성이 높아집니다.
서비스 워커와 어떻게 상호작용하나요?
stale-while-revalidate
에 대해 들어본 적이 있다면 서비스 워커 내에서 사용되는 레시피의 맥락에서 들어봤을 가능성이 큽니다.
Cache-Control
헤더를 통해 stale-while-revalidate를 사용하면 서비스 워커에서 사용하는 것과 몇 가지 유사점이 있으며 최신성 절충 및 최대 전체 기간과 관련된 많은 동일한 고려사항이 적용됩니다. 하지만 서비스 워커 기반 접근 방식을 구현할지 아니면 Cache-Control
헤더 구성을 사용할지 결정할 때 고려해야 할 몇 가지 사항이 있습니다.
다음과 같은 경우 서비스 워커 접근 방식을 사용하세요.
- 웹 앱에서 이미 서비스 워커를 사용하고 있습니다.
- 캐시의 콘텐츠를 세부적으로 제어해야 하며 최근에 가장 많이 사용되지 않은 만료 정책과 같은 것을 구현하려고 합니다. Workbox의 캐시 만료 모듈을 사용하면 이 작업을 할 수 있습니다.
- 재검증 단계 중에 비활성 응답이 백그라운드에서 변경될 때 알림을 받으려고 합니다. 이 경우 Workbox의 Broadcast Cache Update 모듈이 도움이 될 수 있습니다.
- 모든 최신 브라우저에서 이
stale-while-revalidate
동작이 필요합니다.
다음과 같은 경우 Cache-Control 접근 방식을 사용하세요.
- 웹 앱용 서비스 워커를 배포하고 유지하는 데 드는 오버헤드를 처리하고 싶지 않습니다.
- 브라우저의 자동 캐시 관리를 통해 로컬 캐시가 너무 커지지 않도록 해도 됩니다.
- 현재 일부 최신 브라우저에서 지원되지 않는 접근 방식도 허용됩니다(2019년 7월 기준, 향후 지원이 확대될 수 있음).
서비스 워커를 사용하고 있으며 Cache-Control
헤더를 통해 일부 응답에 stale-while-revalidate
를 사용 설정한 경우 일반적으로 서비스 워커가 요청에 응답할 '첫 번째 기회'를 갖게 됩니다. 서비스 워커가 응답하지 않기로 결정하거나 응답을 생성하는 과정에서 fetch()
를 사용하여 네트워크 요청을 실행하면 Cache-Control
헤더를 통해 구성된 동작이 적용됩니다.
자세히 알아보기
- Fetch API 사양의
stale-while-revalidate
응답 - 초기
stale-while-revalidate
사양을 다루는 RFC 5861 - HTTP 캐시: 첫 번째 방어선(이 사이트의 '네트워크 안정성' 가이드 참조)
히어로 이미지: 새뮤얼 젤러 제공