작성일자 : 2020.12.20
환경 : Spring Boot, Chrome
1. 개요
1.1) Web Cache(HTTP Cache)란?
- 서버 지연을 줄이는 목적으로 정적 리소스 등의 웹 문서들을 임시 저장하여 재활용하기 위한 기술
- 어디에 적용하느냐에 따라 Browser Cache, Proxy Cache, Gateway Cache 로 구분지을 수 있음
- 웹 캐싱 방법
- Response 에 Cache-Control Header 사용
1.2) Cache-Control ?
- 서버와 브라우저 사이의 캐시 정책. 여러 지시자들을 사용하여 옵션을 설정할 수 있음
크롬 개발자 도구에서 Cache-Control 헤더를 아래와 같이 확인 가능하다.
- Cache-Control 기본 지시자
- no-cache : 캐시 데이터가 있어도 무조건 서버로부터 유효성을 재검증함 (캐시를 사용하지 않는게 아님)
- no-store : 캐시 데이터를 저장하지 않음 (캐시를 사용하지 않음)
- max-age=[sec] : 캐시 데이터가 유효한 시간을 설정. 해당 시간이후에 캐시 데이터가 만료
- must-revalidate : 만료된 캐시 데이터를 무조건 서버로부터 유효성을 재검증함
- 캐싱 데이터 유효성 검증 방법 (ETag 활용)
- 브라우저가 서버로 첫 요청시, 서버는 응답에 해당하는 데이터와과 함께 Etag 를 반환 (이 떄 응답 데이터, Etag 는 캐싱)
- 브라우저가 서버로 재요청시, If-None-Match 헤더에 캐싱된 Etag 를 담아서 요청 전송
-
서버는 신규 요청에 의해 만들어진 Etag 와 If-None-Match 헤더에 담긴 Etag 를 비교하여, 다르면 새로운 Etag 와 함께 응답 반환. 동일하면 304(Not Modified) Return Code 를 반환
- 브라우저는 304(Not Modified) Return Code 반환 시 기존 캐싱 데이터를 활용하며, 200 Return Code 로 반환 시, 1. 으로 돌아감
1.3) ETag(Entity Tag) ?
- 웹 리소스의 특정버전에 할당한 식별자
- ETag 사용 예시 :
etag 구현체를 필터로 등록하여 사용. 해당 구현체가 필터에 등록되어 Request, Response 에 etag 를 부여/검증한다.
@Bean |
위처럼 ShallowEtagHeaderFilter 를 등록 시 Etag 를 생성 및 검증해주며, Etag 가 존재하면 동일 URI 재요청 시 자동으로 If-None-Match 헤더에 ETag 가 추가해준다.
2. 적용 예시
2.1 Cache Control 활용
* WebMvcConfigurer 를 활용하여 정적 리소스 경로를 설정하였다 가정
@Configuration public class WebConfig implements WebMvcConfigurer { @Override public void addResourceHandlers(ResourceHandlerRegistry registry) { CacheControl cacheControl = CacheControl .maxAge(60, TimeUnit.SECONDS) .mustRevalidate(); registry.addResourceHandler("**/*.js") .addResourceLocations("classpath:/static/") .setCacheControl(cacheControl) ; } } |
: 위 설정 이후, **/*.js 의 요청은 Cache 이 설정됨
index.html
<script src ="http://localhost:8080/test.js"></script> |
- http://localhost:8080/ 첫 요청 시
index.html 반환 및 index.html 에 의해 test.js 요청
200 응답코드와 함께 설정한 Cache-Control 반환되며 해당 응답은 캐싱된다
- http://localhost:8080/ 두번째 요청 시
index.html 반환 및 index.html 에 의해 test.js 요청
요청이 캐싱 이후 60초 이내일 경우(max-age=60) 해당 캐시는 유효하다 판단하며 캐싱 데이터를 재사용한다
* 이 경우 서버와 통신하지 않기 때문에 데이터가 변경되더라도 브라우저에서는 알 수없음
* 단 브라우저 URL 입력창에 직접 호출하는 경우, 무조건 서버와 통신하여 변경 여부를 체크 (Chrome)
* from memory cache, from disk cache 두 종류가 있는데, 일반적인 memory, disk 차이와 비슷하다 어디에 저장할지는 Chrome 이 결정
2.2 Etag 활용
shallowEtagHeaderFilter 필터 설정
@Bean |
: 위 설정 이후, /* 의 요청은 Etag 가 설정됨
Cache-Control 설정
@RequestMapping("/") public void getIndexPage(... HttpServletResponse response) ... response.setHeader("Cache-Control","no-cache"); ... } |
- http://localhost:8080/ 첫 요청 시
Etag 와 함께 응답 반환
- http://localhost:8080/ 두번 째 요청 시
Request 에 Etag 를 함께 전송
Etag 검증 후 Not Modified(304) 반환
'Java' 카테고리의 다른 글
[SpringBoot] Gradle 변수 Property 활용 (0) | 2022.05.30 |
---|---|
[MyBatis] List 형식 멤버 변수 조회 (0) | 2021.02.12 |
[SpringBoot] H2 연동 (0) | 2020.07.21 |
[Spring] App 구동 후 자동 작업 실행 (0) | 2020.02.23 |
Stream Example (0) | 2020.01.05 |