Rate Limits
Our Rate Limits
We impose a rate limit on authenticated operations to our API. We do this to balance the load among all projects and prevent spikes in one project's activity from impacting other merchants' transactions. This rate limit will not delay or obstruct everyday business but may block large and unplanned traffic spikes.
ProcessOut uses three independent rate limits. The primary rate limit applies to all production endpoints not subject to the secondary rate limit. The secondary rate limit covers any endpoints where requests are usually triggered as the result of ProcessOut behaviour. The sandbox rate limit covers all requests to our sandbox environment.
Currently the secondary rate limit covers only GET /events and GET /events/:event_id. Requests to these endpoints should be triggered in response to ProcessOut’s outbound webhooks. This ensures that an incident or outage within ProcessOut’s webhooks system that triggers a spike in outbound webhooks and therefore requests to GET /events cannot impact other critical payment processing endpoints.
The behaviour of the three rate limits (primary, secondary and sandbox) is identical, however the value allocated by PO to each rate limit may be different.
Implementation
Our rate limit implementation uses a Generic Cell Rate Algorithm (GCRA) to provide a "bucket" of request capacity for each project.
This capacity bucket is filled with tokens consistently at a fixed rate derived from your project’s rate limit. Each request to ProcessOut’s API uses a token from this bucket. If the bucket is emptied, i.e. running out of tokens, ProcessOut will start returning 429 status codes.
To help you manage your traffic, all responses from ProcessOut’s API will include the following headers x-ratelimit and x-ratelimit-remaining. The x-ratelimit header contains the project’s rate limit, specified in requests per minute (RPM). The x-ratelimit-remaining header contains the remaining capacity available in the project’s bucket.
Remember that the behaviour of the three rate limits (primary, secondary and sandbox) is identical, however the value allocated by PO to each rate limit may be different.
For example, if a project has a primary rate limit of 3000 RPM, the value of x-ratelimit for requests to endpoints under the primary rate limit will always be 3000. This example considers only requests to the primary rate limit. If this project’s traffic remains below 3000 RPM its bucket remains full and the value of x-ratelimit-remaining will also be 3000. If the project starts sending traffic at 3010 RPM it will begin using up tokens from its bucket at a rate of 10 tokens per minute for 5 hours, until the bucket is empty and requests are rate limited. If instead, the project starts sending traffic at 3300 RPM it will use up the tokens in its bucket by 300 tokens per minute for 10 minutes until the bucket is empty and requests are rate limited.
| Total RPM | Excess RPM | Time to Exhaust | Value of x-ratelimit-remaining after 5 minutes of traffic |
|---|---|---|---|
| 3000 | 0 | Never | 3000 |
| 3005 | 5 | 10 Hours | 2975 |
| 3010 | 10 | 5 Hours | 2950 |
| 3300 | 300 | 10 Minutes | 1500 |
| 3600 | 600 | 5 Minutes | 0 |
Once the project drops back under 3000 RPM the bucket will begin to refill with tokens. At 2900 RPM the bucket will be refilled by 100 tokens every minute until the bucket has been refilled.
Managing Your Rate Limits
We recommend that you implement monitoring of these headers and throttle your traffic if the value of x-ratelimit-remaining approaches 0. Please ensure you monitor the primary and secondary and sandbox rate limits separately.
As the GCRA algorithm fills the bucket consistently, temporary fluctuations in traffic over the allocated RPM for short periods will result in fluctuations in the value of x-ratelimit-remaining. These fluctuations are to be expected.
ProcessOut may alter rate limit values as we see fit. Please ensure that your implementation can handle the sudden changes to x-ratelimit and x-ratelimit-remaining, both upwards and downwards, that this will entail.
Updated about 4 hours ago
