← 목록으로

AI 캐시가 제값을 하려면

들어가며

AI API에서 말하는 캐시 히트가 무엇인지 이해가 잘 되지 않았다. 캐시라고 하니 응답 캐시를 떠올렸다. 같은 질문이 다시 오면 저장해 둔 답을 그대로 돌려주는 캐시다. 그렇게 생각하니 같은 질문도 아닌데 무엇이 캐시된다는 건지 알 수 없었다.

AI 에이전트를 만들려고 하니 비용이 많이 들어서 신경 쓸 수밖에 없게 되었다. 에이전트는 작업 하나를 끝낼 때까지 모델을 여러 번 부르고, 부를 때마다 앞선 대화를 전부 다시 보낸다. 에이전트를 만들려면 캐시 히트를 이해해야만 했다.

이해해야 할 것은 세 가지였다.

  1. 캐시에 저장되는 것은 무엇인가.
  2. 어떤 요청이 캐시에 적중하는가.
  3. 캐싱은 언제 이득인가.

캐시되는 것

AI API 문서들은 이 캐시를 프롬프트 캐싱이라고 부른다. 저장하는 것은 답이 아니라 모델이 입력을 읽으면서 계산한 중간 상태다.

prefill과 decode

LLM 호출은 두 단계로 나뉜다.

  1. prefill — 입력 토큰을 전부 읽는다. 토큰마다, 층(layer)마다 Key·Value 벡터를 계산한다. 뒤 토큰은 앞 토큰들의 K·V를 참고(attention)해 자기 의미를 정한다.
  2. decode — 그 K·V를 참고하며 출력 토큰을 하나씩 만든다.

입력 토큰 비용의 실체는 1번 계산이다. 프롬프트 캐싱은 이 계산 결과인 KV를 요청 사이에 보관했다가, 앞부분이 같은 다음 요청에서 다시 쓴다. OpenAI 문서도 캐시가 토큰이 아니라 KV 텐서를 저장하고, 이 텐서를 GPU 로컬 저장소에 둘 수 있다고 적는다.

시스템 프롬프트가 같은 요청 두 개가 오면, 두 번째 요청은 앞부분의 KV를 캐시에서 읽고 질문만 계산한다.

답은 매번 새로 만든다. 건너뛰는 것은 저장해 둔 앞부분의 prefill이고, 그만큼 비용과 첫 토큰까지의 지연(TTFT)이 준다.

응답 캐시와 다른 점

프롬프트 캐싱응답 캐싱
저장하는 것입력 앞부분의 KV 상태요청과 답의 쌍
저장하는 곳모델 제공자의 GPU 쪽API를 부르는 쪽(게이트웨이, Redis 등)
캐시 히트 조건앞부분이 같다요청이 통째로 같다
답매번 새로 생성저장된 답을 그대로 반환
잘 맞는 곳긴 공통 지시문, 문서, 대화 이력완전히 같은 질문이 반복되는 곳

응답 캐싱은 모델 제공자가 아니라 API를 부르는 쪽이 직접 붙이는 기능이다. 예를 들어 LiteLLM 프록시에서 cache 설정을 켜면, 같은 요청이 다시 올 때 모델을 부르지 않고 Redis에 저장해 둔 답을 돌려준다. 이름이 같아서 프롬프트 캐싱과 헷갈리기 쉽다.

응답 캐시로 이해하면 질문이 매번 다른데 적중하는 이유가 설명되지 않는다. 적중하는 것은 질문이 아니라 질문 앞에 붙은 공통 부분이다.

캐시 히트 조건

캐시에 적중하려면 세 가지가 맞아야 한다. 앞부분이 글자 하나까지 같아야 하고, 그 앞부분이 최소 길이를 넘어야 하고, 유효 시간 안에 다음 요청이 와야 한다.

앞부분 일치

토큰마다의 K·V는 그 앞의 모든 토큰에 의존한다. 앞에서 한 글자만 바뀌어도 그 뒤의 K·V가 전부 달라진다. 그래서 캐시는 처음부터 끊기지 않고 이어지는 구간에만 걸린다. Anthropic 문서도 캐시 표시를 붙인 블록까지 텍스트와 이미지가 100% 같아야 적중한다고 적는다.

