> For the complete documentation index, see [llms.txt](https://docs.hydromancer.xyz/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.hydromancer.xyz/readme/rest-api/candlesticks/candlesnapshot.md).

# candleSnapshot

{% hint style="info" %}

### Currently we offer 1s, 15s, and 30s candlesticks which are not available on Hyperliquid natively. Our candlesticks endpoint also return more than 5k last candles available through the native Hyperliquid API.

{% endhint %}

### Overview

Returns OHLCV candle data for a given coin and interval. Uses the same `candleSnapshot` request type as Hyperliquid's native API, so existing integrations work with no code changes — just point at Hydromancer.

### Request

* **Endpoint**: `POST /info`

```json
{
    "type": "candleSnapshot",
    "req": {
        "coin": "BTC",
        "interval": "1m",
        "startTime": 1700000000000,
        "endTime": 1700003600000
    }
}
```

| Field       | Type   | Required | Description                                                                        |
| ----------- | ------ | -------- | ---------------------------------------------------------------------------------- |
| `coin`      | string | Yes      | Coin name. For HIP-3 assets, prefix with dex name (e.g. `"hyna:ETH"`)              |
| `interval`  | string | Yes      | Candle interval (see valid intervals below)                                        |
| `startTime` | number | Yes      | Start time in milliseconds since epoch (inclusive)                                 |
| `endTime`   | number | Yes      | End time in milliseconds since epoch (exclusive). Must be greater than `startTime` |
| `limit`     | number | No       | Maximum number of candles to return. Default and max: 5000                         |

#### Valid intervals

| Interval | Duration                 |
| -------- | ------------------------ |
| `1s`     | 1 second                 |
| `15s`    | 15 seconds               |
| `30s`    | 30 seconds               |
| `1m`     | 1 minute                 |
| `3m`     | 3 minutes                |
| `5m`     | 5 minutes                |
| `15m`    | 15 minutes               |
| `30m`    | 30 minutes               |
| `1h`     | 1 hour                   |
| `2h`     | 2 hours                  |
| `4h`     | 4 hours                  |
| `8h`     | 8 hours                  |
| `12h`    | 12 hours                 |
| `1d`     | 1 day                    |
| `3d`     | 3 days                   |
| `1w`     | 1 week (Monday-aligned)  |
| `1M`     | 1 month (calendar month) |

{% hint style="info" %}
`1s`, `15s`, and `30s` candles are Hydromancer additions — they are not available on the native Hyperliquid API.
{% endhint %}

### Response

Returns a JSON array of candle objects sorted by time ascending. Maximum 5000 candles per request.

```json
[
    {
        "s": "BTC",
        "i": "1m",
        "t": 1700000040000,
        "T": 1700000099999,
        "o": "45000.00",
        "h": "45100.50",
        "l": "44980.00",
        "c": "45050.25",
        "v": "123.45",
        "q": "5560125.00",
        "n": 312,
        "x": true
    }
]
```

| Field | Type           | Description                                                                         |
| ----- | -------------- | ----------------------------------------------------------------------------------- |
| `s`   | string         | Coin name                                                                           |
| `i`   | string         | Interval string                                                                     |
| `t`   | number         | Candle open time (milliseconds, interval start)                                     |
| `T`   | number         | Candle close time (milliseconds, interval end)                                      |
| `o`   | string         | Open price                                                                          |
| `h`   | string         | High price                                                                          |
| `l`   | string         | Low price                                                                           |
| `c`   | string         | Close (latest) price                                                                |
| `v`   | string         | Volume in base asset                                                                |
| `q`   | string \| null | Quote volume (notional value, sum of price \* size). May be `null` — see note below |
| `n`   | number         | Number of trades                                                                    |
| `x`   | boolean        | `true` if the candle is closed/finalized, `false` if still open                     |

{% hint style="info" %}
**Differences from Hyperliquid's response:** Hydromancer adds `q` (quote volume) and `x` (closed flag). Field names (`s`, `i`, `t`, `T`, `o`, `h`, `l`, `c`, `v`, `n`) are identical to Hyperliquid's format.
{% endhint %}

{% hint style="warning" %}
**`q` may be `null` for candles before 2025-08-01.** Pre-Aug-2025 history was imported from Hyperliquid's `candleSnapshot` API, which does not expose quote volume. Rather than emit a misleading sentinel zero, those buckets are returned as `null`. This propagates to aggregated intervals (`3d`, `1w`, `1M`) whose window includes any pre-cutoff day. From 2025-08-01 onward, `q` is always a string. Clients parsing `q` must handle the `null` branch (e.g. `parseFloat(c.q ?? "0")` or skipping the field entirely for older buckets).
{% endhint %}

### Rate limits

20 points per request (see [rate limits](/readme/rest-api/rate-limits-and-user-limits.md)).

### Examples

{% tabs %}
{% tab title="Python" %}

```python
import requests
import os

api_key = os.environ["HYDROMANCER_API_KEY"]
base_url = os.getenv("HYDROMANCER_API_URL", "https://api.hydromancer.xyz")

resp = requests.post(
    f"{base_url}/info",
    json={
        "type": "candleSnapshot",
        "req": {
            "coin": "BTC",
            "interval": "1h",
            "startTime": 1700000000000,
            "endTime": 1700036000000,
        },
    },
    headers={
        "Content-Type": "application/json",
        "Authorization": f"Bearer {api_key}",
    },
)
candles = resp.json()

for c in candles:
    status = "closed" if c["x"] else "open"
    print(f"{c['t']}  O={c['o']}  H={c['h']}  L={c['l']}  C={c['c']}  V={c['v']}  trades={c['n']}  [{status}]")
```

{% endtab %}

{% tab title="JavaScript" %}

```javascript
const axios = require('axios');

const apiKey = process.env.HYDROMANCER_API_KEY;
const baseUrl = process.env.HYDROMANCER_API_URL || 'https://api.hydromancer.xyz';

async function getCandles() {
    const resp = await axios.post(
        `${baseUrl}/info`,
        {
            type: 'candleSnapshot',
            req: {
                coin: 'BTC',
                interval: '1h',
                startTime: 1700000000000,
                endTime: 1700036000000,
            },
        },
        {
            headers: {
                'Content-Type': 'application/json',
                'Authorization': `Bearer ${apiKey}`,
            },
        }
    );

    for (const c of resp.data) {
        const status = c.x ? 'closed' : 'open';
        console.log(`${c.t}  O=${c.o}  H=${c.h}  L=${c.l}  C=${c.c}  V=${c.v}  trades=${c.n}  [${status}]`);
    }
}

getCandles().catch(console.error);
```

{% endtab %}
{% endtabs %}

### Common errors

| Error                                    | Cause                                       |
| ---------------------------------------- | ------------------------------------------- |
| `Invalid interval`                       | Interval string not in the valid list above |
| `endTime must be greater than startTime` | `endTime <= startTime`                      |
| `Missing required field: coin`           | `coin` field not provided                   |
