# Time & Sales API

Tick-level trade prints for US equity options, historical and live. Every historical option print carries delta, gamma, implied volatility, and the underlying stock price, joined from the ORATS one-minute greeks snapshots; live option prints instead carry the live underlying quote at trade time. The same tape is shown in the Time and Sales view in [Ticker Analysis](https://orats.com/ticker-analysis) in the ORATS dashboard.

History begins 2022-09-09. The live endpoint serves the current session's tape as it builds during market hours; outside a session it returns a 404 with a message that there is no live tape for the date.

Every option print carries the underlying price at the time of the trade (stockPrice, with the live bid and ask on live prints).

Authenticate with the token query parameter. Do not send an Authorization header: large responses redirect to a presigned S3 URL, and clients that forward headers across redirects will get an S3 error.

Responses are JSON by default. Append .csv to the endpoint path (for example /datav2/hist/time-sales/option.csv) for the same rows as CSV.

Small results return inline. Large ones, including any whole-day chain pull, return a 302 redirect to a presigned S3 URL holding the gzip-compressed result, so follow redirects (the -L flag in cURL) and decompress if your client does not do it for you.

Whole-day files are big: a full day of SPY option prints is around 1.3 million rows and 700 MB of JSON, more than most single processes can hold, so narrow the request with from and to, symbol, expirDate, callPut, or minSize. The first request for a ticker and date builds that file and takes around 15 to 20 seconds; after that the cached copy returns in under a second for everyone. Two redirect tiers exist: results of a few megabytes up to about 25,000 rows redirect to a plain JSON object that keeps the same data wrapper as an inline response, while larger results redirect to a presigned, gzip-compressed file holding a bare JSON array of rows; read the body as either shape.

Requests missing a required attribute, or carrying a malformed one (from and to must be HH:MM with from not later than to, tradeDate and expirDate real calendar dates, callPut C or P, strike, minStrike, maxStrike and minSize numeric with minStrike not above maxStrike, symbol a standard option symbol), return a 400 whose body is a message field describing the problem; requests for the .csv form get the same message as text/csv. A tradeDate outside the loaded history, on a non-trading day, or in the future returns a 404 with a message that there is no time and sales data for that date, and an unknown ticker returns an empty result (an empty CSV still carries the header row). ticker and symbol are case-insensitive and trimmed. Only GET is supported; POST returns a 405. The .csv and .json path extensions are case-insensitive, and an unknown extension or path returns a 404 with a message of No such endpoint. JSON responses are capped at 250,000 rows and return a 400 asking you to narrow the query or request the .csv form, which has no cap. Option days captured live end near 16:15 Eastern, while backfilled option days end at 15:59 (12:59 on half days). Share-class tickers are accepted as BRK_B, BRK.B, or BRK/B; their prints are on the tape from 2026-08-26 onward (earlier days have none).

Each endpoint is rate limited to 10 requests per minute per token. Beyond that, requests return a 429 with a message saying when the minute window resets.

Overview and pricing for this and the other Tools APIs are in the [Tools APIs section](https://orats.com/data-api#tools-apis) of the Data API page.

Base URL: `https://api.orats.io/datav2`

---

## Option Time & Sales

`GET https://api.orats.io/datav2/hist/time-sales/option`

Retrieves option trade prints for a trade date: a whole underlying's chain, one expiration or strike, or a single contract, optionally windowed by time of day and filtered by print size.

Each row is one print: the trade price, size, exchange code, and sale conditions, the NBBO bid and ask at the moment of the trade, the inferred aggressorSide (BUY, SELL, or blank when no side could be inferred), and flags for spread legs (spreadLeg), extended-hours prints, and tick validity. The contract is parsed onto the row as root, ticker, expirDate, strike, and callPut. The enrichment fields stockPrice, delta, gamma, and iv are joined from the ORATS one-minute greeks snapshot named by greeksSnapTime, so stockPrice is the snapshot's underlying price for that minute rather than the quote at the instant of the trade, and iv is a decimal. smvValue is the ORATS SMV theoretical value of the contract from that same snapshot, shifted by delta for the underlying's move from the snapshot price to the trade-time stock price, so price minus smvValue (signed by aggressorSide) is how far the fill was from theoretical value; it is null on days whose history predates the field. The intraday SMV fit is not reliable in the opening snapshots (the warm-up period): on the same-day expiry, smvValue, delta, gamma, and iv are null for rows whose greeksSnapTime is 0930 through 0932, and values resume at 0933; the fields may be populated for that window in the future if the opening fit is improved. eventTime is the trade timestamp in epoch milliseconds, eventEstTime the same moment in Eastern time, and eventIndex with eventSequence order prints within a contract: eventIndex is unique per contract rather than per chain, eventSequence steps by two, and a CANCEL row (validTick false) shares both with the NEW print it cancels, so key on symbol, eventIndex, and type together and keep type NEW when summing volume.

### Required attributes

- `tradeDate` (string): The trade date to retrieve. History begins 2022-09-09. Ex: 2026-07-15
- `ticker` (string): The underlying symbol to retrieve; prints for every contract on the underlying are included. Either ticker or symbol is required; symbol takes precedence when both are sent. Ex: SPY
- `symbol` (string): A single contract to retrieve instead of a whole chain, as an OCC option symbol. Either ticker or symbol is required. Ex: SPY260717C00630000

### Optional attributes

- `expirDate` (string): Filter to a single expiration. Ex: 2026-07-17
- `callPut` (string): Filter to calls (C) or puts (P). Ex: P
- `strike` (number): Filter to a single strike. Ex: 630
- `from` (string): Start of an Eastern-time window, inclusive. Defaults to the start of the day. Ex: 09:30
- `to` (string): End of an Eastern-time window, inclusive. Defaults to the end of the day. Ex: 10:00
- `minSize` (integer): Only prints of at least this many contracts. Ex: 100

**cURL**

```bash
curl -L "https://api.orats.io/datav2/hist/time-sales/option?token=my-token&tradeDate=2026-07-15&ticker=SPY&from=09:30&to=10:00&minSize=100"
```

**Response**

```json
{
  "data": [
    {
      "symbol": "SPY260814C00760000",
      "root": "SPY",
      "ticker": "SPY",
      "expirDate": "2026-08-14",
      "strike": 760,
      "callPut": "C",
      "tradeDate": "2026-07-15",
      "eventIndex": "7662746501080154113",
      "eventTime": 1784122200003,
      "eventEstTime": "2026-07-15 09:30:00",
      "eventSequence": 1,
      "exchangeCode": "X",
      "price": 9.41,
      "size": 252,
      "bidPrice": 8.63,
      "askPrice": 8.67,
      "exchangeSaleConditions": "I",
      "aggressorSide": "BUY",
      "spreadLeg": false,
      "extendedTradingHours": false,
      "validTick": true,
      "type": "NEW",
      "stockPrice": 754.24,
      "delta": 0.4586,
      "gamma": 0.01539,
      "iv": 0.129,
      "smvValue": 8.6512,
      "greeksSnapTime": "0930"
    },
    {
      "symbol": "SPY260717C00756000",
      "root": "SPY",
      "ticker": "SPY",
      "expirDate": "2026-07-17",
      "strike": 756,
      "callPut": "C",
      "tradeDate": "2026-07-15",
      "eventIndex": "7662746506851516421",
      "eventTime": 1784122201355,
      "eventEstTime": "2026-07-15 09:30:01",
      "eventSequence": 5,
      "exchangeCode": "X",
      "price": 2.1,
      "size": 100,
      "bidPrice": 2.12,
      "askPrice": 2.1,
      "exchangeSaleConditions": "I",
      "aggressorSide": "SELL",
      "spreadLeg": false,
      "extendedTradingHours": false,
      "validTick": true,
      "type": "NEW",
      "stockPrice": 754.24,
      "delta": 0.414,
      "gamma": 0.05628,
      "iv": 0.133,
      "smvValue": 2.1088,
      "greeksSnapTime": "0930"
    }
  ]
}
```

---

## Live Option Time & Sales

`GET https://api.orats.io/datav2/live/time-sales/option`

Retrieves option trade prints from the current session's tape, from the open through the moment of the request. The tape is today's by default; a tradeDate attribute is accepted and serves one of the last few completed sessions (the same prints the historical endpoint returns once its evening build completes, in the live row shape). The tape refreshes in 30-second buckets and lags real time by 10 to 40 seconds. A date outside that window, or today before the open, returns a 404 with the message that there is no live tape for the date (use the historical endpoint for older sessions); a ticker that has no prints on a day that has a tape returns an empty data array. On a day with no tape every call answers the 404 within a second.

Rows share the historical Option Time & Sales base shape and the same filters apply, but the enrichment differs: live prints do not carry the delta, gamma, iv, or greeksSnapTime fields. In their place each print holds the live underlying quote at trade time: stockPrice, stockBid, stockAsk, stockBidSize, stockAskSize, and stockQuoteTime.

### Required attributes

- `ticker` (string): The underlying symbol to retrieve; prints for every contract on the underlying are included. Either ticker or symbol is required; symbol takes precedence when both are sent. Ex: SPY
- `symbol` (string): A single contract to retrieve instead of a whole chain, as an OCC option symbol. Either ticker or symbol is required. Ex: SPY260717C00630000

### Optional attributes

- `expirDate` (string): Filter to a single expiration. Ex: 2026-07-17
- `callPut` (string): Filter to calls (C) or puts (P). Ex: P
- `strike` (number): Filter to a single strike. Ex: 630
- `from` (string): Start of an Eastern-time window, inclusive. Defaults to the start of the session. Ex: 12:30
- `to` (string): End of an Eastern-time window, inclusive. Defaults to the moment of the request. Ex: 13:00
- `minSize` (integer): Only prints of at least this many contracts. Ex: 100

**cURL**

```bash
curl -L "https://api.orats.io/datav2/live/time-sales/option?token=my-token&ticker=SPY&from=12:30&minSize=100"
```

**Response**

```json
{
  "data": [
    {
      "symbol": "SPY260716P00741000",
      "root": "SPY",
      "ticker": "SPY",
      "expirDate": "2026-07-16",
      "strike": 741,
      "callPut": "P",
      "tradeDate": "2026-07-15",
      "eventIndex": "7662792893928571457",
      "eventTime": 1784133001696,
      "eventEstTime": "2026-07-15 12:30:01",
      "eventSequence": 577,
      "exchangeCode": "N",
      "price": 0.23,
      "size": 164,
      "bidPrice": 0.23,
      "askPrice": 0.24,
      "exchangeSaleConditions": "I",
      "aggressorSide": "SELL",
      "spreadLeg": false,
      "extendedTradingHours": false,
      "validTick": true,
      "type": "NEW",
      "stockPrice": 750.87,
      "stockBid": 750.86,
      "stockAsk": 750.88,
      "stockBidSize": 200,
      "stockAskSize": 300,
      "stockQuoteTime": "2026-07-15 12:30:01"
    }
  ]
}
```