Claude API에서 앞부분은 tools → system → messages 순서로 쌓인다. 어느 단계가 바뀌면 그 단계와 뒤 단계의 캐시가 모두 무효가 된다. 도구 정의를 하나 고치면 system과 messages 캐시까지 깨지는 식이다. tool_choice를 바꾸거나 이미지를 넣고 빼면 messages 캐시가 깨지고, thinking 설정을 바꾸면 messages 캐시는 항상, tools·system 캐시는 모델에 따라 깨진다.

그래서 고정된 내용은 앞에, 바뀌는 내용은 뒤에 둔다. 시스템 프롬프트 앞머리에 현재 시각 같은 값을 넣으면 캐시가 매번 깨진다.

앞부분이 같은 요청과 시스템 프롬프트 앞머리에 현재 시각이 들어간 요청은 캐시에서 읽는 양이 크게 다르다.

Claude Code로 확인했다. Claude Code 2.1.283에서 claude -p로 Sonnet 5를 불렀고, 도구와 MCP 서버는 --tools "" --strict-mcp-config로 껐다. 응답의 cache_creation_input_tokens를 쓰기, cache_read_input_tokens를 읽기로 봤다.

같은 대화를 이어가면서 시스템 프롬프트 끝에 덧붙인 한 줄만 바꿨다. Claude Code는 기본 설정에서 시스템 프롬프트를 대화 첫 요청 때 고정하기 때문에, 이 실험은 --system-prompt-snapshot off로 요청마다 새로 만들게 했다.

호출조건쓰기읽기
1새 대화, 덧붙인 줄 A21,7313,406
2이어가기, A 그대로7925,137
3이어가기, A를 B로 바꿈21,8893,406

2번째 호출은 새로 붙은 대화 79토큰만 쓰고 나머지를 전부 읽었다. 3번째 호출은 시스템 프롬프트 끝의 한 줄이 바뀌자 그 뒤의 21,889토큰을 다시 썼다. 읽은 것은 바뀐 지점보다 앞쪽의 3,406토큰뿐이다.

캐시는 대화가 아니라 앞부분의 내용에 붙는다. 다른 대화에서 1번째 호출과 똑같은 입력을 보내자, 쓰기 없이 25,137토큰을 전부 읽었다. 새 대화의 첫 호출이 3,406토큰을 읽은 것도 같은 이유로 보인다.

Claude Code가 기본으로 시스템 프롬프트를 고정하는 것도 이 때문으로 보인다. 기본 설정인 --system-prompt-snapshot on은 대화 첫 요청의 시스템 프롬프트를 기록해 두고, 이후 요청과 이어가기에서 그대로 다시 보낸다. 이 설정으로 새 대화를 A로 시작한 뒤 B를 넘겨 이어가자 앞부분 25,216토큰을 전부 읽었다. 기록해 둔 A가 그대로 나가서 앞부분이 바뀌지 않았기 때문이다.

최소 길이

캐시할 앞부분은 모델마다 정한 최소 길이를 넘어야 한다. Claude API 기준으로 Opus 5.5와 Opus 5는 512토큰, Sonnet 5는 1,024토큰, Haiku 4.5는 4,096토큰이다. 이보다 짧으면 캐시 없이 처리되고 에러도 나지 않는다. cache_control을 붙였는데 응답의 캐시 쓰기와 읽기가 모두 0이면 이것부터 의심한다.

Sonnet 5에서 800토큰과 1,600토큰 앞부분에 똑같이 캐시 표시를 붙이면 결과가 갈린다.

유효 시간

캐시는 기본 5분 동안 유지되고, 쓰기 요금을 더 내면 1시간으로 늘릴 수 있다. 유효 시간은 캐시를 쓸 때마다 추가 비용 없이 갱신된다. 처음 만든 뒤 5분이 아니라 마지막으로 쓴 뒤 5분이다. 5분 안쪽 간격으로 요청이 계속 오면 캐시는 계속 산다.

5분 TTL에서 요청이 0분, 3분, 7분, 15분에 오면 유효 시간은 이렇게 늘어나다가 끝난다.

시간은 응답이 끝난 때가 아니라 요청이 시작된 때부터 잰다. 응답을 스트리밍하는 데 4분이 걸렸다면, 5분 TTL에서는 응답이 끝나고 1분 안에 다음 요청이 시작돼야 적중한다.

이 실험에서 Claude Code는 캐시를 전부 1시간 TTL로 썼다. 응답의 cache_creation에 쓰기가 모두 ephemeral_1h_input_tokens로 찍혔다. 같은 대화를 시간을 두고 이어갔다.

호출앞 호출과 간격쓰기읽기
121,7163,397
220분 37초7325,113
361분 34초21,8623,397

