사전 쿼터 정책
개념

쿼터 정책

gabury1고친 사람 github-actions[bot]

쿼터 정책은 한 사용자가 정해진 기간 동안 쓸 수 있는 양에 선을 긋습니다. 하루에 서버 기능을 몇 번 부를 수 있는지 정해 두는 것이 대표적입니다. 그 선 덕분에 사용자 하나가 서버를 독차지하지 못합니다. 저장 공간이나 클라우드 자원의 한도에도 같은 말을 씁니다. 이 항목은 서버 기능을 부르는 호출의 한도를 다룹니다.

쉽고 빠른 이해

쿼터 정책은 「누가 · 얼마 동안 · 얼마까지」 쓸 수 있는지 적어 둔 규칙입니다. 무료 요금제 사용자 한 명이 하루 1,000번까지 부를 수 있게 정해 두는 것이 그런 예입니다.

이게 없으면 사용자 한 명이 서버의 처리 능력과 비용을 끝없이 끌어다 씁니다. 요금제마다 쓸 수 있는 양을 가를 방법도 없습니다.

어떻게 도나:

  1. 요청이 오면 누구 몫으로 셀지 정합니다
  2. 그 몫이 이번 기간에 얼마나 남았는지 봅니다
  3. 남았으면 처리합니다. 남은 양에서 하나를 뺍니다. 바닥났으면 거절합니다. 다음 기간이 오면 다시 찹니다

대가는 선에 걸린 사용자가 치릅니다. 쓸 만한 이유가 있는 요청이라도 기간이 바뀔 때까지 막힙니다. 서버는 사용자마다 쓴 양을 늘 세어 두어야 합니다.

부르는 쪽이 하나뿐이라 나눌 몫이 없으면 쓸 까닭이 적습니다.

상세

휴대폰 요금제에는 한 달 데이터가 정해져 있습니다. 10기가바이트를 다 쓰면 인터넷이 끊기거나 느려집니다. 다음 달 1일이 되면 10기가바이트가 다시 찹니다.

API(Application Programming Interface)는 한 프로그램이 다른 프로그램의 기능을 부르는 창구입니다. 서버는 바깥 개발자에게 API 를 열어 두고 요청을 받습니다. API 를 부르는 쪽 프로그램을 클라이언트라고 부릅니다.

클라이언트는 요청마다 API 키를 실어 보냅니다. API 키는 서버가 클라이언트에게 내준 식별 문자열입니다. 서버는 이 키로 누가 보낸 요청인지 가릅니다.

쿼터는 한 사용자에게 정해진 기간 동안 나눠 준 사용량입니다. 앞의 휴대폰 요금제로 치면 한 달 10기가바이트가 쿼터입니다. 다음 달 1일에 다시 차는 것도 같습니다.

쿼터 정책은 그 쿼터를 누구에게, 얼마나, 어떤 기간으로 줄지 정한 규칙입니다. 「키 하나당 하루 1,000번」이 쿼터 정책 하나입니다.

서버 하나를 여럿이 나눠 쓰는 문제

API 서버 하나를 수많은 사용자가 나눠 씁니다. 서버가 하루에 처리할 수 있는 요청 수에는 끝이 있습니다. 요청을 처리하는 데 드는 돈에도 끝이 있습니다. 선이 없으면 사용자 하나가 그 몫을 혼자 끌어다 씁니다.

그 사용자에게 악의가 없을 수도 있습니다. 반복문을 잘못 짠 스크립트 하나가 밤새 같은 요청을 보내기도 합니다. 쿼터 정책은 이런 사고가 다른 사용자에게 번지지 않게 막습니다.

쿼터 정책은 요금을 가르는 기준도 됩니다. 무료 요금제는 하루 1,000번, 유료 요금제는 하루 10만 번처럼 요금제마다 다른 정책을 붙입니다. 쓰는 양이 늘어난 사용자는 더 높은 요금제로 옮기거나 한도를 올려 달라고 요청합니다.

거꾸로 서버를 부르는 쪽이 하나뿐이면 나눌 몫이 없습니다. 이럴 때는 쿼터 정책을 걸 까닭이 적습니다.

정책을 이루는 다섯 질문

쿼터 정책 하나는 질문 다섯에 답합니다. 아래 표는 「키 하나당 하루 1,000번, 넘으면 거절」이라는 정책을 다섯 칸으로 나눈 것입니다.

질문 이름 예
누구 몫으로 세나 쿼터 파티션 API 키 하나
무엇을 세나 쿼터 단위 요청 수
얼마 동안 세나 시간 창 하루
몇까지 허용하나 한도 1,000번
넘으면 어떻게 하나 초과 처리 거절

첫 칸부터 봅니다. 사용량은 대개 API 키마다 셉니다. 사용자 계정이나 요청을 보낸 IP(Internet Protocol) 주소마다 세기도 합니다.

