• C#
  • Java
  • VB
  • C++
  • Python
Contact us
Historical Data

To receive historical data from the API a user must have level 1 market data subscriptions for that contract. The API historical data functionality simply pulls certain types of data from TWS charts, so if data is not available in a TWS chart it will also not be available from the API. TWS charts can be created for many types of instruments without market data subscriptions, but API historical data always requires that the Live Market Data are met.

-For European stocks, a smart-routed historical data requests requires subscriptions to all available exchanges.

-Beginning with API v973.03 and TWS v965, the option to subscribe to historical data is available so that data is continually returned in real time as new bars are available. This is indicated by specifying keepUpToDate = True.

-When retrieving historical data from the TWS, be aware of the Historical Data Limitations.

Requesting Historical Data

Historical data is obtained from the the TWS via the IBApi.EClient.reqHistoricalData function. Every request needs:

  • tickerId, A unique identifier which will serve to identify the incoming data.
  • contract, The IBApi.Contract you are interested in.
  • endDateTime, The request's end date and time (empty string can be used to indicate current time).
  • durationString, The amount of time (or Valid Duration String units) to go back from the request's given end date and time.
  • barSizeSetting, The data's granularity or Valid Bar Sizes
  • whatToShow, The type of data to retrieve. See Historical Data Types
  • useRTH, Whether (1) or not (0) to retrieve data generated only within Regular Trading Hours (RTH)
  • formatDate, The format in which the incoming bars' date should be presented. Note that for day bars, only yyyyMMdd format is available.
  • keepUpToDate, Whether a subscription is made to return real time bars as they are available (True), or all data is returned on a one-time basis (False). Available starting with API v973.03+ and TWS v965+.

For example, making a request with an end date and time of "20160127 23:59:59", a duration string of "3 D" and a bar size of "1 hour" will return three days worth of 1 hour bars data in which the most recent bar will be the closest possible to 20160127 23:59:59.

  • String queryTime = DateTime.Now.AddMonths(-6).ToString("yyyyMMdd HH:mm:ss");
    client.reqHistoricalData(4001, ContractSamples.EurGbpFx(), queryTime, "1 M", "1 day", "MIDPOINT", 1, 1, false, null);
    client.reqHistoricalData(4002, ContractSamples.EuropeanStock(), queryTime, "10 D", "1 min", "TRADES", 1, 1, false, null);
  • Calendar cal = Calendar.getInstance();
    cal.add(Calendar.MONTH, -6);
    SimpleDateFormat form = new SimpleDateFormat("yyyyMMdd HH:mm:ss");
    String formatted = form.format(cal.getTime());
    client.reqHistoricalData(4001, ContractSamples.EurGbpFx(), formatted, "1 M", "1 day", "MIDPOINT", 1, 1, false, null);
    client.reqHistoricalData(4002, ContractSamples.EuropeanStock(), formatted, "10 D", "1 min", "TRADES", 1, 1, false, null);
    Thread.sleep(2000);
    /*** Canceling historical data requests ***/
    client.cancelHistoricalData(4001);
    client.cancelHistoricalData(4002);
  • Dim queryTime As String = DateTime.Now.AddMonths(-6).ToString("yyyyMMdd HH:mm:ss")
    client.reqHistoricalData(4001, ContractSamples.EurGbpFx(), queryTime, "1 M", "1 day", "MIDPOINT", 1, 1, False, Nothing)
    client.reqHistoricalData(4002, ContractSamples.EuropeanStock(), queryTime, "10 D", "1 min", "TRADES", 1, 1, False, Nothing)
  • std::time_t rawtime;
    std::tm* timeinfo;
    char queryTime [80];
    std::time(&rawtime);
    timeinfo = std::localtime(&rawtime);
    std::strftime(queryTime, 80, "%Y%m%d %H:%M:%S", timeinfo);
    m_pClient->reqHistoricalData(4001, ContractSamples::EurGbpFx(), queryTime, "1 M", "1 day", "MIDPOINT", 1, 1, false, TagValueListSPtr());
    m_pClient->reqHistoricalData(4002, ContractSamples::EuropeanStock(), queryTime, "10 D", "1 min", "TRADES", 1, 1, false, TagValueListSPtr());
  • 1  queryTime = (datetime.datetime.today() -
    2  datetime.timedelta(days=180)).strftime("%Y%m%d %H:%M:%S")
    3  # String queryTime = DateTime.Now.AddMonths(-6).ToString("yyyyMMdd HH:mm:ss")
    4  self.reqHistoricalData(4101, ContractSamples.USStockAtSmart(), queryTime,
    5  "1 M", "1 day", "MIDPOINT", 1, 1, [])
    6  self.reqHistoricalData(4001, ContractSamples.EurGbpFx(), queryTime,
    7  "1 M", "1 day", "MIDPOINT", 1, 1, [])
    8  self.reqHistoricalData(4002, ContractSamples.EuropeanStock(), queryTime,
    9  "10 D", "1 min", "TRADES", 1, 1, [])