2번째 호출은 5분을 훌쩍 넘겼지만 1시간 안이라 전부 읽었다. 이 호출로 유효 시간이 다시 1시간 늘었다. 3번째 호출은 그 1시간이 지난 뒤라 대화 부분 21,862토큰을 다시 썼다. 3,397토큰은 여전히 읽었는데, 다른 호출이 계속 쓰는 공통 앞부분이라 살아 있었던 것으로 보인다.

캐시가 제값을 하려면

쓰기와 읽기의 가격

캐싱을 쓰면 입력 요금이 두 가지로 나뉜다. 캐시에 쓰는 토큰은 기본 입력가보다 비싸고, 캐시에서 읽는 토큰은 훨씬 싸다.

기본 입력가 대비Claude 5분 TTLClaude 1시간 TTLOpenAI GPT-5.6 이상OpenAI 이전 모델
쓰기1.25배2배1.25배추가 요금 없음
읽기0.1배0.1배0.1배모델마다 다름

Claude의 읽기 배수에는 예외가 있다. Opus 5.5는 0.05배, Fable 5.1과 Mythos 5.1은 0.025배다. Bedrock의 Claude도 쓰기가 비싸고 읽기가 싼 구조는 같지만, 정확한 금액은 Bedrock 가격표를 봐야 한다. Claude API의 Sonnet 5로 치면 100만 토큰당 입력이 $2, 5분 쓰기가 $2.50, 1시간 쓰기가 $4, 읽기가 $0.20이다.

3장의 앞부분 변경 실험을 금액으로 바꿔 보면 차이가 크다. Claude Code는 구독이라 실제로 청구되지는 않지만, claude -p 결과의 total_cost_usd에 API 단가로 환산한 금액을 남긴다. 세션 누적값이라 표에는 호출마다 늘어난 만큼을 적었다. 이 실험은 1시간 TTL로 썼기 때문에 쓰기가 2배로 매겨졌다.

호출쓰기읽기환산액
캐시에 쓴 호출21,7313,406$0.0876
캐시에서 읽은 호출7925,137$0.0054
캐시 없이 보냈다면00$0.0503

마지막 줄은 캐시를 거치지 않은 2토큰까지 더한 25,139토큰을 캐시 없이 기본 입력가로 계산한 값이다. 캐시에 쓴 호출은 캐시 없이 보냈을 때보다 1.7배 비싸고, 캐시에서 읽은 호출은 그 10분의 1 수준이다.

요금 말고 달라지는 것도 있다. Claude API와 Bedrock은 캐시에서 읽은 토큰을 분당 입력 토큰 한도에서 빼 준다. OpenAI API는 캐시에서 읽은 토큰도 한도에 넣는다.

쓰기가 비싸고 읽기가 싼 이유는 공식 문서가 직접 설명하지 않는다. 내 해석은 이렇다. KV는 토큰마다 층 수만큼 쌓여 원문보다 훨씬 크고, 비싼 GPU 쪽 저장소에 둬야 한다. 쓰기 요금은 이 보관 부담이고, 읽기 요금은 prefill을 건너뛴 만큼의 할인이다. 유효 시간이 분 단위로 짧은 것도 같은 이유로 보인다.

손익분기

기본 입력가를 1로 두고 같은 앞부분으로 요청을 여러 번 보낸다고 하자. 캐시가 없으면 요청마다 1을 낸다. 5분 TTL 캐시를 쓰면 첫 요청이 1.25를 내고, 이후 요청은 0.1씩 낸다. 재사용 1번마다 0.9를 아끼므로, 쓰기에 더 낸 0.25를 되찾으려면 쓰기 1번당 평균 0.28번 이상 재사용돼야 한다.

TTL쓰기에 더 내는 값재사용 1번에 아끼는 값본전 조건
5분0.250.9쓰기 1번당 재사용 0.28번 이상
1시간1.00.9쓰기 1번당 재사용 1.11번 이상

캐시 하나로 보면 5분 TTL은 한 번만 재사용돼도, 1시간 TTL은 두 번 재사용돼야 캐시가 없을 때보다 싸다.

적중률로 바꾸면 5분 TTL은 22%, 1시간 TTL은 53%다. 같은 앞부분으로 온 요청 가운데 이만큼이 캐시에서 읽어야 본전이다. 읽기가 0.05배인 Opus 5.5에서는 본전 조건이 0.26번과 1.05번으로 조금 내려간다.

