Guias
Paginação
Como navegar resultados grandes com limit/offset, has_more e next_offset.
A API usa paginação por offset com tamanho configurável de página. Toda resposta lista inclui um objeto pagination.
Parâmetros
| Parâmetro | Tipo | Padrão | Máximo |
|---|---|---|---|
limit | int | 50 | 100 |
offset | int | 0 | — |
Estrutura da resposta
{
"data": [ /* items */ ],
"pagination": {
"limit": 50,
"offset": 0,
"count": 234,
"has_more": true,
"next_offset": 50
}
}count— total de resultados disponíveis para a queryhas_more—truese ainda houver páginasnext_offset— valor a usar na próxima requisição, ounullse for a última página
Loop completo
async function fetchAll(baseParams: Record<string, string>) {
const all: Contact[] = [];
let offset = 0;
const limit = 100;
while (true) {
const url = new URL("https://crm.oficinamartech.com/api/contacts/message-search");
Object.entries(baseParams).forEach(([k, v]) => url.searchParams.set(k, v));
url.searchParams.set("limit", String(limit));
url.searchParams.set("offset", String(offset));
const res = await fetch(url, {
headers: { Authorization: `Bearer ${process.env.OFM_API_KEY}` },
});
const json = await res.json();
all.push(...json.data);
if (!json.pagination.has_more) break;
offset = json.pagination.next_offset;
}
return all;
}Não use offset para sincronização incremental. Se novos contatos forem inseridos durante o loop, você pode pular registros ou duplicar. Para sync incremental, filtre por from/to (timestamps de mensagens) — veja Sincronizar com ERP.
Limite máximo por página
limit > 100 retorna 400 Bad Request. Mantenha entre 50-100 para o melhor equilíbrio entre throughput e payload.
Quando parar
pagination.has_more === false— fim naturalpagination.next_offset === null— mesma coisa- Você acumulou o número desejado (early break)
Total estimado
pagination.count reflete o total no momento da query. Em coleções grandes ou com filtros dinâmicos, esse valor pode variar entre requisições — não dependa dele para checksums.