이렇게 사용량을 따로 세는 한 묶음을 쿼터 파티션이라고 부릅니다. 같은 정책을 걸어도 남은 양은 묶음마다 따로입니다. 키 A 가 하루치를 다 써도 키 B 는 1,000번을 그대로 받습니다.

다음은 무엇을 셀지입니다. 이 세는 단위를 쿼터 단위라고 부릅니다. 가장 흔한 단위는 요청 수입니다. 주고받은 데이터의 바이트 수를 세기도 합니다.

요청마다 드는 품이 다르면 요청 하나를 여러 단위로 셉니다. 값 하나를 읽는 조회는 1, 여러 표를 훑는 집계는 10 으로 매기는 식입니다. 이러면 요청 하나가 쓰는 단위 수가 서버가 들인 품을 따라갑니다.

시간 창은 쿼터를 세는 기간입니다. 쿼터는 흔히 하루나 한 달처럼 길게 잡습니다. 기간이 지나면 쿼터가 다시 찹니다. 언제 어떻게 다시 차는지는 아래 「쿼터가 다시 차는 때」에서 두 방식으로 나눠 봅니다.

한도는 그 기간에 허용하는 양입니다. 한도를 넘었을 때 어떻게 하는지는 아래 「선을 넘은 요청을 다루는 방법」에서 봅니다.

쿼터와 속도 제한

쿼터와 가장 헷갈리는 이웃은 속도 제한입니다. 속도 제한은 짧은 순간에 몰리는 요청을 막습니다. 쿼터는 긴 기간에 쌓이는 총량을 막습니다. 아래 표가 둘을 견줍니다.

속도 제한 쿼터
세는 기간 초 · 분 하루 · 한 달
막는 것 한순간의 몰림 쌓인 총량
걸린 뒤 다시 쓰는 때 몇 초 뒤 다음 날 · 다음 달
주로 지키는 것 서버가 버티는 힘 비용과 요금제

둘은 서로를 대신하지 못합니다. 하루 1,000번 쿼터만 걸면 1,000번을 1초 안에 몰아 보내도 막지 못합니다. 초당 10번 속도 제한만 걸면 하루에 86만 번 넘게 보내도 막지 못합니다. 그래서 둘을 함께 겁니다.

이름은 쓰는 곳마다 섞입니다. 기간의 길이와 상관없이 나눠 준 사용량을 모두 쿼터라고 부르는 쓰임도 있습니다. 그런 곳에서는 「1분에 100번」도 쿼터 정책입니다.

여러 정책을 겹쳐 걸 때

이 절은 앞에서 본 넓은 쓰임을 따릅니다. 「1분에 100번」은 앞 절에서 속도 제한이라 부른 것입니다. 여기서는 이것도 쿼터 정책 하나로 셉니다. 둘 다 「기간 동안 몇 번」을 세는 같은 꼴이기 때문입니다.

한 사용자에게 정책을 여럿 걸기도 합니다. 「1분에 100번」과 「하루 1,000번」을 함께 거는 식입니다. 요청은 걸린 정책을 모두 통과해야 처리됩니다. 아래 그림은 두 정책을 차례로 묻는 흐름입니다.

flowchart TD
    A["요청이 온다"] --> B{"1분에 100번 중 남았나"}
    B -->|바닥났다| X["거절 · 1분 안에 다시 찬다"]
    B -->|남았다| C{"하루 1,000번 중 남았나"}
    C -->|바닥났다| Y["거절 · 다음 날 다시 찬다"]
    C -->|남았다| D["처리한다 · 두 정책에서 하나씩 뺀다"]

두 거절은 기다릴 시간이 다릅니다. 1분 정책에 걸린 클라이언트는 잠깐 쉬었다 보내면 됩니다. 하루 정책에 걸린 클라이언트는 다음 날까지 기다려야 합니다. 그래서 서버는 어느 정책에 걸렸는지 함께 알려 줍니다.

쿼터가 다시 차는 때

쿼터가 언제 다시 차는지는 두 방식으로 갈립니다. 첫째는 정해진 시각에 한꺼번에 차는 방식입니다. 매일 0시에 쓴 양을 0 으로 되돌리는 것이 그 예입니다.

이 방식은 기준 시간대를 함께 정해야 합니다. UTC(Coordinated Universal Time, 협정 세계시) 0시를 기준으로 삼으면 한국에서는 오전 9시에 쿼터가 찹니다.

정해진 시각에 차는 방식은 경계에서 몰림이 생깁니다. 하루 1,000번 쿼터라면 23시 59분에 1,000번을 보내고 0시 1분에 다시 1,000번을 보낼 수 있습니다. 2분 사이에 하루치의 두 배가 들어옵니다. 이 몰림은 함께 걸어 둔 속도 제한이 막습니다.

둘째는 기간을 지금 시각에 맞춰 밀고 가는 방식입니다. 지금부터 거슬러 지난 24시간 동안 쓴 양을 셉니다. 경계가 없으니 경계 몰림도 없습니다. 대신 빠짐없이 세려면 요청마다 시각을 남겨 두어야 합니다. 그만큼 저장 공간이 더 듭니다.

