# Pagination

List endpoints use **cursor-based** pagination — opaque cursors rather than `offset` / `limit`. This keeps results stable when new records are inserted during your traversal.

## Request Parameters

| Parameter | Type    | Detail                                                                        |
| --------- | ------- | ----------------------------------------------------------------------------- |
| `limit`   | integer | Page size. Default `50`. Maximum varies per endpoint (often `200` or `2000`). |
| `cursor`  | string  | Pagination cursor. Omit (or pass `""`) on the first request.                  |

## Response Shape

The `data` block contains:

```json
{
  "code": "0",
  "msg": "",
  "data": {
    "list": [ … ],
    "next_cursor": "eyJsYXN0X2lkIjoiMTIzIn0=",
    "has_more": true
  },
  "trace_code": ""
}
```

| Field         | Detail                                                             |
| ------------- | ------------------------------------------------------------------ |
| `list`        | The current page of records.                                       |
| `next_cursor` | Pass back as `cursor` for the next page. `null` when no more data. |
| `has_more`    | Convenience boolean — equivalent to `next_cursor != null`.         |

## Combining With Time Ranges

`start_time` and `end_time` define the **data range** (a filter on the underlying record set). `cursor` walks within that filtered range.

* **First request**: pass `start_time` / `end_time` (optional) and `limit`. Omit `cursor`.
* **Subsequent requests**: keep the same `start_time` / `end_time` / `limit`, and pass the previous response's `next_cursor` as `cursor`.

```python
import requests

base_params = {
    "address": "0xabc…",
    "symbol_id": 100001,
    "start_time": 1719000000000,
    "end_time": 1719500000000,
    "limit": 200,
}

cursor = None
while True:
    params = dict(base_params)
    if cursor:
        params["cursor"] = cursor
    r = requests.get("http://10.34.8.77:8481/v1/trade/orders/history", params=params).json()
    for o in r["data"]["list"]:
        process(o)
    if not r["data"]["has_more"]:
        break
    cursor = r["data"]["next_cursor"]
```

## Retention Caps

Some history endpoints cap the absolute number of records you can iterate, even with pagination:

| Endpoint                                 | Per-page max | Total retrievable          |
| ---------------------------------------- | ------------ | -------------------------- |
| `GET /v1/trade/orders/history`           | 2000         | 10,000 most-recent records |
| `GET /v1/trade/executions`               | 2000         | 10,000 most-recent records |
| `GET /v1/account/asset-flow`             | 2000         | 10,000 most-recent records |
| `GET /v1/account/positions/history`      | 200          | 1,000 most-recent records  |
| `GET /v1/explorer/address/{address}/txs` | —            | 500 most-recent records    |

{% hint style="info" %}
If you need older data than the retention cap allows, query the chain directly via the **Explorer** endpoints.
{% endhint %}


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://docs.lynxtrade.world/conventions/pagination.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
