Rate Limiting
Understand Sematryx rate limits and learn how to handle them gracefully in your applications.
Rate Limits by Tier
Rate limits are applied per minute and vary by plan:
| Tier | Requests/Minute | Burst Limit | Monthly Solves |
|---|---|---|---|
| Free | 10 | 15 | 100 |
| Pay-as-you-go | 60 | 90 | Unlimited |
Burst limits allow temporary spikes above the sustained rate. See Billing & Usage for monthly optimization limits.
Rate Limit Headers
Every API response includes rate limit information in the headers:
X-RateLimit-Limit: 300
X-RateLimit-Remaining: 287
X-RateLimit-Reset: 1640995200
X-RateLimit-Window: 60Header Fields
- X-RateLimit-Limit: Maximum requests allowed in the window
- X-RateLimit-Remaining: Requests remaining in current window
- X-RateLimit-Reset: Unix timestamp when the window resets
- X-RateLimit-Window: Window duration in seconds
Handling Rate Limits
When you exceed the rate limit, you'll receive a 429 Too Many Requests response. Always check rate limit headers and implement retry logic:
Python Example
import time
import requests
def make_request_with_retry(url, headers, max_retries=3):
for attempt in range(max_retries):
response = requests.post(url, headers=headers)
if response.status_code == 429:
reset_time = int(response.headers.get('X-RateLimit-Reset', 0))
wait_time = max(reset_time - time.time(), 1)
print(f'Rate limit exceeded. Waiting {wait_time} seconds...')
time.sleep(wait_time)
continue
return response
raise Exception('Max retries exceeded')JavaScript Example
async function makeRequestWithRetry(url, headers, maxRetries = 3) {
for (let attempt = 0; attempt < maxRetries; attempt++) {
const response = await fetch(url, { method: 'POST', headers })
if (response.status === 429) {
const resetTime = parseInt(response.headers.get('X-RateLimit-Reset') || '0')
const waitTime = Math.max(resetTime - Date.now() / 1000, 1)
console.log(`Rate limit exceeded. Waiting ${waitTime} seconds...`)
await new Promise(resolve => setTimeout(resolve, waitTime * 1000))
continue
}
return response
}
throw new Error('Max retries exceeded')
}Exponential Backoff
For more robust rate limit handling, implement exponential backoff with jitter:
import time
import random
def exponential_backoff(attempt, base_delay=1, max_delay=60):
"""Calculate exponential backoff delay with jitter"""
delay = min(base_delay * (2 ** attempt), max_delay)
jitter = random.uniform(0, delay * 0.1)
return delay + jitter
# Usage
for attempt in range(max_retries):
try:
response = make_request()
break
except RateLimitError:
wait_time = exponential_backoff(attempt)
time.sleep(wait_time)Benefits
- • Prevents thundering herd problems
- • Reduces server load during high traffic
- • More efficient use of available rate limit
- • Jitter prevents synchronized retries
Best Practices
✓ Do
- • Monitor rate limit headers
- • Implement exponential backoff
- • Cache results when possible
- • Batch requests when available
- • Respect the reset time
✗ Don't
- • Ignore 429 status codes
- • Retry immediately without waiting
- • Make unnecessary requests
- • Exceed limits intentionally
- • Spin in tight retry loops
Increasing Rate Limits
Need higher rate limits? You have options:
Upgrade to Pay-as-you-go
Pay-as-you-go tier offers 6x the rate limit of Free tier with unlimited monthly solves.
View plans →High-Volume Needs
Need higher rate limits? Contact us at hello@sematryx.com to discuss your requirements.