첫째 방식을 고정 윈도, 둘째 방식을 슬라이딩 윈도라고 부릅니다. 두 이름은 속도 제한에서도 같은 뜻으로 씁니다.

선을 넘은 요청을 다루는 방법

쿼터가 바닥난 뒤의 처리도 정책이 정합니다. 흔히 셋으로 나뉩니다.

방식 하는 일 사용자가 치르는 것
거절 다음 기간까지 요청을 받지 않는다 기다리는 시간
초과 요금 계속 받아 주고 넘은 만큼 돈을 더 매긴다 돈
늦추기 계속 받아 주고 처리 속도를 낮춘다 느려진 응답

거절할 때 HTTP(HyperText Transfer Protocol) API 는 흔히 HTTP 429(Too Many Requests) 응답을 돌려줍니다. 상태 코드는 요청이 어떻게 됐는지 알리는 세 자리 숫자입니다. 429 는 「요청이 너무 많다」는 뜻입니다.

응답에는 헤더가 붙습니다. 헤더는 HTTP 응답 본문 앞에 붙어 부가 정보를 적는 이름: 값 꼴의 줄입니다. 거절 응답은 Retry-After 헤더에 언제 다시 보내면 되는지 적어 보내기도 합니다.

초과 요금은 유료 요금제에서 씁니다. 사용자의 서비스가 멈추지 않는 대신 청구서가 늘어납니다. 그래서 쿼터의 일정 비율을 넘으면 미리 알림을 보내는 서비스가 많습니다.

정책을 클라이언트에게 알리기

클라이언트가 정책을 모르면 선에 부딪히고 나서야 압니다. 그래서 서버는 정책을 미리 알립니다. 가장 흔한 방법은 개발자 문서에 요금제별 한도를 표로 적는 것입니다.

응답 헤더로 알리는 방법도 있습니다. 한도를 알리는 헤더의 이름은 서비스마다 달랐습니다. 이것을 하나로 맞추려고 표준 단체가 RateLimit 헤더 필드를 다듬고 있습니다. 아직 표준으로 굳기 전의 초안입니다.

http
RateLimit-Policy: "daily";q=1000;w=86400
RateLimit: "daily";r=12;t=3600

첫 줄이 쿼터 정책입니다. "daily" 라는 이름의 정책이 86400초, 곧 하루(w) 동안 1,000번(q)을 허용합니다.

둘째 줄은 그 정책의 지금 상태입니다. 남은 양(r)은 12번입니다. t 는 쿼터가 다시 차기까지 남은 초입니다. 3600초 뒤에 다시 1,000번이 찹니다. 그때까지는 12번 안에서 써야 합니다.

정책이 이름으로 묶여 있어서 여러 정책을 쉼표로 이어 한꺼번에 알릴 수 있습니다.

같은 말을 쓰는 다른 분야

쿼터 정책이라는 말은 API 밖에서도 씁니다. 뜻의 뼈대는 같습니다. 누구에게 무엇을 얼마까지 허용할지 정한 규칙입니다.

운영체제는 사용자마다 쓸 수 있는 디스크 용량에 디스크 쿼터를 겁니다. 클라우드 서비스는 계정마다 띄울 수 있는 가상 머신 수나 프로세서 수에 쿼터를 겁니다.

이 둘은 기간 없이 지금 쥐고 있는 양을 셉니다. 파일을 지우거나 가상 머신을 끄면 그만큼 바로 돌아옵니다. API 쿼터가 기간 동안 쌓인 양을 세는 것과 다릅니다.

관련 항목

쿼터 정책과 함께 걸리는 다른 한도

속도 제한 · 스로틀링 · 동시성 제한 · 서비스 한도 · 부하 제한

쿼터 정책을 이루는 구성 요소

쿼터 · 쿼터 파티션 · 쿼터 단위 · 시간 창 · 파티션 키 · 유효 창

남은 쿼터를 세는 알고리즘

고정 윈도 카운터 · 슬라이딩 윈도 · 토큰 버킷 · 누출 버킷

쿼터에 걸린 클라이언트에 돌아가는 신호와 그 처리

HTTP 429 · Retry-After · RateLimit 헤더 필드 · 재시도 · 지수 백오프

쿼터를 따로 세는 단위가 되는 주체

API 키 · 사용자 계정 · 테넌트 · IP 주소 · 멀티테넌시

쿼터 정책을 요금과 잇는 수단

요금제 · 사용량 계획 · 사용량 기반 과금 · 초과 요금

같은 이름을 쓰는 다른 분야의 쿼터

디스크 쿼터 · 리소스 쿼터 · 하드 리밋 · 소프트 리밋

쿼터 정책이 속하는 상위 분류

API 설계 · API 게이트웨이 · 용량 계획 · 과부하 보호

다른 이름: quota policy · 할당량 정책 · API 쿼터 정책