AI 생성웹이 느리다면 서버부터 늘리지 마세요 — HTTP 캐시 헤더 4개로 요청 줄이는 법

웹이 느리다면 서버부터 늘리지 마세요 — HTTP 캐시 헤더 4개로 요청 줄이는 법

🤖 AI 생성 콘텐츠 — 이 글은 AI가 자료를 수집하고 초안을 작성했으며, 발행 전 누슘 운영자가 검수했습니다.

HTTP 캐시는 이전 응답을 재사용해 지연과 네트워크 사용량을 줄입니다. Cache-Control·ETag·Last-Modified·Vary를 언제 써야 하는지 실무 기준으로 설명합니다.

웹사이트가 느리다고 서버 수부터 늘리는 건, 편의점 물건 하나 사러 매번 공장에 가는 것과 비슷합니다. 자주 쓰는 응답을 브라우저나 CDN 가까이에 보관하면 원본 서버까지 가지 않아도 됩니다. 이게 HTTP 캐시입니다.

목차

  • HTTP 캐시는 어떻게 요청을 줄이나?
  • Cache-Control 지시어는 어떻게 고르나?
  • ETag와 Last-Modified는 무엇이 다른가?
  • 개인정보와 배포 사고를 어떻게 막나?

HTTP 캐시는 어떻게 요청을 줄이나?

RFC 9111은 HTTP 캐시를 응답 메시지를 저장하고 조회·삭제하는 하위 시스템으로 정의합니다. 목적은 이후의 동등한 요청에서 응답 시간과 네트워크 대역폭을 줄이는 것입니다.

캐시는 크게 두 종류입니다.

  • 개인 캐시: 한 사용자만 쓰는 브라우저 캐시
  • 공유 캐시: 여러 사용자가 함께 쓰는 CDN이나 프록시 캐시

저장된 응답이 아직 신선하면 원본 서버 확인 없이 바로 재사용할 수 있습니다. 신선하지 않아도 버릴 필요는 없습니다. 조건부 요청으로 “이 파일 그대로 써도 되나요?”라고 확인해 변경이 없으면 본문 없이 304 Not Modified를 받을 수 있습니다.

브라우저와 CDN, 원본 서버로 이어지는 HTTP 캐시 계층 이미지

Cache-Control 지시어는 어떻게 고르나?

가장 자주 만나는 지시어를 헷갈리지 않게 정리해 봅시다.

지시어 흔한 용도
max-age=초 해당 시간 동안 신선 버전이 붙은 정적 파일
s-maxage=초 공유 캐시의 신선도 별도 지정 CDN 캐시
private 공유 캐시에 저장 금지 사용자별 페이지
no-store 저장 자체를 금지 매우 민감한 응답
no-cache 저장 가능하지만 재사용 전 검증 자주 바뀌는 HTML
must-revalidate 오래된 응답을 임의 재사용하지 않음 엄격한 최신성 필요

가장 흔한 오해는 no-cache가 “캐시하지 마”라는 뜻이라는 것입니다. 실제로는 저장할 수 있지만 재사용 전에 원본과 검증하라는 뜻입니다. 저장도 하지 않게 하려면 no-store가 맞습니다.

정적 자산 파일명에 콘텐츠 해시를 넣는다면 긴 캐시가 잘 맞습니다. 내용이 바뀌면 URL도 바뀌기 때문입니다. 반면 로그인한 사용자의 계정 페이지에 무턱대고 public을 붙이면 공유 CDN에 개인정보가 남을 수 있습니다.

ETag와 Last-Modified는 무엇이 다른가?

둘 다 재검증에 쓰는 검증자입니다.

  • ETag: 서버가 응답의 특정 버전을 식별하는 문자열입니다.
  • Last-Modified: 리소스가 마지막으로 바뀐 시각입니다.

브라우저는 If-None-Match에 ETag를 담거나 If-Modified-Since에 시간을 담아 다시 묻습니다. 서버가 변경 없음을 확인하면 본문 대신 304로 답합니다. 큰 이미지나 자바스크립트를 다시 보내지 않아도 됩니다.

ETag는 서버가 버전을 정밀하게 제어하기 좋습니다. Last-Modified는 단순하지만 시간 해상도와 생성 방식에 따라 변화 감지가 덜 정확할 수 있습니다. 둘을 함께 제공하는 구현도 많지만, 실제 동작은 서버와 CDN 설정을 점검해야 합니다.

브라우저가 서버에 버전을 확인하고 본문 전송을 생략하는 이미지

개인정보와 배포 사고를 어떻게 막나?

캐시는 성능 도구인 동시에 보안 경계입니다.

  1. 인증 쿠키에 따라 내용이 달라지는 응답은 기본적으로 private 또는 적절한 저장 금지 정책을 검토합니다.
  2. Vary를 사용하면 어떤 요청 헤더에 따라 캐시 키가 달라지는지 알릴 수 있습니다.
  3. 정적 파일에는 콘텐츠 해시를 붙이고 긴 TTL을 사용합니다.
  4. HTML은 짧은 TTL과 재검증을 조합합니다.
  5. CDN 설정에서 원본의 Cache-Control을 덮어쓰는 규칙이 없는지 확인합니다.
  6. 배포 전후 Age, Cache-Control, ETag, Vary 응답 헤더를 실제로 측정합니다.

캐시 무효화는 어렵기로 유명합니다. 그래서 “모든 걸 짧게 캐시”하기보다 URL 버전 관리와 응답 종류별 정책을 먼저 세우는 편이 낫습니다.

자주 묻는 질문 (FAQ)

Q. no-cache와 no-store는 같은 뜻인가요? A. 아닙니다. no-cache는 저장된 응답을 재사용하기 전에 검증하라는 뜻이고, no-store는 응답을 저장하지 말라는 뜻입니다.

Q. CDN을 쓰면 브라우저 캐시는 필요 없나요? A. 둘은 거리가 다릅니다. CDN은 사용자와 가까운 공유 캐시이고, 브라우저 캐시는 사용자 기기 안의 개인 캐시입니다. 적절히 함께 쓰면 네트워크 요청 자체를 더 줄일 수 있습니다.

Q. 정적 파일은 얼마나 오래 캐시해야 하나요? A. 콘텐츠 해시가 파일명에 들어가 변경 시 URL이 바뀐다면 긴 max-age를 쓰기 좋습니다. 같은 URL의 내용이 바뀐다면 무효화 전략과 재검증을 함께 설계해야 합니다.

Q. 304 응답이면 캐시를 안 쓴 건가요? A. 캐시된 본문을 재사용하되 원본 서버에 유효성만 확인한 것입니다. 완전한 캐시 적중보다는 왕복이 들지만 본문 전송량을 줄입니다.

마치며

HTTP 캐시는 서버를 “더 세게” 만드는 기술이 아니라, 서버까지 갈 필요 없는 요청을 없애는 기술입니다. 정적 파일, HTML, 사용자별 API를 같은 정책으로 묶지 마세요. 응답의 성격부터 나누면 Cache-Control이 훨씬 쉬워집니다.

여러분 서비스에서 가장 캐시하기 어려운 응답은 무엇인가요? 누슘 댓글에서 사례를 나눠 주세요.

참고자료


태그: #HTTP캐시 #CacheControl #ETag #LastModified #CDN #브라우저캐시 #RFC9111

이 게시판의 글

개발 뉴스