> TickerLayer documentation for AI agents and LLMs, the Markdown version of https://tickerlayer.com/docs/rest/indices
> REST base URL https://api.tickerlayer.com, API key in the `x-api-key` header. WebSocket wss://stream.tickerlayer.com?apiKey=YOUR_API_KEY.
> Any docs page reads as Markdown at its URL plus `.md`. Index: https://tickerlayer.com/llms.txt · Full API reference: https://tickerlayer.com/llms-full.txt

# Indices

Indicative index levels under /indices: discovery, quotes, last trade, snapshots, and aggregates for analytics, display, and operational tooling.

- **Auth:** x-api-key header
- **Base path:** /indices
- **WebSocket:** indices.quotes · indices.trades
- **Symbol format:** Public index codes (e.g. US500, US30, DE40, EU50)

## Symbols

Symbols are generic public codes such as `US500`, `US30`, `US100`, `DE40`, `EU50`, and `JP225`. Unlike stocks and ETFs, index codes carry **no market prefix**: an index is written `HK33`, never `HK:HK33`, and the prefixed form is rejected. Use `GET /indices/symbols` for the curated list enabled for your key (see [Symbols → Indices](https://tickerlayer.com/docs/rest/symbols#indices-symbols)).

## Symbol list

**Endpoint:** `GET /indices/symbols`

Curated index symbols available on the REST API.

### Request

```bash
curl -sS "https://api.tickerlayer.com/indices/symbols" \
  -H "x-api-key: <YOUR_API_KEY>"
```

```python
import requests

res = requests.get(
    "https://api.tickerlayer.com/indices/symbols",
    headers={"x-api-key": "<YOUR_API_KEY>"},
)
print(res.json())
```

```javascript
const res = await fetch("https://api.tickerlayer.com/indices/symbols", {
  headers: { "x-api-key": "<YOUR_API_KEY>" },
});
const data = await res.json();
console.log(data);
```

```go
req, _ := http.NewRequest("GET", "https://api.tickerlayer.com/indices/symbols", nil)
req.Header.Set("x-api-key", "<YOUR_API_KEY>")
```

### Response

```json
{
  "symbols": [
    { "symbol": "DE40", "name": "Germany 40", "aggregates": true },
    { "symbol": "EU50", "name": "Europe 50", "aggregates": true },
    { "symbol": "US500FUT", "name": "US500 Futures", "aggregates": false }
  ]
}
```

### Notes

`aggregates` says whether `/indices/agg/...` serves the symbol. Quotes and snapshots are available for every listed symbol; a few futures and regional codes are quote-only, and the directory says so rather than answering `404` on the bar routes.

## Latest quote

**Endpoint:** `GET /indices/quote/:symbol`

Indicative bid/ask and timestamp from the consolidated REST quote path.

### Path parameters

| Parameter | Type | Required | Description |
| --- | --- | --- | --- |
| `symbol` | string | Yes | Enabled index symbol (e.g. US500, DE40, EU50, JP225). Generic regional codes only, trimmed and uppercased before lookup. Full list: GET /indices/symbols. |

### Request

```bash
curl -sS "https://api.tickerlayer.com/indices/quote/US500" \
  -H "x-api-key: <YOUR_API_KEY>"
```

```python
import requests

res = requests.get(
    "https://api.tickerlayer.com/indices/quote/US500",
    headers={"x-api-key": "<YOUR_API_KEY>"},
)
print(res.json())
```

```javascript
const res = await fetch("https://api.tickerlayer.com/indices/quote/US500", {
  headers: { "x-api-key": "<YOUR_API_KEY>" },
});
const data = await res.json();
console.log(data);
```

```go
req, _ := http.NewRequest("GET", "https://api.tickerlayer.com/indices/quote/US500", nil)
req.Header.Set("x-api-key", "<YOUR_API_KEY>")
```

### Response

```json
{
  "symbol": "US500",
  "bid": 4788.12,
  "ask": 4788.12,
  "bid_size": 62,
  "ask_size": 58,
  "timestamp": 1743512400000
}
```

### Notes

`404 unknown symbol` if the code is not enabled. `404 no quote available` when no consolidated quote can be resolved.

## Last trade

**Endpoint:** `GET /indices/trade/last/:symbol`

Latest indicative trade-style print for the index. size may be null when the feed has no lot size.

### Path parameters

| Parameter | Type | Required | Description |
| --- | --- | --- | --- |
| `symbol` | string | Yes | Enabled index symbol (e.g. US500, DE40, EU50, JP225). Generic regional codes only, trimmed and uppercased before lookup. Full list: GET /indices/symbols. |

### Request

```bash
curl -sS "https://api.tickerlayer.com/indices/trade/last/US500" \
  -H "x-api-key: <YOUR_API_KEY>"
```

```python
import requests

res = requests.get(
    "https://api.tickerlayer.com/indices/trade/last/US500",
    headers={"x-api-key": "<YOUR_API_KEY>"},
)
print(res.json())
```

```javascript
const res = await fetch("https://api.tickerlayer.com/indices/trade/last/US500", {
  headers: { "x-api-key": "<YOUR_API_KEY>" },
});
const data = await res.json();
console.log(data);
```

```go
req, _ := http.NewRequest("GET", "https://api.tickerlayer.com/indices/trade/last/US500", nil)
req.Header.Set("x-api-key", "<YOUR_API_KEY>")
```

### Response

```json
{
  "symbol": "US500",
  "price": 4788.12,
  "size": 62,
  "timestamp": 1743512400000
}
```

### Notes

`404` when the symbol is unknown or no trade-style value can be resolved (message text may be `unknown symbol` or `symbol not available`).

## Snapshot

**Endpoint:** `GET /indices/snapshot/:symbol`

Combined bid/ask, last reference level, previous daily close, and change metrics.

### Path parameters

| Parameter | Type | Required | Description |
| --- | --- | --- | --- |
| `symbol` | string | Yes | Enabled index symbol (e.g. US500, DE40, EU50, JP225). Generic regional codes only, trimmed and uppercased before lookup. Full list: GET /indices/symbols. |

### Request

```bash
curl -sS "https://api.tickerlayer.com/indices/snapshot/US500" \
  -H "x-api-key: <YOUR_API_KEY>"
```

```python
import requests

res = requests.get(
    "https://api.tickerlayer.com/indices/snapshot/US500",
    headers={"x-api-key": "<YOUR_API_KEY>"},
)
print(res.json())
```

```javascript
const res = await fetch("https://api.tickerlayer.com/indices/snapshot/US500", {
  headers: { "x-api-key": "<YOUR_API_KEY>" },
});
const data = await res.json();
console.log(data);
```

```go
req, _ := http.NewRequest("GET", "https://api.tickerlayer.com/indices/snapshot/US500", nil)
req.Header.Set("x-api-key", "<YOUR_API_KEY>")
```

### Response

```json
{
  "symbol": "US500",
  "bid": 4788.12,
  "ask": 4788.12,
  "bid_size": 62,
  "ask_size": 58,
  "last_price": 4788.12,
  "last_timestamp": 1743512400000,
  "prev_close": 4750.00,
  "change": 38.12,
  "change_percent": 0.8025
}
```

### Notes

`change_percent` is `null` when `prev_close` is zero or unavailable.

## Previous bar

**Endpoint:** `GET /indices/agg/:symbol/prev`

Most recent fully completed daily OHLCV bar in UTC (previous session close).

### Path parameters

| Parameter | Type | Required | Description |
| --- | --- | --- | --- |
| `symbol` | string | Yes | Enabled index symbol (e.g. US500, DE40, EU50, JP225). Generic regional codes only, trimmed and uppercased before lookup. Full list: GET /indices/symbols. |

### Query parameters

| Parameter | Type | Description |
| --- | --- | --- |
| `interval` | string | Returns the most recently settled bar at that interval instead of the previous daily bar, and adds `interval`, `bar_start`, `bar_end` and `as_of` to the response. Leave it out for the daily bar. Values: `1m`, `5m`, `15m`, `1h`, `4h`, `1d`. |

### Request

```bash
curl -sS "https://api.tickerlayer.com/indices/agg/US500/prev" \
  -H "x-api-key: <YOUR_API_KEY>"
```

```python
import requests

res = requests.get(
    "https://api.tickerlayer.com/indices/agg/US500/prev",
    headers={"x-api-key": "<YOUR_API_KEY>"},
)
print(res.json())
```

```javascript
const res = await fetch("https://api.tickerlayer.com/indices/agg/US500/prev", {
  headers: { "x-api-key": "<YOUR_API_KEY>" },
});
const data = await res.json();
console.log(data);
```

```go
req, _ := http.NewRequest("GET", "https://api.tickerlayer.com/indices/agg/US500/prev", nil)
req.Header.Set("x-api-key", "<YOUR_API_KEY>")
```

### Response

```json
{
  "symbol": "US500",
  "result": {
    "o": 5950.0,
    "h": 5980.0,
    "l": 5930.0,
    "c": 5965.0,
    "v": null,
    "t": 1732924800000
  }
}
```

### Notes

The bar is the real open, high, low, close and volume of the prior session, taken from the same daily series the range endpoint serves, so it matches `/indices/agg/:symbol/1/day/...` for that date; `v` is `null` where the index has no consolidated volume. `404 no bar available` when the daily bar cannot be resolved yet. A bar requested with `?interval=` is held for a short settle lag after it closes, so small clock differences between callers do not change which bar comes back, and it is the same bar the range endpoint returns for that window. `Cache-Control` and `ETag` mark when the value can next change. While the market is closed the last real bar is returned, still labelled with its own `bar_start`.

## Aggregate bars (OHLCV)

**Endpoint:** `GET /indices/agg/:symbol/:multiplier/:timespan/:from/:to`

Historical bars between two UTC calendar dates.

### Path parameters

| Parameter | Type | Required | Description |
| --- | --- | --- | --- |
| `symbol` | string | Yes | An enabled symbol of this asset class, for example `BTCUSD` or `US:KO`. Trimmed before lookup. |
| `multiplier` | number | Yes | Bar size in units of `timespan`: `1`, `5` or `15` with `minute`; `1` or `4` with `hour`; `1` with `day`. Other pairs return `400`, and the message lists the valid ones. |
| `timespan` | string | Yes | Case-insensitive. Other values return `400`. Values: `minute`, `hour`, `day`. |
| `from` | string | Yes | First UTC date, inclusive, as `YYYY-MM-DD`. |
| `to` | string | Yes | Last UTC date, inclusive, as `YYYY-MM-DD`. Not before `from`. |

### Query parameters

| Parameter | Type | Description |
| --- | --- | --- |
| `limit` | number | Page size, up to `5000`. `results_count` is the size of this page and `total_count` the bars in the whole range; follow `next_offset` until it is `null`. Default: `500`. |
| `offset` | number | Zero-based row offset, applied after sorting. Default: `0`. |
| `sort` | string | Order of bars by timestamp `t`, applied before pagination. Values: `asc`, `desc`. Default: `desc`. |

### Request

```bash
curl -sS "https://api.tickerlayer.com/indices/agg/EU50/1/day/2025-11-01/2025-11-30?sort=desc&limit=2" \
  -H "x-api-key: <YOUR_API_KEY>"
```

```python
import requests

res = requests.get(
    "https://api.tickerlayer.com/indices/agg/EU50/1/day/2025-11-01/2025-11-30?sort=desc&limit=2",
    headers={"x-api-key": "<YOUR_API_KEY>"},
)
print(res.json())
```

```javascript
const res = await fetch("https://api.tickerlayer.com/indices/agg/EU50/1/day/2025-11-01/2025-11-30?sort=desc&limit=2", {
  headers: { "x-api-key": "<YOUR_API_KEY>" },
});
const data = await res.json();
console.log(data);
```

```go
req, _ := http.NewRequest("GET", "https://api.tickerlayer.com/indices/agg/EU50/1/day/2025-11-01/2025-11-30?sort=desc&limit=2", nil)
req.Header.Set("x-api-key", "<YOUR_API_KEY>")
```

### Response

```json
{
  "symbol": "EU50",
  "results_count": 2,
  "results": [
    { "o": 5950.0, "h": 5980.0, "l": 5930.0, "c": 5965.0, "v": null, "t": 1733011200000 },
    { "o": 5920.0, "h": 5945.0, "l": 5905.0, "c": 5935.0, "v": null, "t": 1732924800000 }
  ],
  "next_offset": 2
}
```

### Notes

- `v` may be null when no consolidated volume exists for that interval.
- One request covers at most 31 days of 1-minute bars, 90 of 5-minute, 180 of 15-minute, 365 of hourly, 730 of 4-hour and 5000 of daily bars, counting `from` and `to` as whole UTC days. A longer range returns `400` with the limit in the message.
- Daily bars follow each index's trading days. `USVOL` skips US market holidays like `US500`, even when the index is calculated in an extended session that day; its intraday bars show every calculated value.

## WebSocket

Stream live quotes and trades for this asset class over the public WebSocket.

**Connect**

```
wss://stream.tickerlayer.com/?apiKey=<YOUR_API_KEY>
```

### Available channels

- `indices.quotes`: quotes
- `indices.trades`: trades

### Subscribe example

After the connection is ready, send a JSON text frame:

```json
{
  "action": "subscribe",
  "channels": [
    "indices.quotes",
    "indices.trades"
  ],
  "symbols": [
    "US500",
    "DE40"
  ]
}
```

### Example messages

**indices.quotes**

```json
{
  "type": "quote",
  "channel": "indices.quotes",
  "asset": "indices",
  "symbol": "US500",
  "bid": 4788.12,
  "ask": 4788.12,
  "bid_size": 62,
  "ask_size": 58,
  "ts": 1743512400000,
  "timestamp": 1743512400000
}
```

**indices.trades**

```json
{
  "type": "trade",
  "channel": "indices.trades",
  "asset": "indices",
  "symbol": "US500",
  "price": 4788.4,
  "size": 12,
  "ts": 1743512400000,
  "timestamp": 1743512400000
}
```

### General WebSocket documentation

For authentication, subscribe/unsubscribe lifecycle, errors, limits, and heartbeats, see the [WebSocket overview](https://tickerlayer.com/docs/websocket), [Subscriptions](https://tickerlayer.com/docs/websocket/subscriptions) and [Message types](https://tickerlayer.com/docs/websocket/messages).
