노트

ETag와 조건부 요청

ETag (Entity Tag)

프런트엔드#http#performance · 연결된 개념 2개

쉽게 말하면

ETag는 파일에 붙은 버전 스티커예요. 브라우저가 '내 스티커는 이건데 바뀌었나요?' 하고 물으면, 서버는 같을 때 304로 그대로 쓰라고만 답하고 본문은 다시 보내지 않아요.

비유가 깨지는 곳 스티커를 파일 내용 해시로 읽으면 안 돼요. S3 같은 저장소의 ETag는 업로드 방식에 따라 MD5가 아니니 버전 토큰으로만 쓰고, 저장할 때 If-Match로 보내면 덮어쓰기 충돌도 막아요.

리소스의 특정 버전을 가리키는 식별자를 담은 HTTP 응답 헤더(entity tag). 클라이언트가 이 값을 다시 보내 "그사이 바뀌었는지"를 묻는 조건부 요청(Conditional Request)의 기준이 된다. RFC(Request for Comments) 9110에 정의된 표준 헤더다.

GET /style.css
→ 200 OK
  ETag: "33a64df5"
 
GET /style.css
If-None-Match: "33a64df5"
→ 304 Not Modified   (본문 없음, 캐시 재사용)
  • 같으면 304로 본문 전송을 생략해 대역폭을 아낀다. 다르면 200과 새 본문, 새 ETag가 온다 → 브라우저 캐시
  • Last-Modified/If-Modified-Since와 같은 역할이지만 초 단위 시각이 아니라 버전 자체를 비교하므로 더 정확하다
  • W/"..."는 약한 ETag다. 바이트가 똑같지 않아도 의미상 같으면 같은 값으로 친다(압축 방식만 다른 경우 등)

버전 토큰으로 다루기

표준은 "버전을 식별한다"는 역할만 정하고 만드는 방법은 정하지 않는다. AWS S3(Amazon Simple Storage Service)나 Cloudflare R2 같은 객체 저장소도 객체마다 ETag를 붙이는데, 단일 업로드에서는 MD5(Message-Digest Algorithm 5)처럼 보여도 멀티파트 업로드나 암호화 방식에 따라 MD5가 아니다. 그래서:

  • ETag를 파일 내용 해시로 해석하지 않는다. "이 객체의 현재 버전 토큰"으로만 쓴다
  • 낙관적 잠금(Optimistic Locking)에 쓰기 좋다. 읽을 때 받은 ETag를 저장할 때 If-Match로 보내면, 그사이 누가 바꿨을 경우 412 Precondition Failed로 실패한다. 덮어쓰기 충돌을 막는다 → 멱등성
  • 사용자에게 보여 줄 수정 시각은 ETag가 아니라 Last-Modified(또는 저장소의 수정 시각 필드)를 쓴다

출처: MDN — ETag · RFC 9110 — 8.8.3. ETag

연결된 개념

이 노트를 가리키는 문서

뜻이 가까운 노트

  • CDN

    CDN(Content Delivery Network)은 세계 곳곳에 둔 서버(엣지, edge)들이 원본 서버(오리진, origin)의 응답을 복사해 두었다가 사용자와 가까운 곳에서 대신 내주는 네트워크다. 물리적 거리가 줄어 응답이 빨라지고, 오리진으로 가는 요청이 줄어 서버 부담도 줄어든다.

  • HTTP 쿠키

    서버가 브라우저에 저장시키는 작은 이름-값 데이터. 브라우저는 조건이 맞는 요청마다 쿠키를 자동으로 실어 보내므로, 상태가 없는 HTTP 위에서 로그인 같은 상태를 이어 가는 데 쓴다.

  • 커넥션 드레이닝과 무중단 재시작

    배포 중 서버를 재시작하는 몇 초 동안 로드밸런서가 그 서버로 요청을 보내면 502가 난다. 먼저 로드밸런서에서 빼고(드레이닝), 진행 중인 요청을 마친 뒤 재시작하고, 준비되면 다시 넣는다.

  • 버전 스큐와 정적 자산 오프로드

    버전 스큐(Version Skew)는 새 버전을 배포한 뒤에도 브라우저에 떠 있는 이전 빌드의 클라이언트가 새 서버와 통신하면서 생기는 불일치다. 대표 증상은 이전 HTML이 참조하던 JS 청크를 늦게 불러오려다 404가 나는 ChunkLoadError다.

  • 서버 전송 이벤트(SSE)

    서버 전송 이벤트(Server-Sent Events, SSE)는 HTTP(HyperText Transfer Protocol) 응답 하나를 닫지 않고 열어 둔 채, 서버가 원할 때마다 텍스트 이벤트를 흘려보내는 서버 → 클라이언트 단방향 푸시 방식이다. HTML 표준에 정의돼 있고 브라우저는 EventSource로 받는다.

보기 옵션