Earliest Available Data

To find the earliest available data point for a given instrument and data type a function is in the API starting in v973.02 and v963 of TWS/IBG, IBApi::EClient::reqHeadTimestamp

  • client.reqHeadTimestamp(14001, ContractSamples.USStock(), "TRADES", 1, 1);
  • client.reqHeadTimestamp(4003, ContractSamples.USStock(), "TRADES", 1, 1);
  • client.reqHeadTimestamp(14001, ContractSamples.USStock(), "TRADES", 1, 1)
  • m_pClient->reqHeadTimestamp(14001, ContractSamples::EurGbpFx(), "MIDPOINT", 1, 1);
  • 1  self.reqHeadTimeStamp(4103, ContractSamples.USStockAtSmart(), "TRADES", 0, 1)

The resulting head timestamp is returned to the function IBApi.EWrapper.headTimestamp

  • public class EWrapperImpl : EWrapper
    {
    ...
    public void headTimestamp(int reqId, string headTimestamp)
    {
    Console.WriteLine("Head time stamp. Request Id: {0}, Head time stamp: {1}", reqId, headTimestamp);
    }
  • public class EWrapperImpl implements EWrapper {
    ...
    @Override
    public void headTimestamp(int reqId, String headTimestamp) {
    System.out.println("Head timestamp. Req Id: " + reqId + ", headTimestamp: " + headTimestamp);
    }
  • Public Class EWrapperImpl
    Implements EWrapper
    ...
    Public Sub headTimestamp(requestId As Integer, timeStamp As String) Implements IBApi.EWrapper.headTimestamp
    Console.WriteLine("Head time stamp. Request Id: {0}, Head time stamp: {1}", requestId, timeStamp)
    End Sub
  • class TestCppClient : public EWrapper
    {
    ...
    void TestCppClient::headTimestamp(int reqId, const std::string& headTimestamp) {
    printf( "Head time stamp. ReqId: %d - Head time stamp: %s,\n", reqId, headTimestamp.c_str());
    }
  • 1 class TestWrapper(wrapper.EWrapper):
    ...
    1  def headTimestamp(self, reqId:int, headTimestamp:str):
    2  print("HeadTimestamp: ", reqId, " ", headTimestamp)

A reqHeadTimeStamp request can be cancelled with IBApi::EClient::cancelHeadTimestamp

  • client.cancelHeadTimestamp(14001);
  • client.cancelHeadTimestamp(4003);
  • client.cancelHeadTimestamp(14001)
  • m_pClient->cancelHeadTimestamp(14001);
  • 1  self.cancelHeadTimeStamp(4103)

Receiving Historical Data

The historical data will be delivered via the IBApi::EWrapper::historicalData method in the form of candlesticks. If reqHistoricalData was invoked with keepUpToDate = false, once all candlesticks have been received the IBApi.EWrapper.historicalDataEnd marker will be sent. Otherwise bars will continue to be returned in real time to IBApi::EWrapper::historicalDataUpdate. The keepUpToDate functionality can only be used with bar sizes 5 seconds or greater and requires the endDate is set as the empty string.

  • public class EWrapperImpl : EWrapper
    {
    ...
    public virtual void historicalData(int reqId, Bar bar)
    {
    Console.WriteLine("HistoricalData. " + reqId + " - Time: " + bar.Time + ", Open: " + bar.Open + ", High: " + bar.High + ", Low: " + bar.Low + ", Close: " + bar.Close + ", Volume: " + bar.Volume + ", Count: " + bar.Count + ", WAP: " + bar.WAP);
    }
    ...
    public virtual void historicalDataEnd(int reqId, string startDate, string endDate)
    {
    Console.WriteLine("HistoricalDataEnd - "+reqId+" from "+startDate+" to "+endDate);
    }
  • public class EWrapperImpl implements EWrapper {
    ...
    @Override
    public void historicalData(int reqId, Bar bar) {
    System.out.println("HistoricalData. "+reqId+" - Date: "+bar.time()+", Open: "+bar.open()+", High: "+bar.high()+", Low: "+bar.low()+", Close: "+bar.close()+", Volume: "+bar.volume()+", Count: "+bar.count()+", WAP: "+bar.wap());
    }
    ...
    @Override
    public void historicalDataEnd(int reqId, String startDateStr, String endDateStr) {
    System.out.println("HistoricalDataEnd. "+reqId+" - Start Date: "+startDateStr+", End Date: "+endDateStr);
    }
  • Public Class EWrapperImpl
    Implements EWrapper
    ...
    Public Sub historicalData(reqId As Integer, bar As Bar) Implements IBApi.EWrapper.historicalData, IBApi.EWrapper.historicalDataUpdate
    Console.WriteLine("HistoricalData - ReqId [" & reqId & "] Date [" & bar.Time & "] Open [" & bar.Open & "] High [" &
    bar.High & "] Low [" & bar.Low & "] Volume [" & bar.Volume & "] Count [" & bar.Count & "]")
    End Sub
    ...
    Public Sub historicalDataEnd(reqId As Integer, start As String, [end] As String) Implements IBApi.EWrapper.historicalDataEnd
    Console.WriteLine("HistoricalDataEnd - ReqId [" & reqId & "] Start [" & start & "] End [" & [end] & "]")
    End Sub
  • class TestCppClient : public EWrapper
    {
    ...
    void TestCppClient::historicalData(TickerId reqId, Bar bar) {
    printf( "HistoricalData. ReqId: %ld - Date: %s, Open: %g, High: %g, Low: %g, Close: %g, Volume: %d, Count: %d, WAP: %g\n", reqId, bar.time.c_str(), bar.open, bar.high, bar.low, bar.close, bar.volume, bar.count, bar.wap);
    }
    ...
    void TestCppClient::historicalDataEnd(int reqId, std::string startDateStr, std::string endDateStr) {
    std::cout << "HistoricalDataEnd. ReqId: " << reqId << " - Start Date: " << startDateStr << ", End Date: " << endDateStr << std::endl;
    }
  • 1 class TestWrapper(wrapper.EWrapper):
    ...
    1  def historicalData(self, reqId: TickerId, date: str, open: float, high: float,
    2  low: float, close: float, volume: int, barCount: int,
    3  WAP: float, hasGaps: int):
    4  super().historicalData(reqId, date, open, high, low, close, volume,
    5  barCount, WAP, hasGaps)
    6  print("HistoricalData. ", reqId, " Date:", date, "Open:", open,
    7  "High:", high, "Low:", low, "Close:", close, "Volume:", volume,
    8  "Count:", barCount, "WAP:", WAP, "HasGaps:", hasGaps)
    ...
    1  def historicalDataEnd(self, reqId: int, start: str, end: str):
    2  super().historicalDataEnd(reqId, start, end)
    3  print("HistoricalDataEnd ", reqId, "from", start, "to", end)
    4 


  • public void historicalDataUpdate(int reqId, Bar bar)
    {
    Console.WriteLine("HistoricalDataUpdate. " + reqId + " - Time: " + bar.Time + ", Open: " + bar.Open + ", High: " + bar.High + ", Low: " + bar.Low + ", Close: " + bar.Close + ", Volume: " + bar.Volume + ", Count: " + bar.Count + ", WAP: " + bar.WAP);
    }
  • @Override
    public void historicalDataUpdate(int reqId, Bar bar) {
    System.out.println("HistoricalDataUpdate. "+reqId+" - Date: "+bar.time()+", Open: "+bar.open()+", High: "+bar.high()+", Low: "+bar.low()+", Close: "+bar.close()+", Volume: "+bar.volume()+", Count: "+bar.count()+", WAP: "+bar.wap());
    }
  • void TestCppClient::historicalDataUpdate(TickerId reqId, Bar bar) {
    printf( "HistoricalDataUpdate. ReqId: %ld - Date: %s, Open: %g, High: %g, Low: %g, Close: %g, Volume: %d, Count: %d, WAP: %g\n", reqId, bar.time.c_str(), bar.open, bar.high, bar.low, bar.close, bar.volume, bar.count, bar.wap);
    }

Valid Duration String units

UnitDescription
SSeconds
DDay
WWeek
MMonth
YYear

Valid Bar Sizes

Size
1 secs 5 secs 10 secs 15 secs 30 secs
1 min 2 mins 3 mins 5 mins 10 mins 15 mins 20 mins 30 mins
1 hour 2 hours 3 hours 4 hours 8 hours
1 day
1 week
1 month

Historical Data Types

(whatToShow)

All different kinds of historical data are returned in the form of candlesticks and as such the values return represent the state of the market during the period covered by the candlestick. For instance, it might appear obvious but a TRADES day bar's 'close' value does NOT represent the product's closing price but rather the last traded price registered.

TypeOpenHighLowCloseVolume
TRADESFirst traded priceHighest traded priceLowest traded priceLast traded priceTotal traded volume
MIDPOINTStarting midpoint priceHighest midpoint priceLowest midpoint priceLast midpoint priceN/A
BIDStarting bid priceHighest bid priceLowest bid priceLast bid priceN/A
ASKStarting ask priceHighest ask priceLowest ask priceLast ask priceN/A
BID_ASKTime average bidMax AskMin BidTime average askN/A
HISTORICAL_VOLATILITYStarting volatilityHighest volatilityLowest volatilityLast volatilityN/A
OPTION_IMPLIED_VOLATILITYStarting implied volatilityHighest implied volatilityLowest implied volatilityLast implied volatilityN/A
REBATE_RATEStarting rebate rateHighest rebate rateLowest rebate rateLast rebate rateN/A
FEE_RATEStarting fee rateHighest fee rateLowest fee rateLast fee rateN/A
YIELD_BIDStarting bid yieldHighest bid yieldLowest bid yieldLast bid yield N/A
YIELD_ASKStarting ask yieldHighest ask yieldLowest ask yieldLast ask yieldN/A
YIELD_BID_ASKTime average bid yieldHighest ask yieldLowest bid yieldTime average ask yieldN/A
YIELD_LASTStarting last yieldHighest last yieldLowest last yieldLast last yield

N/A


Available Data per Product

Product Type
TRADES
MIDPOINT
BID
ASK
BID_ASK
HISTORICAL_VOLATILITY
OPTION_IMPLIED_VOLATILITY
YIELD_BID
YIELD_ASK
YIELD_BID_ASK
YIELD_LAST
Stocks
Y
Y
Y
Y
Y
Y
Y
N
N
N
N
Commodities
N
Y
Y
Y
Y
N
N
N
N
N
N
Options
Y
Y
Y
Y
Y
N
N
N
N
N
N
Futures
Y
Y
Y
Y
Y
N
N
N
N
N
N
FOPs
Y
Y
Y
Y
Y
N
N
N
N
N
N
ETFs
Y
Y
Y
Y
Y
Y
Y
N
N
N
N
Warrants
Y
Y
Y
Y
Y
N
N
N
N
N
N
Structured Products
Y
Y
Y
Y
Y
N
N
N
N
N
N
SSFs
Y
Y
Y
Y
Y
N
N
N
N
N
N
Forex
N
Y
Y
Y
Y
N
N
N
N
N
N
Metals
Y
Y
Y
Y
Y
N
N
N
N
N
N
Indices
Y
N
N
N
N
Y
Y
N
N
N
N
Bonds*
Y
Y
Y
Y
Y
N
N
Y
Y
Y
Y
Funds
N
Y
Y
Y
Y
N
N
N
N
N
N
CFDs*
N
Y
Y
Y
Y
N
N
N
N
N
N

-Yield historical data only available for corporate bonds

Requesting Histograms

Histograms