Pular para o conteúdo principal

Limites de uso (rate limiting)

A API do InHire aplica um limite de requisições por conta para garantir estabilidade e tempo de resposta consistente para todos os clientes. Esta página descreve como esse limite é calculado, como acompanhar seu consumo em tempo real e como sua integração deve se comportar quando o limite é atingido.

Como o limite é calculado​

O limite é por conta, não por token de acesso.

Todas as requisições autenticadas com usuários de API da sua conta compartilham o mesmo saldo. Se você tem mais de um usuário de API (por exemplo, um para sincronizar seu ERP e outro para alimentar seu site de carreiras), os dois consomem do mesmo limite.

informação

Requisições feitas por pessoas usando a plataforma web não contam para esse limite. Ele se aplica somente ao acesso programático via API.

O controle usa o algoritmo de balde de fichas (token bucket):

  • Sua conta tem um balde com uma capacidade máxima de fichas, chamada de burst.
  • Cada requisição consome uma ficha.
  • O balde é reabastecido continuamente, na taxa sustentada da sua conta.
  • Uma requisição que chega com o balde vazio recebe 429 Too Many Requests.

Limites​

Valor
Taxa sustentada20 requisições/segundo
Burst400 requisições

A taxa sustentada é o volume que você pode manter indefinidamente. O burst é quanto você pode disparar acima dessa taxa em um pico, aproveitando as fichas acumuladas enquanto sua integração estava ociosa.

Entendendo o burst​

O burst existe para que picos legítimos não sejam penalizados. Uma integração que ficou parada acumula fichas e pode disparar um lote rapidamente, sem tomar 429.

Veja o comportamento do limite ao longo do tempo:

MomentoO que a integração fazFichas no baldeResultado
t = 0sestá ociosa400 (cheio)balde no máximo
t = 0s a t = 3sdispara 400 requisições (~133/s)400 → 60todas passam
t = 3s a t = 3,5smantém as ~133/s60 → 0balde esvazia
a partir de t = 3,5smantém as ~133/s0recebe 429
a partir de t = 3,5sreduz para 20/s0, estáveltodas passam
pausa de 20 segundosnão faz requisições0 → 400burst recarregado

Na prática, isso significa:

  • Sincronização em lote. Paginar 5.000 candidaturas: as primeiras 400 requisições passam na velocidade que sua rede permitir, e as 4.600 restantes saem a 20/s. O trabalho todo leva cerca de 4 minutos, sem nenhum 429, desde que sua integração mantenha o ritmo em vez de despejar tudo de uma vez.
  • Pico disparado por evento. 100 candidaturas chegam de uma vez e sua integração busca os dados de cada uma: são 100 requisições contra um burst de 400, absorvidas integralmente, sem 429.
  • Laço com defeito. Uma integração em loop a 200 req/s consome as 400 fichas em cerca de 2 segundos e passa a receber 429 na maior parte das requisições seguintes, até reduzir o ritmo.

Acompanhando seu consumo​

Toda resposta da API inclui três headers que permitem acompanhar o saldo sem precisar provocar um 429:

HeaderSignificado
X-RateLimit-LimitCapacidade total do balde da sua conta
X-RateLimit-RemainingFichas disponíveis no momento da resposta
X-RateLimit-ResetTimestamp Unix (em segundos) de quando o balde volta a ficar cheio
HTTP/1.1 200 OK
Content-Type: application/json
X-RateLimit-Limit: 400
X-RateLimit-Remaining: 287
X-RateLimit-Reset: 1785874957
aviso

X-RateLimit-Limit é a capacidade do balde, não o número de requisições permitidas por segundo. Esse header retorna 400, mas sua taxa sustentada é de 20 requisições por segundo. Não use o valor do header para dimensionar a velocidade da sua integração.

Recomendamos monitorar X-RateLimit-Remaining e desacelerar preventivamente quando ele ficar baixo, em vez de acelerar até tomar 429.

Quando o limite é excedido​

Requisições acima do limite recebem o status 429 Too Many Requests:

{
"message": "Rate limit exceeded"
}

A resposta traz o header Retry-After, além dos headers de consumo:

HTTP/1.1 429 Too Many Requests
Content-Type: application/json
Retry-After: 1
X-RateLimit-Limit: 400
X-RateLimit-Remaining: 0
X-RateLimit-Reset: 1785874977

Use Retry-After para agendar a próxima tentativa. Ele vem em segundos, arredondado para cima, com valor mínimo de 1.

aviso

Não use X-RateLimit-Reset para decidir quando repetir a requisição. Ele marca quando o balde volta a ficar cheio, o que a partir de um balde vazio está a 20 segundos de distância, enquanto uma única ficha é reposta em 50 milissegundos. Esperar o Reset para retentar desperdiça quase toda a capacidade disponível nesse intervalo. Esse header serve para você entender quando recupera o burst inteiro, não quando a próxima requisição passa.

dica

O limite é aplicado antes da requisição chegar à API, então um 429 garante que a operação não foi executada. Repetir a requisição é seguro, inclusive em POST e PUT, sem risco de duplicar recursos. Essa garantia vale só para o 429: em erros 5xx ou timeout, a operação pode ter sido processada, e a repetição precisa de cuidado.

Boas práticas​

Use backoff exponencial com jitter​

Ao receber 429, espere e tente novamente com intervalos crescentes. Some um valor aleatório (jitter) a cada espera para evitar que várias tentativas colidam no mesmo instante.

async function requestWithRetry(url, options, maxAttempts = 5) {
for (let attempt = 0; attempt < maxAttempts; attempt++) {
const response = await fetch(url, options);

if (response.status !== 429) return response;

// Header ausente ou inválido cai para 1 segundo.
const headerSeconds = Number(response.headers.get("retry-after"));
const retryAfter = headerSeconds >= 1 ? headerSeconds : 1;

const backoffSeconds = retryAfter * 2 ** attempt;
const jitterSeconds = Math.random() * backoffSeconds * 0.3;

await new Promise((resolve) =>
setTimeout(resolve, (backoffSeconds + jitterSeconds) * 1000),
);
}

throw new Error("Limite de requisições persistente após várias tentativas");
}

Prefira webhooks a polling​

Consultar a API em intervalos curtos para descobrir o que mudou é o padrão que mais consome limite, e quase sempre pode ser substituído. Com webhooks, o InHire notifica seu sistema quando algo acontece, e você faz requisições apenas sobre os registros que realmente mudaram.

Limite a concorrência​

Disparar muitas requisições em paralelo esvazia o burst em poucos segundos e o ganho é menor do que parece, porque a taxa sustentada é a mesma. Mantenha um número fixo de requisições simultâneas (algo entre 5 e 20 atende à maioria dos casos) em vez de disparar tudo de uma vez.

Pagine com o maior tamanho de página disponível​

Trazer mais registros por requisição reduz o número total de chamadas para percorrer o mesmo volume de dados. Consulte o guia do endpoint para saber o tamanho máximo de página suportado.

Cacheie dados estáveis​

Vagas, campos personalizados e definições de scorecard mudam com pouca frequência. Guardar esses dados do seu lado e revalidar periodicamente evita repetir as mesmas consultas.

Mudanças nesta política​

Os limites descritos aqui podem ser ajustados. Qualquer alteração que reduza a capacidade disponível será comunicada com pelo menos 30 dias de antecedência e precedida de um período em que o novo limite é medido, mas não aplicado, para que você possa se adaptar sem impacto.