§ Conventions
Pagination
All list endpoints use cursor-based pagination. There are no page numbers, no offsets, and no total counts — just a stable opaque cursor and a fixed limit.
How it works
Pass limit (default 25, max 100). The response includes a data array and a nextCursor. When nextCursoris null, you've reached the end.
First pagebash
curl "https://livesofthesaintscalendar.com/api/v1/saints?limit=25" \
-H "Authorization: Bearer osc_live_…"jsonjson
{
"data": [ /* 25 saints */ ],
"nextCursor": "saint-john-chrysostom"
}Next pagebash
curl "https://livesofthesaintscalendar.com/api/v1/saints?limit=25&cursor=saint-john-chrysostom" \
-H "Authorization: Bearer osc_live_…"Looping through everything
javascriptjavascript
let cursor = undefined;
const all = [];
do {
const url = new URL("https://livesofthesaintscalendar.com/api/v1/saints");
url.searchParams.set("limit", "100");
if (cursor) url.searchParams.set("cursor", cursor);
const res = await fetch(url, {
headers: { Authorization: `Bearer ${process.env.LOTS_API_KEY}` },
});
const page = await res.json();
all.push(...page.data);
cursor = page.nextCursor;
} while (cursor);Stability
Cursors are stable for at least 24 hours. If you re-run a paginated walk after a long delay and a row was deleted, you may skip the immediate next slug — re-fetch the first page if you need a strict snapshot.