Rate Limit Overview
The Exchange Rates API uses a monthly quota system with different limits based on your subscription plan. Rate limits ensure fair usage and optimal performance for all users.
All rate limits are calculated based on your billing cycle and reset on your monthly renewal date.
Plan Comparison
Plan Tiers
| Plan | Price (AUD/month) | Monthly Requests | Historical Data | Timeseries Max Range | Support |
|---|
| Free | $0 | 300 | None | No access | Community |
| Starter | $29 | 5,000 | Last 30 days | 7 days | Email (48h) |
| Professional | $79 | 50,000 | Full (2018+) | 90 days | Email (24h) |
| Business | $299 | 500,000 | Full (2018+) | 365 days | Phone (4h) |
Free Tier Details
The free tier is perfect for:
- Testing and development
- Personal projects
- Small applications with low traffic
- Proof of concept implementations
Limitations:
- 300 requests per month
- No historical data access
- No timeseries endpoint access
- Community support only
- No SLA guarantees
Paid Plans Benefits
All paid plans include:
- Higher monthly quotas
- Historical data access
- Priority support
- 99.9% uptime SLA
- Advanced features (webhooks, CSV exports)*
*Some features coming soon
Every API response includes rate limit information in the headers:
curl -i https://api.exchangeratesapi.com.au/latest \
-H "Authorization: Bearer your_api_key_here"
HTTP/2 200
X-RateLimit-Limit-Monthly: 5000
X-RateLimit-Remaining-Monthly: 4847
X-RateLimit-Reset: 2025-10-01T00:00:00Z
X-Request-Id: 123e4567-e89b-12d3-a456-426614174000
| Header | Description |
|---|
X-RateLimit-Limit-Monthly | Total monthly quota for your plan |
X-RateLimit-Remaining-Monthly | Remaining requests this month |
X-RateLimit-Reset | When the quota resets (next billing cycle) |
X-Request-Id | Unique identifier for debugging |
Free Endpoint Rate Limits
Some endpoints don’t require authentication but have IP-based rate limits:
| Endpoint | Limit | Reset Period |
|---|
GET /status | Unlimited | - |
GET /symbols | Unlimited | - |
GET /convert (free) | 3 requests | Per hour per IP |
Free Conversion Example
# No API key required, but limited to 3/hour per IP
curl "https://api.exchangeratesapi.com.au/convert?from=AUD&to=USD&amount=100"
Response includes rate limit headers:
X-RateLimit-Limit: 3
X-RateLimit-Remaining: 2
X-RateLimit-Window: 3600
Rate Limit Exceeded Responses
Monthly Quota Exceeded (Authenticated)
{
"success": false,
"error": {
"code": 429,
"type": "rate_limit_exceeded",
"info": "Monthly quota of 5000 requests exceeded. Quota resets on your next billing cycle."
}
}
IP Rate Limit Exceeded (Free Endpoints)
{
"success": false,
"error": {
"code": 429,
"type": "rate_limit_exceeded",
"info": "Rate limit exceeded. Try again in 3456 seconds."
}
}
Monitoring Your Usage
Dashboard Analytics
Track your API usage in the dashboard:
- Monthly Usage: Requests made this billing cycle
- Historical Usage: 12-month usage chart
- Top Endpoints: Most frequently used endpoints
- Response Times: Average API performance
- Error Rates: Success vs error rates
Rate Limit Best Practices
1. Implement Client-Side Throttling
class ExchangeRatesAPI {
constructor(apiKey) {
this.apiKey = apiKey;
this.baseURL = 'https://api.exchangeratesapi.com.au';
this.remainingRequests = null;
this.quotaResetTime = null;
}
async makeRequest(endpoint) {
// Check if we have quota remaining
if (this.remainingRequests !== null && this.remainingRequests <= 0) {
const now = new Date();
if (now < new Date(this.quotaResetTime)) {
throw new Error('Monthly quota exceeded. Try again after your billing cycle resets.');
}
}
const response = await fetch(`${this.baseURL}${endpoint}`, {
headers: { 'Authorization': `Bearer ${this.apiKey}` }
});
// Update rate limit info from headers
this.remainingRequests = parseInt(
response.headers.get('X-RateLimit-Remaining-Monthly')
);
this.quotaResetTime = response.headers.get('X-RateLimit-Reset');
if (!response.ok) {
const error = await response.json();
throw new Error(error.error.info);
}
return response.json();
}
}
2. Cache Responses Intelligently
RBA data updates once daily at 4 PM AEST, so cache aggressively to minimize monthly quota usage:
class CachedExchangeRates {
constructor(apiKey) {
this.api = new ExchangeRatesAPI(apiKey);
this.cache = new Map();
this.cacheExpiry = new Map();
}
async getLatestRates() {
const cacheKey = 'latest';
const now = Date.now();
// Check if cached data is still fresh
if (this.cache.has(cacheKey) &&
this.cacheExpiry.get(cacheKey) > now) {
return this.cache.get(cacheKey);
}
// Fetch fresh data
const data = await this.api.makeRequest('/latest');
// Cache until next RBA update (4 PM AEST next day)
const tomorrow4PM = new Date();
tomorrow4PM.setDate(tomorrow4PM.getDate() + 1);
tomorrow4PM.setHours(16, 0, 0, 0); // 4 PM
this.cache.set(cacheKey, data);
this.cacheExpiry.set(cacheKey, tomorrow4PM.getTime());
return data;
}
}
3. Handle Rate Limit Errors Gracefully
async function robustApiCall(apiClient, endpoint) {
try {
return await apiClient.makeRequest(endpoint);
} catch (error) {
if (error.message.includes('quota exceeded')) {
// Log the issue and return cached data if available
console.warn('Monthly API quota exceeded, using cached data');
return getCachedData(endpoint);
}
if (error.message.includes('rate limit')) {
// Wait and retry for temporary rate limits
await sleep(60000); // Wait 1 minute
return apiClient.makeRequest(endpoint);
}
throw error; // Re-throw other errors
}
}
4. Batch Requests Efficiently
Instead of multiple single-currency requests, use batch endpoints:
// Bad - Multiple requests
const usdRate = await api.makeRequest('/latest/USD'); // 1 request
const eurRate = await api.makeRequest('/latest/EUR'); // 1 request
const gbpRate = await api.makeRequest('/latest/GBP'); // 1 request
// Total: 3 requests
// Good - Single batch request
const allRates = await api.makeRequest('/latest'); // 1 request
const usdRate = allRates.rates.USD;
const eurRate = allRates.rates.EUR;
const gbpRate = allRates.rates.GBP;
// Total: 1 request
Upgrade Options
When to Upgrade
Consider upgrading when you:
- Consistently hit monthly quotas
- Need historical data access
- Require faster support response
- Want SLA guarantees
- Need advanced features
Upgrade Process
Immediate Effect
New quotas take effect immediately after payment
No Code Changes
Your existing API keys continue working with higher limits