> ## Documentation Index
> Fetch the complete documentation index at: https://docs.fraudeg.com/llms.txt
> Use this file to discover all available pages before exploring further.

# FraudEG API Rate Limits, Quotas, and Backoff Strategies

> Understand FraudEG API rate limits by endpoint group, rate limit response headers, and best practices for handling 429 errors and scaling your integration.

Rate limits protect the stability of the FraudEG platform and ensure fair, consistent performance for every customer. All accounts are subject to the default limits described on this page. If your integration requires higher throughput, contact the FraudEG sales team to discuss high-volume plans with elevated quotas.

## Default Rate Limits

Rate limits are enforced per API key on a rolling one-minute window. Exceeding any per-endpoint limit or the global limit triggers a `429 Too Many Requests` response.

| Endpoint Group                               | Limit             |
| -------------------------------------------- | ----------------- |
| `POST /v1/transactions/score`                | 1,000 req/min     |
| `POST /v1/identity/verify`                   | 200 req/min       |
| `GET` endpoints (`/v1/events`, `/v1/alerts`) | 500 req/min       |
| All other `POST` endpoints                   | 300 req/min       |
| **Global (all endpoints combined)**          | **2,000 req/min** |

<Note>
  Sandbox API keys have lower rate limits — **100 req/min** across all endpoints — to encourage efficient integration patterns and help you detect and fix unnecessary duplicate requests before going to production.
</Note>

## Rate Limit Response Headers

FraudEG includes rate limit headers on **every response**, not just error responses. Monitor these headers proactively to avoid hitting the limit rather than reacting after you receive a `429`.

| Header                  | Description                                                                                                              |
| ----------------------- | ------------------------------------------------------------------------------------------------------------------------ |
| `X-RateLimit-Limit`     | Your current rate limit for the endpoint that was called, in requests per minute.                                        |
| `X-RateLimit-Remaining` | The number of requests remaining in the current window for this endpoint.                                                |
| `X-RateLimit-Reset`     | A Unix timestamp (seconds) indicating when the current window resets and `X-RateLimit-Remaining` returns to its maximum. |
| `Retry-After`           | The number of seconds to wait before sending another request. **Only present on `429` responses.**                       |

An example of the headers on a successful response:

```http theme={null}
HTTP/1.1 200 OK
X-RateLimit-Limit: 1000
X-RateLimit-Remaining: 847
X-RateLimit-Reset: 1713984060
Content-Type: application/json
```

And on a `429` response:

```http theme={null}
HTTP/1.1 429 Too Many Requests
X-RateLimit-Limit: 1000
X-RateLimit-Remaining: 0
X-RateLimit-Reset: 1713984060
Retry-After: 23
Content-Type: application/json
```

## Handling 429 Errors

When you receive a `429 Too Many Requests` response, read the `Retry-After` header and wait that many seconds before sending another request to the same endpoint. Do not retry immediately — doing so will not succeed and will extend the window in which your key is throttled.

<Warning>
  Plan for gradual ramp-up when onboarding new traffic to FraudEG. Sudden bursts — such as replaying a backlog of transactions all at once — will immediately exceed rate limits and trigger `429` errors at scale. Spread high-volume jobs over time using a queue with a controlled dispatch rate.
</Warning>

## Exponential Backoff Example

The following Node.js example wraps any API call with automatic retry logic that respects the `Retry-After` header and applies exponential backoff:

```javascript theme={null}
async function withRetry(fn, maxRetries = 3) {
  for (let attempt = 0; attempt <= maxRetries; attempt++) {
    const response = await fn();
    if (response.status !== 429) return response;
    const retryAfter = parseInt(response.headers.get('Retry-After') || '1');
    await new Promise(r => setTimeout(r, retryAfter * 1000 * Math.pow(2, attempt)));
  }
  throw new Error('Max retries exceeded');
}
```

Pass any function that returns a `fetch` `Response` object:

```javascript theme={null}
const result = await withRetry(() =>
  fetch('https://api.fraudeg.com/v1/transactions/score', {
    method: 'POST',
    headers: {
      'Authorization': 'Bearer <API_KEY>',
      'Content-Type': 'application/json',
      'Idempotency-Key': crypto.randomUUID(),
    },
    body: JSON.stringify({ transaction_id: 'txn_123', amount: 4999, currency: 'USD' }),
  })
);
```

<Tip>
  Pair retry logic with the `Idempotency-Key` header so that retried `POST` requests never create duplicate resources, even when the original request may have partially succeeded before the rate limit was hit.
</Tip>

## Best Practices

Follow these practices to stay well within your rate limits and build a resilient integration:

<Steps>
  <Step title="Cache risk scores for repeated lookups">
    If your system evaluates the same transaction multiple times — for example, during session replay or rule testing — cache the score response using the `session_id` combined with `amount` and `user_id` as a cache key. Avoid re-scoring identical inputs.
  </Step>

  <Step title="Use batch patterns for high-volume processing">
    For bulk operations such as historical data analysis or nightly report generation, spread requests evenly across the window using a job queue. Dispatch at a rate safely below your per-endpoint limit rather than sending all requests concurrently.
  </Step>

  <Step title="Monitor X-RateLimit-Remaining proactively">
    Read the `X-RateLimit-Remaining` header on every response. When the value drops below a threshold you define (for example, 10% of your limit), slow down your request rate before hitting zero. This prevents your integration from fully blocking on `429` responses during peak traffic.
  </Step>

  <Step title="Contact sales for higher limits">
    If your production workload consistently approaches the default limits, reach out to [sales@fraudeg.com](mailto:sales@fraudeg.com). High-volume plans offer elevated per-endpoint and global limits, as well as dedicated infrastructure for latency-sensitive use cases.
  </Step>
</Steps>
