Can't get historical data with IB API C++

Discussion in 'Interactive Brokers' started by Sivon, Dec 14, 2020.

  1. Sivon

    Sivon

    Hi, there is no errors and evetyrhing is working well but after calling

    C->reqHistoricalData(100, contract, "", "1 D", "1 hour", "MIDPOINT", 1, 1, false, TagValueListSPtr());

    there is no return.

    Here is the whole code:

    Code:
    #include "stdafx.h"
    
    #include <Contract.h>
    #include <Order.h>
    #include <OrderState.h>
    #include <Execution.h>
    #include <CommissionReport.h>
    #include <ScannerSubscription.h>
    #include <executioncondition.h>
    #include <PriceCondition.h>
    #include <MarginCondition.h>
    #include <PercentChangeCondition.h>
    #include <TimeCondition.h>
    #include <VolumeCondition.h>
    #include <CommonDefs.h>
    #include <EWrapper.h>
    #include <EReaderOSSignal.h>
    #include <EReader.h>
    #include <EClientSocket.h>
    #include <EClient.h>
    
    #include <stdio.h>
    #include <chrono>
    #include <iostream>
    #include <thread>
    #include <ctime>
    #include <fstream>
    #include <cstdint>
    
    using namespace std;
    
    class MyEwrapper : public EWrapper
    {
    public:
        void tickPrice(TickerId tickerId, TickType field, double price, const TickAttrib& attrib) {}
        void tickSize(TickerId tickerId, TickType field, int size) {}
        void tickOptionComputation(TickerId tickerId, TickType tickType, int tickAttrib, double impliedVol, double delta,
            double optPrice, double pvDividend, double gamma, double vega, double theta, double undPrice) {}
        void tickGeneric(TickerId tickerId, TickType tickType, double value) {}
        void tickString(TickerId tickerId, TickType tickType, const std::string& value) {}
        void tickEFP(TickerId tickerId, TickType tickType, double basisPoints, const std::string& formattedBasisPoints,
            double totalDividends, int holdDays, const std::string& futureLastTradeDate, double dividendImpact, double dividendsToLastTradeDate) {}
        void orderStatus(OrderId orderId, const std::string& status, double filled,
            double remaining, double avgFillPrice, int permId, int parentId,
            double lastFillPrice, int clientId, const std::string& whyHeld, double mktCapPrice) {}
        void openOrder(OrderId orderId, const Contract&, const Order&, const OrderState&) {}
        void openOrderEnd() {}
        void winError(const std::string& str, int lastError) {}
        void connectionClosed() {}
        void updateAccountValue(const std::string& key, const std::string& val,
            const std::string& currency, const std::string& accountName) {}
        void updatePortfolio(const Contract& contract, double position,
            double marketPrice, double marketValue, double averageCost,
            double unrealizedPNL, double realizedPNL, const std::string& accountName) {}
        void updateAccountTime(const std::string& timeStamp) {}
        void accountDownloadEnd(const std::string& accountName) {}
        void nextValidId(OrderId orderId) {}
        void contractDetails(int reqId, const ContractDetails& contractDetails) {}
        void bondContractDetails(int reqId, const ContractDetails& contractDetails) {}
        void contractDetailsEnd(int reqId) {}
        void execDetails(int reqId, const Contract& contract, const Execution& execution) {}
        void execDetailsEnd(int reqId) {}
        void error(int id, int errorCode, const std::string& errorString) {}
        void updateMktDepth(TickerId id, int position, int operation, int side,
            double price, int size) {}
        void updateMktDepthL2(TickerId id, int position, const std::string& marketMaker, int operation,
            int side, double price, int size, bool isSmartDepth) {}
        void updateNewsBulletin(int msgId, int msgType, const std::string& newsMessage, const std::string& originExch) {}
        void managedAccounts(const std::string& accountsList) {}
        void receiveFA(faDataType pFaDataType, const std::string& cxml) {}
        void historicalData(TickerId reqId, const Bar& bar);
        void historicalDataEnd(int reqId, const std::string& startDateStr, const std::string& endDateStr) {}
        void scannerParameters(const std::string& xml) {}
        void scannerData(int reqId, int rank, const ContractDetails& contractDetails,
            const std::string& distance, const std::string& benchmark, const std::string& projection,
            const std::string& legsStr) {}
        void scannerDataEnd(int reqId) {}
        void realtimeBar(TickerId reqId, long time, double open, double high, double low, double close,
            long volume, double wap, int count) {}
        void currentTime(long time) {}
        void fundamentalData(TickerId reqId, const std::string& data) {}
        void deltaNeutralValidation(int reqId, const DeltaNeutralContract& deltaNeutralContract) {}
        void tickSnapshotEnd(int reqId) {}
        void marketDataType(TickerId reqId, int marketDataType) {}
        void commissionReport(const CommissionReport& commissionReport) {}
        void position(const std::string& account, const Contract& contract, double position, double avgCost) {}
        void positionEnd() {}
        void accountSummary(int reqId, const std::string& account, const std::string& tag, const std::string& value, const std::string& curency) {}
        void accountSummaryEnd(int reqId) {}
        void verifyMessageAPI(const std::string& apiData) {}
        void verifyCompleted(bool isSuccessful, const std::string& errorText) {}
        void displayGroupList(int reqId, const std::string& groups) {}
        void displayGroupUpdated(int reqId, const std::string& contractInfo) {}
        void verifyAndAuthMessageAPI(const std::string& apiData, const std::string& xyzChallange) {}
        void verifyAndAuthCompleted(bool isSuccessful, const std::string& errorText) {}
        void connectAck() {}
        void positionMulti(int reqId, const std::string& account, const std::string& modelCode, const Contract& contract, double pos, double avgCost) {}
        void positionMultiEnd(int reqId) {}
        void accountUpdateMulti(int reqId, const std::string& account, const std::string& modelCode, const std::string& key, const std::string& value, const std::string& currency) {}
        void accountUpdateMultiEnd(int reqId) {}
        void securityDefinitionOptionalParameter(int reqId, const std::string& exchange, int underlyingConId, const std::string& tradingClass,
            const std::string& multiplier, const std::set<std::string>& expirations, const std::set<double>& strikes) {}
        void securityDefinitionOptionalParameterEnd(int reqId) {}
        void softDollarTiers(int reqId, const std::vector<SoftDollarTier> &tiers) {}
        void familyCodes(const std::vector<FamilyCode> &familyCodes) {}
        void symbolSamples(int reqId, const std::vector<ContractDescription> &contractDescriptions) {}
        void mktDepthExchanges(const std::vector<DepthMktDataDescription> &depthMktDataDescriptions) {}
        void tickNews(int tickerId, time_t timeStamp, const std::string& providerCode, const std::string& articleId, const std::string& headline, const std::string& extraData) {}
        void smartComponents(int reqId, const SmartComponentsMap& theMap) {}
        void tickReqParams(int tickerId, double minTick, const std::string& bboExchange, int snapshotPermissions) {}
        void newsProviders(const std::vector<NewsProvider> &newsProviders) {}
        void newsArticle(int requestId, int articleType, const std::string& articleText) {}
        void historicalNews(int requestId, const std::string& time, const std::string& providerCode, const std::string& articleId, const std::string& headline) {}
        void historicalNewsEnd(int requestId, bool hasMore) {}
        void headTimestamp(int reqId, const std::string& headTimestamp) {}
        void histogramData(int reqId, const HistogramDataVector& data) {}
        void historicalDataUpdate(TickerId reqId, const Bar& bar) {}
        void rerouteMktDataReq(int reqId, int conid, const std::string& exchange) {}
        void rerouteMktDepthReq(int reqId, int conid, const std::string& exchange) {}
        void marketRule(int marketRuleId, const std::vector<PriceIncrement> &priceIncrements) {}
        void pnl(int reqId, double dailyPnL, double unrealizedPnL, double realizedPnL) {}
        void pnlSingle(int reqId, int pos, double dailyPnL, double unrealizedPnL, double realizedPnL, double value) {}
        void historicalTicks(int reqId, const std::vector<HistoricalTick> &ticks, bool done) {}
        void historicalTicksBidAsk(int reqId, const std::vector<HistoricalTickBidAsk> &ticks, bool done) {}
        void historicalTicksLast(int reqId, const std::vector<HistoricalTickLast> &ticks, bool done) {}
        void tickByTickAllLast(int reqId, int tickType, time_t time, double price, int size, const TickAttribLast& tickAttribLast, const std::string& exchange, const std::string& specialConditions) {}
        void tickByTickBidAsk(int reqId, time_t time, double bidPrice, double askPrice, int bidSize, int askSize, const TickAttribBidAsk& tickAttribBidAsk) {}
        void tickByTickMidPoint(int reqId, time_t time, double midPoint) {}
        void orderBound(long long orderId, int apiClientId, int apiOrderId) {}
        void completedOrder(const Contract& contract, const Order& order, const OrderState& orderState) {}
        void completedOrdersEnd() {}
        void replaceFAEnd(int reqId, const std::string& text) {}
    };
    
    void MyEwrapper::historicalData(TickerId reqId, const Bar& bar)
    {
        cout << "Open: " << bar.open << " Close: " << bar.close << endl;
    }
    
    int main()
    {
        MyEwrapper MV;
        EReaderOSSignal Esignal(2000);
        EClientSocket* EC = new EClientSocket(&MV, &Esignal);
    
        if (EC->eConnect("127.0.0.1", 7497, 271726))
        {
            cout << "Connected" << endl;
            this_thread::sleep_for(chrono::seconds(3));
            //unique_ptr<EReader>m_pReader = unique_ptr<EReader>(new EReader(EC, &Esignal));
            //m_pReader->start();
            //EC->startApi();
        }
        else
            cout << "Not Connected" << endl;
    
        Contract contract;
        contract.symbol = "EUR";
        contract.secType = "CASH";
        contract.currency = "USD";
        contract.exchange = "IDEALPRO";
    
        //time_t rawtime;
        //tm* timeinfo;
        //char queryTime[80];
    
        //time(&rawtime);
        //timeinfo = localtime(&rawtime);
        //strftime(queryTime, 80, "%Y%m%d %H:%M:%S", timeinfo);
     
        this_thread::sleep_for(chrono::seconds(3));
        EC->reqHistoricalData(100, contract, "", "1 D", "1 hour", "MIDPOINT", 1, 1, false, TagValueListSPtr());
     
        system("pause");
        return 0;
    }
     
    Last edited by a moderator: Dec 14, 2020
  2. DaveV

    DaveV

    Immediately after the Connect, you need to call StartReaderThread.
     
    Sivon and stochastix like this.
  3. ET180

    ET180

    Here's what I'm using (it's Java, but should be close to the C++ implementation). I copied most of it from somewhere else.

    Code:
        public IBDataPuller() {
            this.df = new SimpleDateFormat("yyyyMMdd");
            tasks = new ConcurrentHashMap<Integer, IBTask>();
            EReaderSignal readerSignal = new EJavaSignal();
            socket = new EClientSocket(this, readerSignal);
            nextcounter = new AtomicInteger(0);
            try {
                socket.eConnect(new Socket("", 4001), clientid.getAndIncrement());
                while(!socket.isConnected()) {
                    Thread.sleep(100);
                }
                System.out.println("Is connected");
                socket.startAPI();
                final EReader reader = new EReader(socket, readerSignal);     
                reader.start();
                //An additional thread is created in this program design to empty the messaging queue
                new Thread(() -> {
                    while (socket.isConnected()) {
                        readerSignal.waitForSignal();
                        try {
                            reader.processMsgs();
                        } catch (Exception e) {
                            System.out.println("Exception: "+e.getMessage());
                        }
                    }
                }).start();
                socket.reqMarketDataType(2);
            } catch (IOException e) {
                socket.eDisconnect();
                e.printStackTrace();
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
     
    Last edited by a moderator: Dec 14, 2020
    Sivon likes this.
  4. ET180

    ET180

    Same as above, but easier to read.
    upload_2020-12-14_14-47-59.png
     
    Sivon likes this.
  5. IB's servers return the requested data through historicalData(). You need to to write the contents of this and specify what to do with the data (e.g. print to screen, or store to file). Your code shows that you are doing nothing with that incoming data.
     
  6. Sivon

    Sivon

    Thank yoy very much!
    It's working!
    Interesting fact:
    I never used Python but figured out how to connect to TWS and get hisyorical data in less than an hour (thanks to IBpy library) and spend almost 3 days to do the same in c++ . :)
     
  7. Sivon

    Sivon

    void MyEwrapper::historicalData(TickerId reqId, const Bar& bar)
    {
    cout << "Open: " << bar.open << " Close: " << bar.close << endl;
    }

    You might missed that.
    Problem was that I didn't recieve any data but it's working now.
    Thank you.
     
  8. ET180

    ET180

    Most universities teach Python as the intro to programming language. C++ is more complicated and more difficult to debug. I only use C++ if I can't use Java.
     
    stochastix likes this.
  9. Ooops, you are correct: I overlooked those lines of code.
    Good to see that you have got it working by now.