가로축을 적중률로 놓고 요청 1건의 비용을 그리면, 두 TTL 선이 22%와 53%에서 캐시 없음 선 아래로 내려간다.

캐시 없음5분 TTL1시간 TTL요청 1건 비용 (캐시 없음 = 1)0.00.51.01.52.01시간 TTL5분 TTL캐시 없음0%100%22%53%적중률

재사용되지 않는 캐시는 순손해다. 적중률 0%에서 5분 TTL은 25%, 1시간 TTL은 100%를 더 낸다.

요청이 5분보다 자주 오면 5분 TTL이 계속 갱신되므로 1시간 TTL을 쓸 이유가 없다. Anthropic 문서는 1시간 TTL을 5분보다 뜸하지만 1시간 안에는 다시 쓰는 프롬프트에 권한다. 5분 넘게 걸리는 보조 에이전트나, 사용자가 5분 안에 답하지 않을 긴 대화가 그 예다.

에이전트와 챗봇

같은 캐싱이라도 요청이 오는 모양에 따라 얻는 것이 크게 다르다. 두 경우를 나란히 놓았다. 하나는 에이전트인 Claude Code이고, 다른 하나는 슬랙에서 질문을 받는 챗봇이다.

에이전트

에이전트는 작업 하나를 끝낼 때까지 모델을 연달아 부른다. Claude Code에 BullMQ 연재 5편을 파일 하나씩 읽고 한 줄씩 요약하게 했더니 21초 동안 API를 7번 불렀다. 실험 조건은 3장과 같고, 도구는 Read와 Glob만 열었다.

호출쓰기읽기
126,7630
225226,763
37,72627,015
48,49534,741
519,32543,236
617,39862,561
712,94279,959

호출할 때마다 앞선 대화를 전부 다시 보내므로 읽기가 0에서 8만 토큰까지 불어난다. 새로 쓰는 것은 방금 읽은 파일 내용과 모델의 답뿐이다. 호출 간격이 2~9초라 캐시가 만료될 틈도 없다.

입력 비용은 캐시가 없을 때의 $0.73에서 $0.43으로 42% 줄었다. 짧은 작업이라 새로 쓰는 양이 많았고, 1시간 TTL이라 쓰기가 2배로 매겨졌다. 5분 TTL이었다면 61%가 줄었다.

작업이 길어지면 읽기 비중이 커진다. 이 블로그 레포에서 Claude Code로 작업한 세션 기록을 모았다. 2026년 8월 29일부터 9월 28일까지의 응답 1,110개다.

  • 입력 토큰의 97.6%가 캐시 읽기, 2.4%가 캐시 쓰기였다. 캐시를 거치지 않은 입력은 0.01%도 안 된다.
  • 쓰기를 2배, 읽기를 0.1배로 치면 캐시가 없을 때의 0.15배다. 이 세션들이 주로 쓴 Fable 5.1은 읽기가 0.025배라 실제 비용은 이보다 낮다.
  • 같은 세션 안의 호출 간격은 중앙값이 20초였고, 94.5%가 5분 안, 99.4%가 1시간 안이었다. 이 세션들에서 Claude Code는 캐시를 모두 1시간 TTL로 썼으므로 거의 모든 호출이 적중한다.

챗봇

챗봇은 LiteLLM 게이트웨이를 거쳐 Bedrock의 Claude Sonnet 5를 부른다. 요청은 시스템 프롬프트 뒤에 질문, 지식 베이스에서 찾은 사례 8건, 스레드 맥락이 붙는 구조다. 답이 길어 끊기면 지금까지 쓴 답을 붙여 이어 쓰게 한다.

3분 간격으로 온 두 질문과 이어받기 요청을 나란히 놓으면 직전 요청과 같은 부분이 어디인지 보인다.

공통 앞부분은 시스템 프롬프트 하나다. 파일 크기로 추정하면 약 1,500토큰이라 Sonnet 5의 최소 길이 1,024토큰은 넘을 것으로 보이지만, 재 보지는 않았다. 재사용 기회는 두 가지다. 질문이 5분 안에 이어 오거나, 답이 길어 이어받기를 할 때다.

운영 로그로 2026년 8월 18일부터 9월 23일까지의 답변 63건을 봤다. 질문 간격 62개 가운데 36개(58%)가 5분 안이었다. 드문드문 올 거라고 예상했는데, 한 스레드에서 이어 묻는 식으로 몰려 왔다. 5분 안에 이어 온 질문이 모두 적중한다고 치면 적중률은 58%로, 5분 TTL의 본전인 22%를 넘는다. 이어받기는 63건 가운데 3건이었다.

