22장. Prefetch
이 장에서는 콘텐츠를 미리 캐시에 배포하는 Prefetch에 대해 설명한다.
Prefetch는 관리자가 Manager port를 통해 Job(Prefetch 파일목록)을 업로드 하는 것으로 동작한다. 업로드 된 Job은 설정시간에 순차적으로 다운로드 된다.
API
Prefetch용 HTTP API를 지원한다.
Job 등록
Job 조회 (+ 상태필터)
Job 삭제
모든 API는 Job 단위로 동작한다.
Job 등록
관리자는 다음 주소로 Job을 POST 메소드로 업로드 한다.
http://{STON-IP}:{ManagerPort}/prefetch
업로드 파일 구조는 가상호스트 별로 URL 목록이 나열된 구조이다.
아래는 샘플 파일목록이다.
{
"prefetch" : {
"schedule" : "now",
"vhosts" : [
{
"vhost" : "foo.com",
"urls" : [
{ "url" : "/log.zip" },
{ "url" : "/sample/data" },
{ "url" : "/product/catalog/beauty.pdf?code=1203" }
]
},
{
"vhost" : "bar.com",
"urls" : [
{ "url" : "/demo.zip", "header1": "1323901283" },
{ "url" : "/search/topN.list", "keyword": "shoe" }
]
}
]
}
}
규칙은 다음과 같다.
url
은 가상호스트 하위에 위치하며 반드시 “/” 로 시작해야 한다.url
의 대소문자 구분은 가상호스트 설정을 따른다.가상호스트가 Accept-Encoding헤더 를 구분하도록 설정되었다면 다운로드는 ON/OFF 를 구분하여 2번 이루어진다.
접수된 파일목록은 예정된 시간에 수행되지만
schedule
속성이now
인 경우 (현재 작업 중인 prefetch가 없다면) 즉시 시작된다.(bar.com의 예와 같이) 만약 가상호스트에 별도의 커스터마이징 모듈이 연동되어 있다면 예제의
header1
나keyword
처럼 커스텀 필드로 확장 가능하다.
Job 목록조회
Prefetch 진행 상태를 API로 조회 가능하다.(최대 1,000개)
http://{STON-IP}:{ManagerPort}/prefetch/list
http://{STON-IP}:{ManagerPort}/prefetch/list?status=...
status
Job 상태 필터링wait
대기 중downloading
다운로드 중success
성공fail
실패
응답 예제는 다음과 같다.
{
"prefetch-list":[
{
"id":"1579492339-6c00ab48",
"type":"now",
"status":"success",
"total-url-count":4,
"success-url-count":4,
"registration-time":"2020-01-20T03:52:19Z",
"execution-time":"2020-01-20T03:52:20Z",
"completion-time":"2020-01-20T03:52:21Z"
}, {
"id":"1579492340-6c0b82b8",
"type":"now",
"status":"success",
"total-url-count":4,
"success-url-count":4,
"registration-time":"2020-01-20T03:52:20Z",
"execution-time":"2020-01-20T03:52:22Z",
"completion-time":"2020-01-20T03:52:22Z"
}, {
"id":"1579492341-6c0ba138",
"type":"now",
"status":"success",
"total-url-count":4,
"success-url-count":4,
"registration-time":"2020-01-20T03:52:21Z",
"execution-time":"2020-01-20T03:52:23Z",
"completion-time":"2020-01-20T03:52:23Z"
}, {
"id":"1579492341-6c0bae98",
"type":"now",
"status":"success",
"total-url-count":4,
"success-url-count":4,
"registration-time":"2020-01-20T03:52:21Z",
"execution-time":"2020-01-20T03:52:24Z",
"completion-time":"2020-01-20T03:52:25Z"
}, {
"id":"1579492342-6c0dca98",
"type":"now",
"status":"success",
"total-url-count":4,
"success-url-count":4,
"registration-time":"2020-01-20T03:52:22Z",
"execution-time":"2020-01-20T03:52:26Z",
"completion-time":"2020-01-20T03:52:26Z"
}, {
"id":"1579492404-6c0f13f8",
"type":"now",
"status":"fail",
"total-url-count":4,
"success-url-count":0,
"registration-time":"2020-01-20T03:53:24Z",
"reservation-time":"2020-01-20T03:53:55Z",
"execution-time":"2020-01-20T03:53:55Z",
"completion-time":"2020-01-20T03:53:55Z",
"last-failure-time":"2020-01-20T03:53:55Z",
"failure-url":"/hideface/test1234.jpg"
}
]
}
응답필드 목록은 다음과 같다.
id
- Job IDtype
- Job 스케쥴링 타입 (now
,reserved
,schedule
)status
- wait, downloading, success, failtotal-url-count
- 전체 URL 개수success-url-count
- 다운로드 성공 URL 개수registration-time
- Job 등록 시간reservation-time
- (예약 Job인 경우) 예약된 시간execution-time
- Job 수행 시간completion-time
- Job 완료 시간last-failure-time
- 마지막 Job 실패 시간failure-url
- 실패한 URL
모든 시간표현은 ISO 8601규격으로 제공된다.
Job 상세조회
특정 Job만을 조회하고 싶을 경우 등록된 id
를 통해 조회 가능하다.
http://{STON-IP}:{ManagerPort}/prefetch/item?id=1579492339-6c00ab48
Job 취소
아직 수행되지 않은 Job에 한하여 삭제가 가능하다.
http://{STON-IP}:{ManagerPort}/prefetch/item/remove?id=1579492339-6c00ab48
POST 지원
prefetch는 GET 메소드를 기본으로 한다.
POST 메소드 원본서버와 통신해야 할 경우 다음과 같이 method
, post-body
필드를 확장한다.
{
"prefetch" : {
"schedule" : "now",
"vhosts" : [
{
"vhost" : "foo.com",
"urls" : [
{
"url" : "/log.zip",
"method" : "post",
"post-body" : "home=Cosby&favorite+flavor=flies"
},
{
"url" : "/sample/data",
"method" : "post",
"post-body" : "--boundary\nContent-Disposition: form-data; name=\"field1\""
}
]
}
]
}
}
method
POST 다운로드의 경우 항상post
이다.post-body
POST 메소드로 원본서버에 보낼 Body 데이터.
스케쥴링
파일을 원하는 시점에 미리 캐싱 해두면 서비스 품질 향상과 원본 부하분산 효과를 동시에 얻을 수 있다.
스케쥴링에는 3가지 방식이 제공된다.
Prefetch 시간을 고정한다.
schedule
속성을 생략한다.# server.xml - <Server> <Cache> <Prefetch> <Time>04:00</Time> <Concurrent>5</Concurrent> <Log Type="size" Unit="5" Retention="5" SysLog="OFF" Compression="OFF">ON</Log> </Prefetch> </Cache>
<Time> (기본: AM 4)
등록된 prefetch 를 수행할 시간을 설정한다. 오후 11시 10분을 설정하고 싶다면 23:10으로 설정한다.<Concurrent> (기본: 5)
동시에 다운로드를 진행할 세션 수를 설정한다.<Log>
Prefetch 상세로그를 구성한다.
즉시 Prefetch를 수행한다.
schedule
속성을now
로 지정한다.{ "prefetch" : { "schedule" : "now", "vhosts" : [ ... (생략) ... ] } }
Prefetch 시간을 예약한다.
schedule
속성을reserved
로 지정하고reservation-time
을 반드시 ISO-8601 규격으로 명시한다.{ "prefetch" : { "schedule" : "reserved", "reservation-time" : "2019-11-19T09:00:00Z", "vhosts" : [ ... (생략) ... ] } }
수행정책은 다음과 같다.
Prefetch 스케쥴러의 기본 동작은 FIFO(First Input First Out) 이다.
현재 진행 중인 Prefetch 목록은 간섭받지 않는다.
schedule
이now
인 목록이 그렇지 않은 목록보다 항상 우선한다. ``now``목록끼리는 FIFO 로 수행된다.schedule
이reserved
인 목록의 시간이 같을 경우 FIFO 로 수행된다.schedule
이reserved
인 목록이 경쟁에서 밀려 수행시간이 지나면 다른reserved
보다 우선 수행된다.
Polling
정해진 시간에 약속된 URL을 호출하여 Prefetch Job을 수행한다.
# server.xml - <Server>
<Prefetch>
... (생략)...
<Polling>
<Url>http://example.com/endpoint?key=value</Url>
<Time>03:00</Time>
<Retry>3</Retry>
</Polling>
</Prefetch>
<Url>
Prefetch Job을 게시할 URL<Time>
수행시간 (00:00 ~ 23:59)<Retry>
URL호출 실패시 재시도 횟수
재시도 정책
일시적인 네트워크 장애 등으로 인해 다운로드에 문제가 발생할 수 있다. 재시도 정책을 통해 Prefetch 신뢰도를 향상시킬 수 있다.
# server.xml - <Server>
<Cache>
<Prefetch>
<MaxRetry>3</MaxRetry>
<RetryInterval>60</RetryInterval>
</Prefetch>
</Cache>
<MaxRetry> (기본: 3회)
다운로드 실패시 재시도 횟수 (최소 1회)<RetryInterval> (기본: 60초)
재시도 간격 (최소 1초)
로그
Prefetch 로그는 2가지로 구분된다.
먼저 Prefetch 목록의 접수와 실행은 info.log에 기록된다.
2019-11-19 16:54:17 [INFO] [PREFETCH] Register task. (Task: 1574148743_4.reserved)
2019-11-19 16:54:18 [INFO] [PREFETCH] Start task. (Task: 1574148743_4.reserved)
2019-11-19 16:54:20 [INFO] [PREFETCH] Complete task. (Task: 1574148743_4.reserved)
2019-11-19 17:00:00 [INFO] [PREFETCH] Start task. (Task: 1574150029_2.scheduled)
2019-11-19 17:00:03 [INFO] [PREFETCH] Complete task. (Task: 1574150029_2.scheduled)
2019-11-19 17:00:04 [INFO] [PREFETCH] Start task. (Task: 1574149879_0.scheduled)
위 로그 파일에서 알 수 있듯이 업로드된 형태 그대로 prefetch 디렉토리에 기록된다. 등록된 목록은 예약시점인 오전 2시부터 순차적으로 진행됨을 알 수 있다.
Prefetch를 수행하는 Prefetcher는 Loopback(127.0.0.1) 클라이언트이다. 따라서 Prefetcher가 STON을 원본서버로 바라보는 형태의 Origin 로그 형식으로 기록된다.
#date time cs-sid cs-tcount c-ip cs-method s-domain cs-uri s-ip sc-status cs-range sc-sock-error sc-http-error sc-content-length cs-requestsize sc-responsesize sc-bytes time-taken time-dns time-connect time-firstbyte time-complete cs-reqinfo cs-acceptencoding sc-cachecontrol s-port x-vhostname x-task
2019-11-19 17:00:03 10 1 127.0.0.1 GET 127.0.0.1 /hideface/test1.mp4?v=3 127.0.0.1 200 - - - 50029902 111 324 50029902 2288 0 0 3 2285 http gzip+deflate - 80 - 0 foo.com 1574150029_2.now
2019-11-19 17:00:03 9 1 127.0.0.1 GET 127.0.0.1 /hideface/test1.mp4?v=3 127.0.0.1 200 - - - 50029902 79 324 50029902 2354 0 0 3 2351 http - - 80 - 0 foo.com 1574150029_2.now
2019-11-19 17:00:03 12 1 127.0.0.1 GET 127.0.0.1 /hideface/test2.mp4?v=4 127.0.0.1 200 - - - 49547420 111 324 49547420 2406 0 0 3 2403 http gzip+deflate - 80 - 0 foo.com 1574150029_2.reserved
2019-11-19 17:00:03 11 1 127.0.0.1 GET 127.0.0.1 /hideface/test2.mp4?v=4 127.0.0.1 200 - - - 49547420 79 324 49547420 2408 0 0 3 2405 http - - 80 - 0 foo.com 1574150029_2.scheduled
2019-11-19 17:00:04 18 1 127.0.0.1 GET 127.0.0.1 /hideface/test1.mp4?v=10 127.0.0.1 200 - - - 50029902 112 324 50029902 172 0 1 2 170 http gzip+deflate - 80 - 0 foo.com 1574149879_0.scheduled
2019-11-19 17:00:04 20 1 127.0.0.1 GET 127.0.0.1 /hideface/test2.mp4?v=11 127.0.0.1 200 - - - 49547420 112 324 49547420 171 0 0 2 169 http gzip+deflate - 80 - 0 foo.com 1574149879_0.now
2019-11-19 17:00:04 19 1 127.0.0.1 GET 127.0.0.1 /hideface/test2.mp4?v=11 127.0.0.1 200 - - - 49547420 80 324 49547420 173 0 1 2 171 http - - 80 - 0 foo.com 1574149879_0.scheduled
2019-11-19 17:00:04 17 1 127.0.0.1 GET 127.0.0.1 /hideface/test1.mp4?v=10 127.0.0.1 200 - - - 50029902 80 324 50029902 173 0 0 2 171 http - - 80 - 0 foo.com 1574149879_0.scheduled.now
모든 필드는 Origin 로그 형식과 유사하며 다음 확장필드를 가진다.
x-vhostname
가상호스트명x-task
prefetch 파일명