How It Works
All list endpoints return a paginated response with a has_more field. When has_more is true, pass the last item's ID as starting_after to get the next page.
{
"object": "list",
"data": [ ... ],
"has_more": true,
"url": "/v1/stores/{storeId}/products"
}Parameters
| Parameter | Type | Description |
|---|---|---|
| limit | integer | Items per page. Default 25, max 500. |
| starting_after | string | Cursor for forward pagination. Pass the ID of the last item on the current page. |
| ending_before | string | Cursor for backward pagination. Pass the ID of the first item on the current page. |
Forward Pagination
Fetch the first page, then use starting_after with the last item's ID to get subsequent pages.
# First page
curl ".../products?limit=10"
# Next page (use last item's id)
curl ".../products?limit=10&starting_after=550e8400-..."
# Keep going until has_more is falseBackward Pagination
Use ending_before with the first item's ID on the current page to navigate backward.
# Previous page
curl ".../products?limit=10&ending_before=a1b2c3d4-..."Auto-Paginate (TypeScript)
async function* paginate(url: string, apiKey: string) {
let cursor: string | undefined;
while (true) {
const params = new URLSearchParams({ limit: '100' });
if (cursor) params.set('starting_after', cursor);
const res = await fetch(`${url}?${params}`, {
headers: { 'x-api-key': apiKey },
});
const page = await res.json();
for (const item of page.data) {
yield item;
}
if (!page.has_more) break;
cursor = page.data[page.data.length - 1].id;
}
}
// Usage
for await (const product of paginate(baseUrl + '/products', key)) {
console.log(product.name);
}