다만 절대량이 작다. 5주에 63건이고, 적중해도 요청마다 1,500토큰의 90%를 아낀다.

명시적 캐싱을 넣지 않아도 Bedrock의 암묵적 캐싱이 이미 일부 적용되고 있을 수 있다. 챗봇이 응답의 캐시 필드를 로그에 남기지 않아서 지금은 알 수 없다. 그래서 cache_control을 넣기 전에 응답 usage의 캐시 필드를 로그에 남기는 것이 먼저다. 실제 적중률을 보고 판단한다.

비교

에이전트(Claude Code)슬랙 챗봇
요청 간격중앙값 20초, 94.5%가 5분 안58%가 5분 안
TTL1시간5분
캐시할 수 있는 앞부분입력 거의 전부시스템 프롬프트 약 1,500토큰
적중률97.6%(토큰 기준, 실측)58%(질문 기준, 추정)
앞부분 비용(캐시 없음 = 1)0.150.58(추정)
규모한 달 응답 1,110개5주 답변 63건

둘 다 본전은 넘는다. 다만 에이전트는 입력 거의 전부가 캐시를 거치고, 챗봇은 요청마다 1,500토큰 남짓에만 캐시가 걸린다.

게이트웨이 라우팅

캐시는 요청을 처리한 곳에 쌓인다. 게이트웨이가 같은 모델을 여러 deployment나 리전으로 나눠 보내면, 앞부분이 같은 요청도 다른 곳으로 가서 캐시를 읽지 못한다. 로드밸런싱으로 처리량과 가용성을 얻는 대신 적중률을 잃는다.

앞부분이 같은 요청 4개를 세 deployment에 나눠 보낼 때와 한 곳으로만 보낼 때를 비교하면 캐시에 쓰는 횟수가 달라진다.

모델 제공자 안에서도 마찬가지다. OpenAI 문서는 캐시된 상태가 머신마다 따로 있어서, 맞는 캐시를 가진 머신에 요청이 닿아야 재사용된다고 적는다. Bedrock 문서도 리전을 넘나드는 cross-region 추론에서는 수요가 몰릴 때 캐시 쓰기가 늘 수 있다고 적는다.

게이트웨이 설정에서 코드리뷰 봇이 쓰는 모델 별칭만 deployment 1개로 고정해 둔 것도 이 때문이다. 다른 별칭은 여러 deployment로 나눠 보낸다. 설정 주석에 따르면 봇이 턴마다 8만 토큰 넘게 다시 보내서, 지연보다 캐시 적중률이 비용을 좌우한다. 4장의 배수로 치면 적중한 턴은 입력 비용이 10분의 1이 되고, 다른 deployment로 가서 놓친 턴은 5분 TTL 기준 1.25배를 낸다. 다만 deployment를 하나로 고정하면 그 deployment가 한도에 걸리거나 멈췄을 때 같은 별칭 안에서는 돌아갈 곳이 없다.

deployment를 하나로 묶지 않고도 캐시를 지킬 수 있다. LiteLLM은 router_settings.optional_pre_call_checks에 prompt_caching을 넣으면 캐시를 쓴 호출을 기억해 두고, 같은 캐시를 읽으려는 다음 호출을 캐시를 쓴 deployment로 보낸다.

router_settings:
  optional_pre_call_checks: ["prompt_caching"]

LiteLLM 문서는 요청 로그에서 두 번째 호출이 캐시를 읽었는지, Model ID가 첫 호출과 같은지 확인하라고 안내한다.

제공자별 설정

켜는 법과 확인할 응답 필드는 제공자마다 다르다. 먼저 짧게 비교하면 이렇다.

Claude APIBedrock의 ClaudeOpenAI API
기본 동작표시해야 캐시표시 없이도 시도자동으로 캐시
표시 개수요청당 4개요청당 4개요청당 4개(GPT-5.6 이상)
최소 길이모델별 512~4,096토큰Claude API와 같음1,024토큰(GPT-5.6 이상)
TTL5분, 1시간5분, 1시간30분 이상(GPT-5.6 이상)
공유 범위워크스페이스조직조직

Claude API

