Manual de Integração — API Direct Data
O Look a Like é o produto da Direct Data que identifica empresas semelhantes ao perfil desejado. A partir de um conjunto de filtros (CNAE, UF, cidade, porte, situação cadastral, etc.), o cliente obtém uma lista de CNPJs qualificados e enriquecidos.
A API pública v2 substitui integralmente o fluxo anterior (Filter → Preview → Quote → Purchase v1), com três diferenças principais:
SearchPreview devolve o total encontrado e uma amostra na mesma requisição, sem polling.Purchase). Buscas exploratórias não geram registros no banco.| Termo | Descrição |
|---|---|
| Filtro | Conjunto de critérios de busca (CNAE, UF, cidade, porte, etc.). Pelo menos um filtro (whitelist) deve ser fornecido no SearchPreview. |
| SearchGuid | Identificador efêmero de uma busca em aberto, retornado pelo SearchPreview. Válido por 15 minutos e consumido na primeira Purchase. Não é persistido. |
| ListGuid | Identificador persistente da lista, retornado pela primeira Purchase. Reutilizável em novas Purchase para comprar mais empresas da mesma busca, durante 30 dias. |
| ExportGuid | Identificador de um lote de compra específico. Cada Purchase gera um ExportGuid — use-o em GetExport para acompanhar o status e em Download para baixar o arquivo final. |
| Quantidade cobrada | Quantidade de empresas efetivamente incluídas no lote. Se a quantidade solicitada exceder o disponível, a API rejeita com 400 — nenhuma cobrança parcial silenciosa. |
Todos os endpoints exigem o header Token com o Guid de autenticação da sua conta.
Sem token válido, a resposta é 401 Unauthorized.
Token: aaaaaaaa-bbbb-cccc-dddd-eeeeeeeeeeee
Todas as respostas seguem o formato:
{
"success": true,
"status": "OK",
"elapsedTimeMs": 42,
"dateTimeExecution": "07/07/2026 16:41:01",
"error": null,
... (campos específicos do endpoint)
}
Em caso de erro:
{
"success": false,
"status": "Bad Request",
"elapsedTimeMs": 15,
"dateTimeExecution": "07/07/2026 16:41:02",
"error": {
"fieldName": "Quantity",
"message": "A quantidade deve ser maior que zero e não pode exceder o total encontrado no preview."
}
}
/v2/Quote
OPCIONAL
Consulta o preço unitário antes de iniciar a busca.
requisição de cotação{ unitPrice }/v2/SearchPreview
Envia os filtros e recebe o total encontrado + uma amostra da busca.
{ filtros }{ total, searchGuid, rows[] }/v2/Purchase
Confirma a compra usando o searchGuid e a quantidade desejada.
{ searchGuid, quantity }{ listGuid, exportGuid, … }/Export/{exportGuid}
POLLING · REPETIR ATÉ CONCLUIR
Consulta o status do export em intervalos até que fique Concluído.
exportGuid (na URL){ exportStatus, … }/Export/{exportGuid}/Download
Baixa o arquivo final assim que o export estiver concluído.
exportGuid (na URL)stream ZIP/v2/Purchase
REUTILIZAÇÃO · OPCIONAL
Compra mais empresas da mesma lista usando o listGuid, sem refazer a busca — gera um novo export (volta ao passo 4).
{ listGuid, quantity }{ novo exportGuid, … }SearchGuid expira em 15 min — se demorar mais que isso pra decidir comprar, refaça o SearchPreview.ListGuid retornado na primeira compra — dá pra comprar mais empresas da mesma lista por até 30 dias sem refazer a busca.
Os endpoints desta seção não geram cobrança e não persistem nada. Quote devolve o preço unitário;
SearchPreview devolve total + amostra da busca com um SearchGuid para reutilização na compra.
Executa a busca de forma síncrona. Retorna o total de empresas que batem com o filtro (capado internamente),
uma amostra de até 5 empresas e um SearchGuid efêmero que pode ser reutilizado no
Purchase sem precisar reenviar o filtro.
| Campo | Tipo | Obrigatório | Descrição |
|---|---|---|---|
numberOfResults | long | Não | Limite máximo de resultados a considerar na busca. Mínimo: 1. Máximo: 100.000. Default: 1.000. |
filters | object | Sim | Conjunto de filtros de busca — ver tabela abaixo. Pelo menos uma whitelist deve estar preenchida em algum filtro. |
ignoredCnpjList | array<string> | Não | Lista de CNPJs que devem ser excluídos do resultado. Útil para remover clientes já existentes ou empresas que não devem ser prospectadas. Aceita CNPJ formatado ("12.345.678/0001-99") ou apenas dígitos ("12345678000199"). CNPJs duplicados são ignorados automaticamente. Máximo: 100.000 itens. |
filters
A maioria dos campos aceita o formato FormValue:
{ "whiteList": ["valor1", "valor2"], "blackList": ["valor3"] }
whiteList inclui apenas empresas que possuem os valores informados;
blackList exclui empresas que possuem os valores informados. Ambas as listas podem ser vazias.
| Campo | Tipo | Obrigatório | Descrição |
|---|---|---|---|
employeeCountRange |
{ min: int, |
Não |
Faixa de número de funcionários. Use exatamente uma das cinco faixas válidas:
|
postalCodes |
FormValue | Não | CEPs no formato XXXXX-XXX (ex: "01310-100"). |
states |
FormValue | Não | Siglas de UF brasileiras, 2 letras (ex: "SP", "RJ"). |
cities |
FormValue | Não | Nomes de cidades (ex: "São Paulo", "Campinas"). |
neighborhoods |
FormValue | Não | Nomes de bairros (ex: "Centro", "Jardim Paulista"). |
primaryCnae |
FormValue | Não | Código CNAE primário da empresa (apenas dígitos, ex: "6201500"). |
secondaryCnae |
FormValue | Não | Código CNAE secundário da empresa (apenas dígitos, ex: "6201500"). |
unifiedCnae |
{ mode: int, |
Não |
Filtro unificado de CNAE — aplica sobre CNAE primário, secundário ou ambos conforme o mode:
|
companySize |
FormValue | Não |
Sigla do porte da empresa. Envie exatamente uma destas strings — qualquer valor fora da lista retorna 400:
|
specialStatus |
FormValue | Não |
ID da situação especial da empresa:
|
registrationStatus |
FormValue | Não |
ID da situação cadastral da empresa:
|
openingDateStart |
string | Não | Data de abertura mínima, no formato dd/MM/yyyy (ex: "01/01/2010"). |
openingDateEnd |
string | Não | Data de abertura máxima, no formato dd/MM/yyyy (ex: "31/12/2020"). Deve ser maior ou igual a openingDateStart quando ambos forem informados. |
POST /api/LookALike/v2/SearchPreview HTTP/1.1
Host: {base-url-directdata}
Token: 00000000-0000-0000-0000-000000000000
Content-Type: application/json
{
"numberOfResults": 5000,
"filters": {
"states": { "whiteList": ["SP"], "blackList": [] },
"cities": { "whiteList": ["São Paulo"], "blackList": [] },
"neighborhoods": { "whiteList": ["Centro", "Bela Vista"], "blackList": [] },
"primaryCnae": { "whiteList": ["6201500", "6202300"], "blackList": [] },
"companySize": { "whiteList": ["ME", "EPP"], "blackList": [] },
"registrationStatus": { "whiteList": ["1"], "blackList": [] },
"employeeCountRange": { "min": 10, "max": 49 },
"openingDateStart": "01/01/2010",
"openingDateEnd": "31/12/2020"
},
"ignoredCnpjList": [
"12.345.678/0001-99",
"98765432000111"
]
}
{
"numberOfResults": 1000,
"filters": {
"states": { "whiteList": ["SP", "RJ"], "blackList": [] },
"unifiedCnae": {
"mode": 3,
"whiteList": ["4711302", "4712100"],
"blackList": []
},
"companySize": { "whiteList": ["EPP", "MEDIA", "GRANDE"], "blackList": [] }
}
}
| Campo | Tipo | Descrição |
|---|---|---|
total | long | Total de empresas encontradas (capado em numberOfResults). |
searchGuid | Guid | Chave efêmera desta busca. Envie-a no Purchase em vez de reenviar os filtros. Válida por 15 min e consumida na primeira compra. |
rows | array | Amostra de até 5 empresas (razão social mascarada, CNPJ mascarado, UF, porte, situação, data de abertura, CNAE principal e CNAEs secundários). |
{
"total": 42,
"searchGuid": "653805e2-1e6b-43c6-acb8-ccedbf44a96e",
"rows": [
{
"companyName": "ACM* ****CI* LTDA",
"cnpj": "12.***.***/**01-**",
"state": "SP",
"companySize": "ME",
"registrationStatus": "Ativa",
"foundationDate": "12/03/2010",
"mainCnae": { "code": "47.11-3-02", "description": "Comércio varejista de mercadorias em geral" },
"secondaryCnaes": []
}
],
"success": true,
"elapsedTimeMs": 4523,
"dateTimeExecution": "07/07/2026 16:41:01",
"error": null
}
SearchPreview gera um SearchGuid novo,
mesmo se você mandar exatamente o mesmo filtro. Se chamar 3 vezes, você tem 3 guids válidos ao mesmo tempo (cada um com
seu TTL de 15 min). Sempre use o SearchGuid mais recente na hora de comprar — os anteriores
continuam válidos até expirarem, mas usar um antigo não traz benefício e ainda ocupa espaço no cache.
Retorna o preço unitário atual do Look a Like. Valor global — não varia por cliente. Não gera cobrança.
Sem body e sem query params. Só o header Token.
| Campo | Tipo | Descrição |
|---|---|---|
unitPrice | decimal | Preço unitário atual por empresa (em currency). |
currency | string | Moeda do preço. Fixo BRL. |
{
"unitPrice": 0.36,
"currency": "BRL",
"success": true,
"elapsedTimeMs": 3,
"dateTimeExecution": "07/07/2026 16:40:00",
"error": null
}
Confirma a compra e cobra sua empresa por cada empresa incluída no lote. Aceita dois modos:
searchGuid retornado pelo SearchPreview. A lista é criada nesse momento.listGuid retornado pela primeira compra. Válido por 30 dias.| Campo | Tipo | Obrigatório | Descrição |
|---|---|---|---|
searchGuid | Guid? | Exclusivo com listGuid | SearchGuid do SearchPreview. Use na primeira compra. |
listGuid | Guid? | Exclusivo com searchGuid | ListGuid da primeira compra. Use para comprar mais empresas da mesma lista. |
quantity | int | Sim | Quantidade de empresas a comprar neste lote. Se maior que o disponível, a API rejeita com 400. |
searchGuid ou listGuid.
Enviar ambos, ou nenhum, resulta em 400. Não use string vazia ("") — omita o campo ou envie null.
POST /api/LookALike/v2/Purchase HTTP/1.1
Token: aaaaaaaa-bbbb-cccc-dddd-eeeeeeeeeeee
Content-Type: application/json
{
"searchGuid": "653805e2-1e6b-43c6-acb8-ccedbf44a96e",
"quantity": 10
}
Ou, para comprar mais empresas de uma lista existente:
{
"listGuid": "589d81b6-a5f5-4dc9-b061-4578f59323f4",
"quantity": 5
}
| Campo | Tipo | Descrição |
|---|---|---|
listGuid | Guid | Identificador persistente da lista. Guarde para futuras compras da mesma busca (até availableUntil). |
exportGuid | Guid | Identificador deste lote específico. Use em GetExport/Download. |
quantityCharged | long | Quantidade efetivamente cobrada (igual ao quantity pedido em caso de sucesso). |
amountCharged | decimal | Valor total cobrado nesta transação. |
currency | string | Moeda. Fixo BRL. |
status | string | Status descritivo do compilado (ex.: "Pago", "Enriquecendo Arquivo", "Concluído"). |
availableUntil | string | Data-limite (30 dias após a criação da lista) até quando o listGuid aceita novas compras. |
purchasedAt | string | Data-hora desta compra. |
totalOfList | long | Total original da lista (valor da busca original, imutável). |
alreadyPurchased | long | Total já comprado da lista (inclui esta transação). |
available | long | Empresas ainda disponíveis para compras futuras nesta lista. |
{
"listGuid": "589d81b6-a5f5-4dc9-b061-4578f59323f4",
"exportGuid": "3da0f3eb-3748-453b-900b-c8f2e50a59e7",
"quantityCharged": 10,
"amountCharged": 3.60,
"currency": "BRL",
"status": "Enriquecendo Arquivo",
"availableUntil": "06/08/2026, 16:31",
"purchasedAt": "07/07/2026, 16:41",
"totalOfList": 42,
"alreadyPurchased": 10,
"available": 32,
"success": true,
"elapsedTimeMs": 16595,
"dateTimeExecution": "07/07/2026 16:41:01",
"error": null
}
totalOfList, alreadyPurchased e available
vêm populados tanto no sucesso quanto no erro. Se você receber 400 por quantidade inválida, esses
campos mostram exatamente quantas empresas restam para compra, sem precisar chamar outro endpoint.
{
"listGuid": "00000000-0000-0000-0000-000000000000",
"exportGuid": null,
"quantityCharged": 0,
"amountCharged": 0,
"currency": "BRL",
"status": "Bad Request",
"availableUntil": "",
"purchasedAt": null,
"totalOfList": 42,
"alreadyPurchased": 32,
"available": 10,
"success": false,
"elapsedTimeMs": 45,
"dateTimeExecution": "07/07/2026 17:15:22",
"error": {
"fieldName": "Quantity",
"message": "A quantidade deve ser maior que zero e não pode exceder o total encontrado no preview."
}
}
Retorna o status atual de um lote de compra. Após o Purchase, o compilado passa pelos estágios
Pago → Enriquecendo Arquivo → Concluído. Baixe o arquivo em Download apenas quando
isDownloadReady for true.
| Campo | Tipo | Descrição |
|---|---|---|
exportGuid | Guid | Retornado no Purchase. |
| Campo | Tipo | Descrição |
|---|---|---|
exportGuid | Guid | Eco do path. |
exportStatus | string | Status descritivo em pt-BR (ex.: "Pago", "Enriquecendo Arquivo", "Concluído"). |
listName | string | Nome da lista pai (auto-gerado como API_Preview_{listGuid}). |
quantity | long | Quantidade cobrada neste lote. |
amountCharged | decimal | Valor cobrado neste lote. |
currency | string | Moeda. Fixo BRL. |
purchasedAt | string | Data-hora da compra. |
completedAt | string? | Data-hora de conclusão (preenchido só quando Concluído). |
refundReason | string? | Motivo do estorno, se houver. |
isDownloadReady | bool | true quando o arquivo está pronto para download. |
{
"exportGuid": "3da0f3eb-3748-453b-900b-c8f2e50a59e7",
"exportStatus": "Concluído",
"listName": "API_Preview_589d81b6-a5f5-4dc9-b061-4578f59323f4",
"quantity": 10,
"amountCharged": 3.60,
"currency": "BRL",
"purchasedAt": "07/07/2026 16:41:01",
"completedAt": "07/07/2026 16:44:38",
"refundReason": null,
"isDownloadReady": true,
"success": true,
"elapsedTimeMs": 12,
"dateTimeExecution": "07/07/2026 17:00:00",
"error": null
}
Baixa o arquivo ZIP enriquecido do lote. Disponível apenas quando exportStatus == "Concluído".
| Campo | Tipo | Descrição |
|---|---|---|
exportGuid | Guid | Retornado no Purchase. |
Em caso de sucesso, retorna 200 OK com o corpo em application/zip
(stream binário — não é JSON).
Nome do arquivo: LookALike-{ListName}.zip.
| HTTP | Situação |
|---|---|
404 | Export não encontrado ou não pertence à empresa autenticada. |
409 | Export ainda não está com status Concluído. |
502 | Falha ao recuperar o arquivo do serviço de enriquecimento (indisponibilidade temporária). |
Em qualquer resposta com success: false, o corpo inclui o campo error:
"error": {
"fieldName": "Quantity",
"message": "A quantidade deve ser maior que zero e não pode exceder o total encontrado no preview."
}
| HTTP | Situação | Endpoints |
|---|---|---|
400 | Body inválido, filtros vazios ou quantity <= 0 / quantity > disponível. | SearchPreview, Purchase |
400 | Enviou searchGuid + listGuid juntos, ou nenhum dos dois. | Purchase |
401 | Token ausente/inválido. | Todos |
402 | Saldo insuficiente ou falha no pagamento. | Purchase |
403 | Cliente bloqueado ou produto não contratado. | Purchase |
404 | SearchGuid ou ListGuid não encontrado (ou pertence a outro cliente). | Purchase |
404 | Export não encontrado ou não é do cliente. | GetExport, Download |
409 | Busca expirada (SearchGuid ficou no cache mais de 15 min). | Purchase |
409 | Busca retornou total = 0 — nenhuma empresa bate com o filtro. | Purchase |
409 | Lista é de uma versão anterior (v1) e não aceita novas compras. | Purchase |
409 | Lista expirou (30 dias após a criação). | Purchase |
409 | Lista ainda está sendo materializada — aguarde alguns segundos e tente novamente. | Purchase |
409 | Lista totalmente consumida — todas as empresas já foram compradas. | Purchase |
409 | Export ainda não está com status Concluído. | Download |
429 | Limite de requisições simultâneas atingido. | SearchPreview, Purchase |
500 | Erro interno inesperado. | Todos |
502 | Falha ao contatar o serviço de enriquecimento. | Download |
Os endpoints SearchPreview e Purchase têm limite de requisições simultâneas
por Token (não por janela de tempo, pois cada requisição pode levar até 5 min no pior caso).
| Endpoint | Simultâneas | Fila |
|---|---|---|
POST /v2/SearchPreview | 2 | 2 |
POST /v2/Purchase | 1 | 2 |
Quando o limite é atingido, a API retorna 429 Too Many Requests.
Espere alguma requisição pendente concluir antes de tentar de novo.
SearchPreview gera um SearchGuid novo — mesmo se o filtro for idêntico.SearchGuid vive em memória por 15 minutos.Purchase — não dá para reutilizar.SearchPreview de novo.SearchGuid gerado por outra empresa nunca funciona no seu token.Purchase materializa a lista e devolve um ListGuid persistente.Purchase passando o mesmo listGuid para comprar mais empresas da mesma busca.available na resposta do Purchase mostra o saldo atual.listGuid expira e a lista bloqueia novas compras — refaça o SearchPreview para gerar uma nova busca com dados frescos.409.