> For the complete documentation index, see [llms.txt](https://docs.enlyze.com/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.enlyze.com/en/enlyze-api/pagination.md).

# Pagination

How to page through large result sets in the ENLYZE API.

List endpoints in the ENLYZE API return results one page at a time. Instead of returning every record at once, the API returns a single page along with a cursor you use to fetch the next page. With `limit` you set how many records a page holds at most.

## How pagination works

The ENLYZE API uses cursor-based pagination. The flow is always the same:

1. Call a list endpoint without a `cursor` to get the first page.
2. Read the `metadata.next_cursor` value from the response.
3. Call the same endpoint again, passing that value as the `cursor` parameter, to get the next page.
4. Repeat steps 2 and 3 until `metadata.next_cursor` is `null`. At that point there is no more data.

Keep all other parameters (such as filters and `limit`) unchanged across follow-up requests. Otherwise the cursor is no longer valid.

## Response structure

Every paginated response has the same structure:

| Field                  | Type             | Description                                                                  |
| ---------------------- | ---------------- | ---------------------------------------------------------------------------- |
| `data`                 | Array            | The records on the current page.                                             |
| `metadata.next_cursor` | String or `null` | The continuation point for the next page. `null` when there is no more data. |

On the request side, you control pagination with two parameters:

| Parameter | Location | Description                                                                                                                                            |
| --------- | -------- | ------------------------------------------------------------------------------------------------------------------------------------------------------ |
| `cursor`  | Query    | The starting point of the page to fetch. Pass the `metadata.next_cursor` value from the previous response. Without a `cursor`, you get the first page. |
| `limit`   | Query    | The maximum number of records per page. Without a `limit`, a page holds up to 1000 records. 1000 is also the maximum.                                  |

## Control the page size with `limit`

A `limit` below the default shrinks the page. A larger one is not possible, because the default is also the maximum.

`limit` combines with `cursor` and with all filters. If the result set holds more records than `limit` allows, the response still carries a `next_cursor` for the next page. On sorted endpoints, `limit` follows that order: `limit=1` returns the first record of the sort.

A `limit` that is not an integer, is below 1 or above the maximum is rejected with status code `422` (see [Errors](/en/enlyze-api/errors.md)).

{% hint style="info" %}
For the `POST /v2/timeseries` endpoint, `cursor` and `limit` are passed in the request body rather than as query parameters. There, `limit` counts rows of the timeseries: without a `limit`, a page holds up to 10,000 rows, and 10,000 is also the maximum. A row counts even when every requested variable in it is `null`. The response structure with `data` and `metadata.next_cursor` stays the same.
{% endhint %}

## Example

Fetch the first page:

```http
GET https://app.enlyze.com/api/v2/production-runs
```

Response:

```json
{
  "data": [
    { "uuid": "3f2a…" },
    { "uuid": "8b1c…" }
  ],
  "metadata": {
    "next_cursor": "eyJpZCI6MTQ4fQ"
  }
}
```

Fetch the next page by passing `next_cursor` as `cursor`:

```http
GET https://app.enlyze.com/api/v2/production-runs?cursor=eyJpZCI6MTQ4fQ
```

To fetch a single record, for example to check whether there are any production runs at all, set `limit=1`:

```http
GET https://app.enlyze.com/api/v2/production-runs?limit=1
```

On the last page, `next_cursor` is `null`:

```json
{
  "data": [
    { "uuid": "d90e…" }
  ],
  "metadata": {
    "next_cursor": null
  }
}
```

{% hint style="warning" %}
The cursor is an opaque token. Do not modify its contents or build it yourself. Only use the value from `metadata.next_cursor`.
{% endhint %}
