Erros & Limites
Códigos de erro HTTP, formato das respostas de erro, e limites de rate.
Actualizado em Abril 2026
Formato das respostas de erro
Quando um pedido falha, a API devolve um JSON com a seguinte estrutura:
Estrutura de erro
{
"statusCode": 401,
"message": "API Key inválida ou revogada.",
"error": "Unauthorized"
}Códigos HTTP
Códigos de resposta
| Nome | Tipo | Obrig. | Descrição |
|---|---|---|---|
200 | HTTP | não | Pedido bem-sucedido. |
201 | HTTP | não | Recurso criado com sucesso. |
400 | HTTP | não | Pedido inválido — verifica os campos obrigatórios e os tipos de dados. |
401 | HTTP | não | Não autorizado — API Key em falta, inválida ou revogada. |
403 | HTTP | não | Proibido — a chave não tem o scope necessário para esta operação. |
404 | HTTP | não | Recurso não encontrado — verifica o ID e o Company ID. |
409 | HTTP | não | Conflito — o recurso já existe (ex: NIF duplicado). |
422 | HTTP | não | Entidade não processável — dados válidos mas com erro de negócio. |
429 | HTTP | não | Demasiados pedidos — rate limit atingido. |
500 | HTTP | não | Erro interno do servidor — reporta em suporte@uwata.app. |
Mensagens de erro comuns
Erros frequentes
| Nome | Tipo | Obrig. | Descrição |
|---|---|---|---|
API Key inválida ou revogada | 401 | não | O token não existe ou foi revogado. Gera uma nova chave no Dashboard. |
Scope insuficiente | 403 | não | A chave não tem o scope necessário. Ex: precisas de clients:write para criar clientes. |
X-Company-Id em falta | 400 | não | O cabeçalho X-Company-Id é obrigatório em todos os pedidos. |
Empresa não encontrada | 404 | não | O Company ID não corresponde à empresa associada à API Key. |
Limite de API Keys atingido | 422 | não | Máximo de 10 chaves activas por empresa. Revoga chaves não utilizadas. |
Rate Limiting
A API aplica limites de pedidos por chave para garantir a disponibilidade do serviço. Quando o limite é atingido, recebes um 429 Too Many Requests.
Limites actuais
| Nome | Tipo | Obrig. | Descrição |
|---|---|---|---|
Pedidos por minuto | limit | não | 60 pedidos por minuto por API Key. |
Pedidos por hora | limit | não | 1.000 pedidos por hora por API Key. |
Pedidos por dia | limit | não | 10.000 pedidos por dia por empresa. |
Os cabeçalhosX-RateLimit-RemainingeX-RateLimit-Resetserão adicionados nas próximas versões da API.
Tratamento de erros no código
Tratar erros
const res = await fetch('https://api.uwata.app/api/v1/v1/invoices', {
headers: { Authorization: `Bearer ${API_KEY}`, 'X-Company-Id': COMPANY_ID },
})
if (!res.ok) {
const error = await res.json()
console.error(`Erro ${error.statusCode}: ${error.message}`)
// Tratar conforme o statusCode
if (res.status === 429) {
// Rate limit — aguardar e tentar novamente
await new Promise(r => setTimeout(r, 1000))
}
}Retry com backoff exponencial
Para erros 429 ou 5xx, implementa retry com backoff exponencial: aguarda 1s, depois 2s, depois 4s, até um máximo de 3 tentativas.
Retry com backoff
async function fetchWithRetry(url, options, retries = 3) {
for (let i = 0; i < retries; i++) {
const res = await fetch(url, options)
if (res.ok) return res.json()
if (res.status === 429 || res.status >= 500) {
await new Promise(r => setTimeout(r, Math.pow(2, i) * 1000))
continue
}
throw await res.json()
}
throw new Error('Máximo de tentativas atingido')
}