---
permalink: /rate-limiting
title: Rate Limiting
sub_header: Understanding and Managing Procore API Rate Limits
layout: default
section_title: Plan Your App
---
## Overview
Procore’s API uses two rate limits to help keep the platform reliable: an hourly limit (60-minute window) and a spike limit (10-second window). With every API call, Procore returns rate limit headers so you can understand the limit being reported, how many requests remain, and when that limit resets.
The headers returned may reflect either the spike limit or the hourly limit. The values returned reflect the limit your app is most likely to exceed first. In most cases, the spike limit is reported until you are very close to exhausting the hourly limit.
***
## What Counts Against Your Limit
Every request your app sends counts against your rate limit, including requests that fail. A `400`, `403`, or `404` response consumes quota exactly like a successful call.
This matters more than it first appears. An app with a high client-error rate can spend a substantial share of its hourly allocation on calls that return nothing useful — malformed requests, calls to resources the app lacks permission for, or requests to routes that do not exist. Fixing those errors can recover meaningful capacity without any change to your limit.
Use the API Call Activity Report to see your error distribution by status code and endpoint.
***
## Interpret Rate Limit Headers
There are three important rate limit headers returned when making a request to the Procore API. These values reflect your current limits. They can change at any time, so your application should always read and adapt to them.
| Header | Explanation |
| ---------------------- | --------------------------------------------------------------------------------|
| X-Rate-Limit-Limit | The total number of requests allowed for the limit currently being reported (hourly or spike). |
| X-Rate-Limit-Remaining | How many requests are remaining for the limit currently being reported. For short-term windows, this value may increase again after a brief pause as the window rolls forward. |
| X-Rate-Limit-Reset | The Unix timestamp (in seconds) when the currently reported window resets. |
**Important:** The `X-Rate-Limit-*` headers reflect the limit your app is most likely to exceed first (hourly limit or spike limit). Use the headers returned on each response as the source of truth for throttling logic.
### How to use the headers
Use the rate limit headers to pace requests without needing separate logic for the hourly limit vs the spike limit.
- Read `X-Rate-Limit-Remaining` on every response.
- When `X-Rate-Limit-Remaining` reaches `0`, pause requests until after `X-Rate-Limit-Reset`, then resume processing.
- If your app makes concurrent requests (for example, multi-threaded or trigger-based), enqueue work and control throughput by tuning concurrency (such as adjusting thread pool size).
**Best practice:** Treat the headers as the source of truth and throttle based on the current response, not a single assumed limit (such as `3600/hour`).
**Example: hourly limit headers**
```
X-Rate-Limit-Limit: 600
X-Rate-Limit-Remaining: 589
X-Rate-Limit-Reset: 1466182244
```
**Example: spike limit headers**
```
X-Rate-Limit-Limit: 25
X-Rate-Limit-Remaining: 24
X-Rate-Limit-Reset: 1466182247
```