Pembatasan Laju API AI: Cara Kerjanya dan Cara Menanganinya
Setiap API AI memiliki batasan laju. Terkena batasan ini saat pengembangan itu menjengkelkan. Terkena batasan ini saat produksi dan pengguna Anda melihat error. Memahami cara kerja batasan laju di berbagai penyedia dan membangun logika retry yang tepat adalah perbedaan antara demo dan aplikasi produksi.
Cara Setiap Penyedia Membatasi Anda
OpenAI
OpenAI menggunakan batasan laju bertingkat berdasarkan riwayat penggunaan akun dan tingkat pembayaran Anda.
| Tingkat | RPM (Permintaan/Menit) | TPM (Token/Menit) | Cara Mencapai |
|---|---|---|---|
| Gratis | 3 | 40.000 | Akun baru |
| Tingkat 1 | 500 | 200.000 | Bayar $5 |
| Tingkat 2 | 5.000 | 2.000.000 | Bayar $50 |
| Tingkat 3 | 5.000 | 10.000.000 | Bayar $100 |
| Tingkat 4 | 10.000 | 50.000.000 | Bayar $250 |
| Tingkat 5 | 10.000 | 300.000.000 | Bayar $1.000 |
Batasan berlaku per model. Menggunakan GPT-4.1 tidak mengurangi kuota GPT-4.1-mini Anda.
Anthropic
Anthropic menggunakan sistem tingkat serupa dengan batasan RPM dan TPM. Mereka juga memberlakukan batas token harian pada tingkat yang lebih rendah.
Google (Gemini)
Google AI Studio memiliki batasan per model. Tingkat gratis cukup longgar untuk permintaan harian tapi ketat untuk batas per menit (15 RPM untuk tingkat gratis Gemini 2.5 Flash).
Platform Agregator
Agregator seperti LemonData dan OpenRouter menambahkan lapisan pembatasan laju sendiri di atas batasan penyedia utama. LemonData menggunakan batasan berbasis peran:
| Peran | RPM |
|---|---|
| Pengguna | 1.000 |
| Mitra | 3.000 |
| VIP | 10.000 |
Keuntungannya: batasan agregator biasanya lebih tinggi daripada tingkat gratis penyedia individual, dan routing multi-saluran berarti jika satu saluran utama dibatasi, permintaan dialihkan ke saluran lain.
Membaca Header Batasan Laju
Semua penyedia utama mengembalikan informasi batasan laju di header respons:
x-ratelimit-limit-requests: 500
x-ratelimit-remaining-requests: 499
x-ratelimit-reset-requests: 60s
x-ratelimit-limit-tokens: 200000
x-ratelimit-remaining-tokens: 199500
Gunakan header ini secara proaktif. Jangan tunggu error 429 untuk memperlambat.
Membangun Logika Retry
Cara yang Salah
# Jangan lakukan ini
import time
def call_api(messages):
while True:
try:
return client.chat.completions.create(
model="gpt-4.1",
messages=messages
)
except Exception:
time.sleep(1) # Delay tetap, tanpa backoff, menangkap semua error
Masalah: tidak ada exponential backoff, menangkap error yang tidak bisa di-retry, tidak ada batas maksimal retry, tidak ada jitter.
Cara yang Benar
import time
import random
from openai import RateLimitError, APIError, APIConnectionError
def call_with_retry(messages, model="gpt-4.1", max_retries=3):
"""Retry dengan exponential backoff dan jitter."""
for attempt in range(max_retries + 1):
try:
return client.chat.completions.create(
model=model,
messages=messages
)
except RateLimitError as e:
if attempt == max_retries:
raise
# Gunakan retry_after dari respons jika tersedia
wait = getattr(e, 'retry_after', None)
if wait is None:
wait = (2 ** attempt) + random.uniform(0, 1)
print(f"Dibatasi laju. Menunggu {wait:.1f}s (percobaan {attempt + 1})")
time.sleep(wait)
except APIConnectionError:
if attempt == max_retries:
raise
wait = (2 ** attempt) + random.uniform(0, 1)
time.sleep(wait)
except APIError as e:
# Jangan retry error client (400, 401, 403)
if e.status_code and 400 <= e.status_code < 500:
raise
if attempt == max_retries:
raise
time.sleep((2 ** attempt) + random.uniform(0, 1))
Prinsip utama:
- Exponential backoff: 1s, 2s, 4s, 8s
- Jitter: tambahan acak 0-1 detik untuk menghindari thundering herd
- Hormati header
retry_aftersaat disediakan - Jangan retry error client (permintaan buruk, gagal otentikasi)
- Tetapkan batas maksimal retry
Versi Async
import asyncio
import random
from openai import AsyncOpenAI, RateLimitError
async_client = AsyncOpenAI(
api_key="sk-lemon-xxx",
base_url="https://api.lemondata.cc/v1"
)
async def call_with_retry_async(messages, model="gpt-4.1", max_retries=3):
for attempt in range(max_retries + 1):
try:
return await async_client.chat.completions.create(
model=model,
messages=messages
)
except RateLimitError:
if attempt == max_retries:
raise
wait = (2 ** attempt) + random.uniform(0, 1)
await asyncio.sleep(wait)
Lanjutan: Token Bucket Rate Limiter
Untuk aplikasi dengan throughput tinggi, terapkan pembatasan laju di sisi klien untuk menghindari terkena batas server:
import time
import asyncio
class TokenBucket:
def __init__(self, rate: float, capacity: int):
self.rate = rate # token per detik
self.capacity = capacity # ukuran ledakan maksimal
self.tokens = capacity
self.last_refill = time.monotonic()
async def acquire(self, tokens: int = 1):
while True:
now = time.monotonic()
elapsed = now - self.last_refill
self.tokens = min(
self.capacity,
self.tokens + elapsed * self.rate
)
self.last_refill = now
if self.tokens >= tokens:
self.tokens -= tokens
return
# Tunggu sampai token cukup
wait = (tokens - self.tokens) / self.rate
await asyncio.sleep(wait)
# 500 permintaan per menit = ~8,3 per detik
limiter = TokenBucket(rate=8.0, capacity=20)
async def rate_limited_call(messages, model="gpt-4.1"):
await limiter.acquire()
return await async_client.chat.completions.create(
model=model,
messages=messages
)
Fallback Model Saat Terkena Batas Laju
Ketika model utama Anda terkena batas laju, gunakan fallback ke alternatif:
FALLBACK_CHAIN = [
"claude-sonnet-4-6",
"gpt-4.1",
"gpt-4.1-mini",
]
async def call_with_fallback(messages):
for model in FALLBACK_CHAIN:
try:
return await async_client.chat.completions.create(
model=model,
messages=messages
)
except RateLimitError:
continue
raise Exception("Semua model terkena batas laju")
Di sinilah agregator API bersinar. Dengan lebih dari 300 model di satu endpoint, Anda selalu punya fallback yang tersedia.
Memantau Penggunaan Batas Laju
Lacak konsumsi batas laju Anda untuk menangkap masalah sebelum mempengaruhi pengguna:
import logging
def log_rate_limits(response):
headers = response.headers
remaining = headers.get("x-ratelimit-remaining-requests")
limit = headers.get("x-ratelimit-limit-requests")
if remaining and int(remaining) < int(limit) * 0.1:
logging.warning(
f"Peringatan batas laju: {remaining}/{limit} permintaan tersisa"
)
Atur peringatan saat kapasitas tersisa turun di bawah 10%. Ini memberi Anda waktu untuk menerapkan throttling sebelum pengguna melihat error 429.
Ringkasan
| Strategi | Kapan Digunakan |
|---|---|
| Exponential backoff | Selalu (dasar) |
| Pembatas laju sisi klien | Aplikasi throughput tinggi (>100 RPM) |
| Fallback model | Aplikasi produksi dengan persyaratan SLA |
| Monitoring proaktif | Setiap deployment produksi |
| Batch API | Workload non real-time |
Tujuannya bukan menghindari batas laju sepenuhnya. Tapi menanganinya dengan baik agar pengguna Anda tidak pernah menyadarinya.
Bangun aplikasi AI yang tangguh: lemondata.cc menyediakan routing multi-saluran yang otomatis menangani batas laju upstream. Satu API key, 300+ model.
