Skip to main content

Por que usar

Redes falham. Se sua requisição de POST /runs falhar antes de você receber a resposta, você não sabe se o run foi criado ou não. Sem idempotência, um retry criaria um segundo run — duplicando a consulta. Com Idempotency-Key, você pode fazer retry com segurança: se o run já foi criado com aquela chave, o kycert retorna o resultado original sem executar novamente.

Como usar

Inclua o header Idempotency-Key com um UUID v4 gerado por você:
curl -X POST https://admin.kycert.com.br/api/v1/bureau/runs \
  -H "x-api-key: sk_live_..." \
  -H "Idempotency-Key: 6ba7b810-9dad-11d1-80b4-00c04fd430c8" \
  -H "Content-Type: application/json" \
  -d '{ "template_id": "...", "subject": { "type": "pf", "doc": "12345678901" } }'
import { randomUUID } from 'crypto'

async function createRunWithRetry(
  templateId: string,
  doc: string,
  apiKey: string,
  maxRetries = 3,
) {
  const idempotencyKey = randomUUID()  // gerar uma vez por tentativa lógica

  for (let attempt = 0; attempt < maxRetries; attempt++) {
    try {
      const res = await fetch('https://admin.kycert.com.br/api/v1/bureau/runs', {
        method: 'POST',
        headers: {
          'x-api-key': apiKey,
          'Content-Type': 'application/json',
          'Idempotency-Key': idempotencyKey,  // mesma chave em todos os retries
        },
        body: JSON.stringify({
          template_id: templateId,
          subject: { type: 'pf', doc },
        }),
      })

      if (res.status === 202 || res.status === 200) {
        return await res.json()
      }

      // 4xx sem Retry-After → não tentar novamente
      if (res.status >= 400 && res.status < 500 && !res.headers.get('retry-after')) {
        const err = await res.json()
        throw new Error(`${err.error.code}: ${err.error.message}`)
      }

    } catch (err) {
      if (attempt === maxRetries - 1) throw err
      await new Promise(r => setTimeout(r, 1000 * 2 ** attempt))  // backoff exponencial
    }
  }
}

Comportamento

  • Mesma chave nas próximas 24h: retorna o run original (mesma resposta, mesmo run_id)
  • Chave diferente: cria um novo run
  • Chave expirada (>24h): cria um novo run como se fosse a primeira vez

Regras

  • Use UUID v4 como formato da chave
  • Gere uma chave por tentativa lógica — não por chamada HTTP individual
  • Use a mesma chave em todos os retries da mesma tentativa
  • Não reutilize chaves entre operações diferentes
Se você variar a Idempotency-Key a cada retry, não terá proteção contra duplicação. Se você reutilizar a mesma chave para runs diferentes, poderá receber um resultado incorreto.