Pagination
API v3 list endpoints use page-based pagination.
Pagination parameters
List endpoints support these pagination parameters:
| Parameter | Type | Default | Limits | Description |
|---|---|---|---|---|
page | integer | 1 | Minimum 1 | Page number to retrieve. |
limit | integer | 20 | Between 1 and 100 | Maximum records returned per page. |
include_total | boolean | true | true, false, 1, or 0 | Set false to skip exact totals. |
Values below the allowed minimum are normalized to the minimum. A limit greater than 100 is capped at 100.
curl "https://yourbusiness.salesbinder.com/api/v3/customers?page=2&limit=50" \
--header "Authorization: Bearer YOUR_API_KEY"Pagination response
{
"object": "list",
"url": "/api/v3/customers",
"has_more": true,
"data": [],
"pagination": {
"page": 2,
"per_page": 50,
"total_pages": 4,
"total_records": 184
}
}| Field | Description |
|---|---|
has_more | true when another page follows the current page. |
page | Current requested page. |
per_page | Effective page size after limits are applied. |
total_pages | Total pages available at the current page size. |
total_records | Total records matching the request and the user's visibility boundary. |
To retrieve all records, increment page until has_more is false.
Optional totals
For imports and other workflows that only need the next page, request include_total=false. The server skips the exact count query and checks for one additional record to determine has_more. The extra record is not returned. Record contents, filters, ordering, page, and per_page stay the same; total_pages and total_records are omitted rather than estimated. Omitting the parameter or using include_total=true preserves the existing response. Invalid values return 422 with invalid_query_parameter and param: "include_total".
{
"object": "list",
"url": "/api/v3/customers",
"has_more": true,
"data": [],
"pagination": { "page": 1, "per_page": 100 }
}Example import loop (JavaScript):
let page = 1;
while (true) {
const response = await fetch(
`${baseUrl}/api/v3/customers?limit=100&page=${page}&include_total=false`,
{ headers: { Authorization: `Bearer ${apiKey}` } }
);
if (!response.ok) throw new Error(`API request failed: ${response.status}`);
const result = await response.json();
await processRecords(result.data);
if (!result.has_more) break;
page += 1;
}This option applies to public paginated collections, including nested lists. For exact-ID requests, include_total=false also omits totals; those requests already avoid a count query and remain unpaginated. This remains page-number pagination, so large offsets still have a cost.
Sync cursors
Incremental sync uses signed continuation cursors instead of page numbers. Its limit bounds examined markers, so follow has_more even when a filtered page has no changes. Save each cursor only after applying its page successfully.