캐시의 기본 원리 및 적용

HTTP 헤더 - 캐시

(캐시가 없을 경우)클라이언트가 logo.jpg 이미지에 대한 요청을 보내고 서버가 해당 이미지에 대한 응답을 줄 때, logo.jpg 데이터가 변경되지 않아도 계속 데이터를 새로 다운받아야 합니다.

용량이 클수록 비용이 커지고 브라우저의 로딩 속도가 느려집니다.

캐시를 통한 반복적인 데이터 임시 저장

캐시(Cache)는 컴퓨터 과학에서 데이터나 값을 미리 복사해 놓는 임시 장소를 가리킵니다.

원래 데이터에 접근하는 시간이 오래 걸리는 경우나 값을 다시 계산하는 시간을 절약하고 싶은 경우에 사용합니다.

캐시에 데이터를 미리 복사해 놓으면 계산이나 접근 시간 없이 빠른 속도로 데이터에 접근할 수 있습니다.
(캐시는 유효 시간이 존재하고 유효 시간이 지난 경우, 네트워크 다운로드를 발생시킨다.)

유효 시간이 지난 캐시는 지워지고 새로운 캐시를 업데이트 합니다.


캐시 검증 헤더와 조건부 요청

캐시 유효시간이 초과하더라도 서버 데이터가 변경되지 않았다면 검증 헤더 Last Modified를 이용해 캐시의 수정시간을 알 수 있습니다.

Last Modified는 데이터가 마지막으로 수정된 시간 정보를 헤더에 포함합니다.

캐시 유효시간이 초과됐더라도 If-Modified-Since 헤더를 이용해 조건부 요청을 할 수 있습니다.
(서버의 해당 자료 수정일과 비교해 수정이 안됐을 경우 304 Not Modified 메시지를 담아 알려줍니다.)

Last-Modified와 If-Modified-Since 정리

  • 캐시 유효 시간(기간)이 초과해도 서버의 데이터가 갱신되지 않으면?
    304 Not Modified + 헤더 메타데이터만 응답

  • 클라이언트는 서버가 보낸 응답 헤더 정보로 캐시의 메타데이터를 갱신

  • 클라이언트는 캐시에 저장되어 있는 데이터 재활용

  • 캐시와 다른 자료를 비교해서 갱신 (매우 실용적이라 할 수 있다..)

문제점..?

  • 1초 미만 단위로 캐시 조정이 불가능
  • 날씨 기반의 로직 사용
  • 데이터를 똑같이 수정해 결과가 같은 경우에도 캐시 값 갱신
  • 서버에서 별도의 캐시 로직을 관리하고 싶은 경우

Etag와 If-None-Match

서버에서 캐시를 컨트롤하고 싶은 경우 Etag를 사용할 수 있습니다.

  • Etag: Entity Tag
  • 캐시용 데이터에 임의의 고유한 버전 이름을 달아둠
  • 데이터가 변경되면 이 이름을 바꿔서 변경
  • 단순하게 Etag만 보내서 같으면 유지, 다르면 다시 닫는 방식

작동 원리

  1. 서버에서 헤더에 Etag를 작성해 응답한다.

  2. 클라이언트 캐시에서 해당 Etag 값을 저장한다.
    (만약 캐시 시간이 초과 된 경우 다시 요청해 Etag 값을 검증하는 If-None-Match를 요청 헤더에 작성해서 보낼 수 있다.)

  3. 서버에서 데이터가 변경되지 않았을 경우 Etag는 동일하기에 If-None-Match가 거짓이 된다.
    (서버에서 304 Not Modified를 응답한다.)

  4. 브라우저는 캐시 응답 결과를 바탕으로 재사용하고 헤더 데이터를 갱신한다.


Cache-Control (캐시 지시어)

캐시와 관련된 헤더들과 조건부 요청 헤더

  • Cache-Control: max-age
    캐시 유효 시간, 초 단위

  • Cache-Control: no-cache
    데이터는 캐시해도 되지만, 항상 Origin 서버에서 검증하고 사용

  • Cache-Control: no-store
    데이터에 민감한 정보가 있으면 저정하면 안된다.

  • Expires (캐시 만료일 지정)
    캐시 만료일을 정확한 날짜로 지정 가능하다. 최근에는 max-age를 권장한다.


프록시 캐시 (Proxy Cache)

프록시란 클라이언트와 서버 사이에 대리로 통신을 수행하는 것을 프록시라고 합니다. 중계 기능을 하는 서버는 프록시 서버라고 합니다.

클라이언트 또는 서버가 네트워크에 간접적으로 접속할 수 있기 때문에 보안, 캐싱을 통한 성능, 트래픽 분당 등의 장점을 가집니다.

프록시 캐시 서버의 장점은 빠른 속도로 자료를 가져올 수 있습니다.
(원서버보다 프록시 서버에 가깝게 있을 경우)

클라이언트에서 사용하고 저장하는 캐시를 Private 캐시라 하며, 서버의 캐시를 Public 캐시라고 합니다.

Cache-Control (캐시 지시어 기타)

  • Cache-Control: public
    응답이 public 캐시에 저장됨

  • Cache-Control: Private
    응답이 해당 사용자만을 위한 것, Private 캐시에 저장

  • Cache-Control: s-maxage
    프록시 캐시에만 적용되는 max-age

  • Age: 60 (HTTP 헤더)
    오리진 서버에서 응답 후 프록시 캐시 내에 머문 시간

캐시 무효화

클라이언트가 캐시를 적용하지 않아도 임의로 브라우저가 캐시를 적용하는 경우 특정 페이지에서 캐시가 되면 안되는 정보가 있을 경우 무효화 할 수 있습니다.

  • Cache-Control: no-cache
    데이터는 캐시해도 되지만, 항상 원 서버에서 검증하고 사용

  • Cache-Control: no-store
    데이터에 민감한 정보가 있기 때문에 저장하면 안됨

  • Cache-Control: must-revalidate
    캐시 만료 후 최초 조회 시 원 서버에 검증, 원 서버 접근 실패 시 반드시 오류 발생(504 Gateway Timeout)

no-cache

no-cache, must-revalidate 모두 원 서버에 검증해야 합니다.

요청이 프록시 캐시 서버에 도착했을 때 no-cache인 경우 원 서버(Origin 서버)에 요청을 하게 됩니다.
(원 서버는 검증 후 304 응답을 합니다.)

만약 프록시 캐시 서버가 원 서버와 네트워크 단절이 일어난 경우, 웹 브라우저(클라이언트)는 원 서버에 요청을 보내고 no-cache에 대한 응답으로 200ok를 반환합니다.
(원 서버에도 접근이 불가능한 경우 504 Gateway Timeout을 응답합니다.)

profile
메일은 매일 확인하고 있습니다. 궁금하신 부분이나 틀린 부분에 대한 지적사항이 있으시다면 언제든 편하게 연락 부탁드려요 :)

0개의 댓글