블록에 cache_control을 붙인다. 요청 최상위에 하나만 두면 마지막 블록에 자동으로 걸린다. 표시에서 앞으로 20블록까지만 거슬러 찾으므로, 앞부분이 길면 표시를 여러 개 둔다. 최소 길이는 Opus 5.5·Opus 5·Fable 5.1이 512토큰, Sonnet 5가 1,024토큰, Haiku 4.5가 4,096토큰이다. 응답의 cache_creation_input_tokens가 쓰기, cache_read_input_tokens가 읽기다.

Bedrock의 Claude

표시가 없어도 암묵적 캐싱을 시도하지만 적중은 보장하지 않는다. 명시하려면 Converse API는 cachePoint, InvokeModel은 cache_control을 붙인다. 최소 길이는 Claude API와 같고 Opus 4.7만 4,096토큰으로 다르다.

Converse 응답은 cacheWriteInputTokens와 cacheReadInputTokens로 쓰기와 읽기를 알려 준다. inputTokens는 캐시를 거치지 않은 토큰만 세므로, 보낸 입력 전체는 세 값을 더해야 나온다. 5장의 챗봇처럼 캐시 필드를 로그에 남길 때는 세 값을 함께 남겨야 적중률을 계산할 수 있다.

OpenAI API

기본으로 켜져 있다. GPT-5.6 이상은 콘텐츠 블록에 prompt_cache_breakpoint를 붙여 캐시할 위치를 정할 수 있다. 최소 길이는 GPT-5.6 이상에서 1,024토큰이고, 이전 모델은 요청 설정에 따라 다르다. 보관 시간은 GPT-5.6 이상이 마지막 쓰기나 재사용 뒤 최소 30분이고, 이전 모델은 보통 5~10분에 24시간 옵션이 있다.

응답의 input_tokens_details.cached_tokens가 읽기, input_tokens_details.cache_write_tokens가 쓰기다. 캐시는 조직끼리 공유하지 않고, 리전 처리 경계를 넘어 재사용하지도 않는다.

게이트웨이

게이트웨이에서 켤 수도 있다. LiteLLM은 cache_control_injection_points로 지정한 메시지의 마지막 블록에 cache_control을 대신 붙여 준다. 클라이언트 코드를 고치지 않고 시스템 프롬프트 뒤에 캐시 표시를 달 수 있다. 모델마다 넣어도 되고, router_settings.default_litellm_params에 넣으면 모든 모델에 걸린다.

model_list:
  - model_name: claude-sonnet-5
    litellm_params:
      model: bedrock/us.anthropic.claude-sonnet-5
      cache_control_injection_points:
        - location: message
          role: system

정리

서문의 세 질문으로 돌아가자.

  • 캐시에 저장되는 것 — 답이 아니라 입력 앞부분을 prefill하며 계산한 KV다. 답은 매번 새로 만든다.
  • 적중하는 요청 — 앞부분이 글자 하나까지 같고, 그 앞부분이 최소 길이를 넘고, 유효 시간 안에 온 요청이다. 질문이 달라도 앞부분이 같으면 적중한다.
  • 이득인 때 — 쓰기 1번당 5분 TTL은 0.28번, 1시간 TTL은 1.11번 넘게 재사용될 때다. 적중률로는 22%와 53%다.

캐싱을 켤지는 이 순서로 따져 볼 수 있다.

  1. 요청마다 같은 앞부분이 최소 길이를 넘는지 본다. 도구 정의와 시스템 프롬프트처럼 고정된 내용을 앞에, 시각이나 질문처럼 바뀌는 값을 뒤에 둔다.
  2. 같은 앞부분으로 오는 요청의 간격을 잰다. 5분 안에 오는 비율이 22%를 넘으면 5분 TTL로 본전이다. 5분보다 뜸하지만 1시간 안에 다시 오는 요청이 많으면 1시간 TTL을 따진다.
  3. 절대량을 본다. 적중률이 높아도 요청이 적거나 앞부분이 짧으면 아끼는 금액이 작다.
  4. 게이트웨이가 요청을 여러 deployment로 나눠 보내면, 한 곳으로 고정하거나 캐시를 쓴 곳으로 보내게 한다.
  5. 켜기 전과 켠 뒤에 응답의 캐시 쓰기·읽기 필드를 로그에 남겨 실제 적중률을 확인한다.

에이전트는 호출이 몇 초 간격으로 이어지고 매번 대화 전체를 다시 보내서 1번과 2번은 거의 항상 맞는다. 남는 일은 앞부분을 바꾸지 않는 것과 요청을 흩뜨리지 않는 것이다.