# Quotes, Movers, and Market Status

> Fetch single or batch quotes, movers, exchange status, settlement calendars, and holidays for African markets.

## Quotes

Use `GET /market/quotes?symbols=SCOM.KE,MTN.ZA` for up to 50 symbols per request. Unresolved symbols appear in `not_found` without failing the whole batch. Use `GET /stocks/{symbol}` for a detailed single-instrument response.

## Data freshness — read this before you price a trade

**African equity quotes are exchange-supplied, 15-minute-delayed data—not real-time prices.**
MyStocks has full market-data rights for every supported exchange. The delay is the latency class of
the exchange feed, not a licensing restriction. MyStocks targets a 15-minute ingestion cadence during
the published coverage window, so `delayMinutes: 15` describes the exchange delay while
`refreshIntervalSeconds: 900` describes the API refresh target. There is no tick-by-tick price feed.
Outside the relevant exchange session, the latest observation is normally the EOD close.

Every quote carries its own freshness, so you never have to guess:

<ParamTable fields={[
  { name: 'asOf',                 type: 'string | null', desc: 'The timestamp of the exchange observation — NOT when the API answered. This is the timestamp you should display and use when evaluating freshness.' },
  { name: 'stale',               type: 'boolean', desc: 'true when the price is older than two refresh intervals (30 min). The feed for that symbol is genuinely behind; do not trust the price for pricing.' },
  { name: 'dataFreshnessSeconds', type: 'number | null', desc: 'Age of the price in seconds — the same thing as now − asOf.' },
  { name: 'dataQuality',          type: 'object', desc: 'The full contract: delayMode (DELAYED | END_OF_DAY), delayMinutes, refreshIntervalSeconds, provider, and a plain-English disclaimer.' },
]} />

```json
{
  "symbol": "SCOM.KE",
  "price": 17.85,
  "asOf": "2026-07-13T11:45:02.000Z",
  "stale": false,
  "dataFreshnessSeconds": 214,
  "dataQuality": {
    "delayMode": "DELAYED",
    "delayMinutes": 15,
    "refreshIntervalSeconds": 900,
    "provider": "mstocks",
    "disclaimer": "Exchange-supplied quote delayed by 15 minutes. API refresh target: 15 minutes. Not real-time tick data. Check `asOf`."
  }
}
```

`GET /market/exchanges` returns the same contract per exchange (`marketData`), plus a top-level
`marketDataPolicy` block stating `realtime: false`, the 15-minute exchange delay, the API refresh
target, and whether the intraday coverage window is currently open.

Because quotes are delayed, a **market order is quote-gated**: you must fetch a single-use `quoteId`
from `GET /quote/{symbol}` and submit it with the order, so the price you were shown is the price the
order is bound to. If you need to control the execution price yourself, place a **LIMIT** order
instead — see [Advanced order types](/partners/docs/advanced-order-types).

## Market state

- `GET /market/status` reports whether an exchange is open and its next open time.
- `GET /market/holidays` provides forward-looking closures.

`changePct` is a decimal return (`0.042` means `4.2%`). When the upstream row does not carry the
field, the API derives it from `price` and `previousClose`; it remains `null` only when that comparison
cannot be made. Sector labels are normalized for display and filtering (for example, Banking and
Financial Services resolve to Financials).
- `GET /market/movers` ranks instruments by movement.
- `GET /market/settlement` describes market settlement cycles and execution targets.

Use market status and holidays before submitting orders. A quote can be valid while an exchange is closed; order acceptance and execution remain subject to market hours, halts, auctions, and dealing rules.

All responses are read-only and data-key safe. See [Rate Limits](/partners/docs/rate-limits) for batch and polling strategy.
