Docs / API Reference / Leads
Leads
Search Google Maps for local business leads and retrieve the results programmatically. A search returns a query ID immediately — poll /progress until it completes, then fetch the leads.
Start a Search
/api/v1/leads/searchauthTrigger a new lead search against Google Maps. Returns a query ID immediately — the actual extraction runs asynchronously.
Body parameters
query*Business type or niche to search for. E.g. "Dentists", "Plumbers in Paris".
locationCity or region to restrict the search. Can also be embedded in query.
localeenLanguage code for results (e.g. fr, de).
countryUS2-letter country code used to bias results geographically.
resultLimit20Maximum number of leads to extract. Higher limits cost more credits.
autoEnrichfalseIf true, automatically run email enrichment after the search completes.
Example response
{
"success": true,
"data": {
"query": {
"id": "cm9search123",
"query": "Dentists",
"location": "Austin, TX",
"status": "PENDING",
"totalRecords": 0
},
"isNew": true
}
}curl -X POST https://leadsapi.postorbit.io/api/v1/leads/search \
-H "Authorization: Bearer $LOCALLEADS_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"query": "Dentists",
"location": "Austin, TX",
"resultLimit": 100
}'Poll Search Progress
/api/v1/leads/query/:id/progressauthCheck the status of a running search. Poll this until status is COMPLETED or FAILED.
Path parameters
:id*The query ID returned by POST /search.
{
"success": true,
"data": {
"status": "PROCESSING", // PENDING | PROCESSING | COMPLETED | FAILED
"totalRecords": 47,
"enrichmentStatus": null, // null | PENDING | PROCESSING | COMPLETED
"enrichmentProgress": 0
}
}resultLimit. Stop polling when status is COMPLETED or FAILED.// Poll until complete
async function waitForSearch(queryId) {
const url = `https://leadsapi.postorbit.io/api/v1/leads/query/${queryId}/progress`;
const headers = { Authorization: `Bearer ${process.env.LOCALLEADS_API_KEY}` };
while (true) {
const { data } = await fetch(url, { headers }).then((r) => r.json());
if (data.status === "COMPLETED") return data;
if (data.status === "FAILED") throw new Error("Search failed");
await new Promise((r) => setTimeout(r, 3000)); // wait 3s
}
}Get Leads for a Search
/api/v1/leads/query/:idauthRetrieve the paginated list of leads extracted by a completed search.
Path parameters
:id*Query ID.
Query parameters
page1Page number.
limit20Results per page. Max 100.
{
"success": true,
"data": {
"query": { "id": "cm9search123", "query": "Dentists", "status": "COMPLETED" },
"leads": [
{
"id": "cm9lead001",
"name": "Austin Family Dentistry",
"phone": "+1 512-555-0101",
"website": "https://austinfamilydentistry.com",
"address": "123 Main St, Austin, TX 78701",
"rating": 4.8,
"reviewCount": 312,
"email": null,
"qualityTier": "high"
}
]
},
"meta": { "total": 97, "page": 1, "limit": 20 }
}List All Leads
/api/v1/leads/allauthRetrieve all leads across every search for your organisation with sorting and full-text search.
Query parameters
page1Page number.
limit20Results per page.
sortBycreatedAtField to sort by.
sortOrderdescSort direction.
searchFull-text search across name, email, phone, and address.
qualityTierFilter by lead quality tier.
curl "https://leadsapi.postorbit.io/api/v1/leads/all?limit=50&qualityTier=high" \
-H "Authorization: Bearer $LOCALLEADS_API_KEY"List Previous Searches
/api/v1/leads/prev-searchesauthList all search queries run by your organisation, newest first.
Query parameters
page1Page number.
limit20Results per page.
{
"success": true,
"data": [
{
"id": "cm9search123",
"query": "Dentists",
"location": "Austin, TX",
"status": "COMPLETED",
"totalRecords": 97,
"createdAt": "2026-05-05T10:00:00.000Z"
}
],
"meta": { "total": 14, "page": 1, "limit": 20 }
}/search is stricter than other endpoints: 20 searches per minute per user. Batch your requests if automating large-scale searches.