mastra-ai/mastra · error
page must be 0 when perPage is false
Error message
page must be 0 when perPage is false
What it means
When perPage is false (fetch-all mode), only page 0 is valid because there is a single unpaginated result set. Passing any other page with perPage: false throws 'page must be 0 when perPage is false'.
Source
Thrown at packages/core/src/storage/domains/memory/base.ts:501
* @throws Error if perPageInput is false and page !== 0
* @throws Error if perPageInput is invalid (not false or a non-negative safe integer)
* @throws Error if page is invalid or offset would overflow
*/
protected validatePaginationInput(page: number, perPageInput: number | false): void {
// Validate perPageInput type first
if (perPageInput !== false) {
if (typeof perPageInput !== 'number' || !Number.isFinite(perPageInput) || !Number.isSafeInteger(perPageInput)) {
throw new Error('perPage must be false or a safe integer');
}
if (perPageInput < 0) {
throw new Error('perPage must be >= 0');
}
}
// When fetching all (perPage: false), only page 0 is valid
if (perPageInput === false) {
if (page !== 0) {
throw new Error('page must be 0 when perPage is false');
}
// Still validate page is a valid integer
if (!Number.isFinite(page) || !Number.isSafeInteger(page)) {
throw new Error('page must be >= 0');
}
return;
}
// For numeric perPage, delegate to existing validation
this.validatePagination(page, perPageInput);
}
}
const THREAD_ORDER_BY_SET: Record<ThreadOrderBy, true> = {
createdAt: true,
updatedAt: true,
};
View on GitHub (pinned to 75dd419e61)
Solutions
- Force page to 0 whenever perPage is false.
- Reset the pagination state when switching to fetch-all mode.
- Conditionally build the params object: perPage === false ? { page: 0, perPage: false } : { page, perPage }.
- Ignore/skip the page parameter in fetch-all code paths.
Example fix
// before
await storage.listThreads({ page: currentPage, perPage: false });
// after
await storage.listThreads({ page: 0, perPage: false }); Defensive patterns
Strategy: validation
Validate before calling
const params = perPage === false
? { page: 0, perPage: false }
: { page, perPage }; Type guard
function validListParams(p: { page: number; perPage: number | false }) {
return p.perPage === false ? { ...p, page: 0 } : p;
} Try / catch
try {
await storage.listThreads(params);
} catch (e) {
if (e instanceof Error && e.message === 'page must be 0 when perPage is false') {
return storage.listThreads({ page: 0, perPage: false });
}
throw e;
} Prevention
- Reset page to 0 whenever switching to fetch-all mode
- Centralize list-params construction in one helper
- Do not forward UI pagination state into fetch-all calls
When it happens
Trigger: Calling listThreads/listMessages with { page: 2, perPage: false }; combining 'fetch all' with UI pagination state that is already on page N.
Common situations: Export-all feature reusing paginated request state; toggling perPage to false without resetting the page counter; generic request-mapping code that always forwards page.
Related errors
- perPage must be >= 0
- page must be >= 0
- page value too large
- Invalid knowledge node cursor.
- page must be >= 0
AI-assisted analysis of mastra-ai/mastra@75dd419e61 (2026-08-30).
Data as JSON: /api/errors/4a544a4fc58c7fdf.
Report an issue: GitHub.