示例#1
0
        public void Connect()
        {
            if (!IsConnected)
            {
                try
                {
                    Client.ClientSocket.eConnect(Hostname, Port, ClientId);
                    Reader = new IB.EReader(Client.ClientSocket, Signal);
                    Reader.Start();

                    new Thread(() =>
                    {
                        while (Client.ClientSocket.IsConnected())
                        {
                            Signal.waitForSignal();
                            Reader.processMsgs();
                        }
                    })
                    {
                        IsBackground = true
                    }.Start();

                    IsConnected = Client.ClientSocket.IsConnected();
                }
                catch (Exception e)
                {
                    string errorMsg = "Please check your connection attributes";
                    ErrorHandler(-1, -1, errorMsg, e);
                }
            }
        }
示例#2
0
        /**
         * @brief Creates socket connection to TWS/IBG.
         */
        public void eConnect(string host, int port, int clientId, bool extraAuth)
        {
            if (isConnected)
            {
                wrapper.error(IncomingMessage.NotValid, EClientErrors.AlreadyConnected.Code, EClientErrors.AlreadyConnected.Message);
                return;
            }
            try
            {
                tcpStream       = createClientStream(host, port);
                this.port       = port;
                socketTransport = new ESocket(tcpStream);

                this.clientId  = clientId;
                this.extraAuth = extraAuth;

                sendConnectRequest();

                if (!AsyncEConnect)
                {
                    var eReader = new EReader(this, eReaderSignal);

                    while (serverVersion == 0 && eReader.putMessageToQueue())
                    {
                        eReaderSignal.waitForSignal();
                        eReader.processMsgs();
                    }
                }
            }
            catch (ArgumentNullException ane)
            {
                wrapper.error(ane);
            }
            catch (SocketException se)
            {
                wrapper.error(se);
            }
            catch (EClientException e)
            {
                var cmp = (e as EClientException).Err;

                wrapper.error(-1, cmp.Code, cmp.Message);
            }
            catch (Exception e)
            {
                wrapper.error(e);
            }
        }
示例#3
0
        public virtual bool Connect(int p_socketPort, int p_brokerConnectionClientID)
        {
            Utils.Logger.Info($"ClientSocket.eConnect(127.0.0.1, {p_socketPort}, {p_brokerConnectionClientID}, false)");
            ClientSocket.eConnect("127.0.0.1", p_socketPort, p_brokerConnectionClientID, false);
            //Create a reader to consume messages from the TWS. The EReader will consume the incoming messages and put them in a queue
            m_eReader = new EReader(ClientSocket, Signal);
            m_eReader.Start();
            //Once the messages are in the queue, an additional thread need to fetch them. This is a very long running Thread, always waiting for all messages (Price, historicalData, etc.). This Thread calls the IbWrapper Callbacks.
            new Thread(() =>
            {
                try
                {
                    while (ClientSocket.IsConnected())
                    {
                        Signal.waitForSignal(); // the reader thread will sign the Signal
                        m_eReader.processMsgs();
                    }
                }
                catch (Exception e)
                {
                    if (Utils.MainThreadIsExiting.IsSet)
                        return; // if App is exiting gracefully, this Exception is not a problem
                    Utils.Logger.Error("Exception caught in Gateway Thread that is fetching messages. " + e.Message + " ,InnerException: " + ((e.InnerException != null) ? e.InnerException.Message : ""));
                    throw;  // else, rethrow. This will Crash the App, which is OK. Without IB connection, there is no point to continue the VBroker App.
                }
            })
            { IsBackground = true }.Start();

            /*************************************************************************************************************************************************/
            /* One (although primitive) way of knowing if we can proceed is by monitoring the order's nextValidId reception which comes down automatically after connecting. */
            /*************************************************************************************************************************************************/
            //This is returned at Connection:
            //Account list: U1****6
            //Next Valid Id: 1
            DateTime startWaitConnection = DateTime.UtcNow;
            while (NextOrderId <= 0)
            {
                Thread.Sleep(100);
                if ((DateTime.UtcNow - startWaitConnection).TotalSeconds > 5.0)
                {
                    return false;
                }
            }
            return true;
        }
        /**
         * @brief Establishes a connection to the designated THost.
         * After establishing a connection succesfully, the Host will provide the next valid order id, server's current time, managed accounts and open orders among others depending on the Host version.
         * @param host the Host's IP address. Leave blank for localhost.
         * @param port the Host's port. 7496 by default for the TWS, 4001 by default on the Gateway.
         * @param clientId Every API client program requires a unique id which can be any integer. Note that up to eight clients can be connected simultaneously to a single Host.
         * @sa EWrapper, EWrapper::nextValidId, EWrapper::currentTime
         */
        public void eConnect(string host, int port, int clientId)
        {
            if (isConnected)
            {
                wrapper.error(IncomingMessage.NotValid, EClientErrors.AlreadyConnected.Code, EClientErrors.AlreadyConnected.Message);
                return;
            }
            try
            {
                tcpClient = new TcpClient(host, port);
                tcpClientStream = tcpClient.GetStream();
                tcpWriter = new BinaryWriter(tcpClientStream);

                reader = new EReader(this, new BinaryReader(tcpClientStream));

                try
                {
                    tcpWriter.Write(UTF8Encoding.UTF8.GetBytes(Constants.ClientVersion.ToString()));
                    tcpWriter.Write(Constants.EOL);
                }
                catch (IOException)
                {
                    wrapper.error("Could not establish connection. Make sure the TWS is enabled to accept socket clients!");
                    throw;
                }
                // Receive the response from the remote device.
                serverVersion = reader.ReadInt();
                if (!CheckServerVersion(MinServerVer.MIN_VERSION, ""))
                {
                    ReportUpdateTWS("");
                    return;
                }

                if (serverVersion >= 20)
                {
                    string twsTime = reader.ReadString();
                    Console.WriteLine("TWS time: " + twsTime);
                }
                if (serverVersion >= 3)
                {
                    tcpWriter.Write(UTF8Encoding.UTF8.GetBytes(clientId.ToString()));
                    tcpWriter.Write(Constants.EOL);
                }
                reader.Start();
                while (!reader.IsAlive()) ;
                isConnected = true;

            }
            catch (ArgumentNullException ane)
            {
                wrapper.error(ane);
            }
            catch (SocketException se)
            {
                wrapper.error(se);
            }
            catch (Exception e)
            {
                wrapper.error(e);
            }
           
        }
        /**
         * @brief Closes the socket connection and terminates its thread.
         */
        public void eDisconnect()
        {   
            if(tcpWriter == null)
            {
                return;
            }

            isConnected = false;
            serverVersion = 0;


            if (tcpWriter != null)
            {
                tcpWriter.Close();
                tcpWriter = null;
                tcpClientStream.Close();
                tcpWriter = null;
            }

            if (reader != null)
            {
                try
                {
                    reader.Interrupt();
                    reader = null;
                }
                catch (Exception) 
                {
                    throw;
                }
            }
            wrapper.connectionClosed();

        }
示例#6
0
        public void eConnect(string host, int port, int clientId, bool extraAuth)
        {
            if (isConnected)
            {
                wrapper.error(IncomingMessage.NotValid, EClientErrors.AlreadyConnected.Code, EClientErrors.AlreadyConnected.Message);
                return;
            }
            try
            {
                tcpStream = createClientStream(host, port);
                this.port = port;
                socketTransport = new ESocket(tcpStream);

                this.clientId = clientId;
                this.extraAuth = extraAuth;

                sendConnectRequest();

                if (!AsyncEConnect)
                {
                    var eReader = new EReader(this, eReaderSignal);

                    while (serverVersion == 0 && eReader.putMessageToQueue())
                    {
                        eReaderSignal.waitForSignal();
                        eReader.processMsgs();
                    }
                }
            }
            catch (ArgumentNullException ane)
            {
                wrapper.error(ane);
            }
            catch (SocketException se)
            {
                wrapper.error(se);
            }
            catch (EClientException e)
            {
                var cmp = (e as EClientException).Err;

                wrapper.error(-1, cmp.Code, cmp.Message);
            }
            catch (Exception e)
            {
                wrapper.error(e);
            }
        }
        /// <summary>
        /// Connects the client to the IB gateway
        /// </summary>
        public override void Connect()
        {
            if (IsConnected) return;

            // we're going to receive fresh values for both of these collections, so clear them
            _accountHoldings.Clear();
            _accountProperties.Clear();

            var attempt = 1;
            const int maxAttempts = 65;
            while (true)
            {
                try
                {
                    Log.Trace("InteractiveBrokersBrokerage.Connect(): Attempting to connect ({0}/{1}) ...", attempt, maxAttempts);

                    // we're going to try and connect several times, if successful break
                    _client.ClientSocket.eConnect(_host, _port, _clientId);

                    // create the message processing thread
                    var signal = new EReaderMonitorSignal();
                    var reader = new EReader(_client.ClientSocket, signal);
                    reader.Start();

                    var messageProcessingThread = new Thread(() =>
                    {
                        Log.Trace("IB message processing thread started.");

                        while (_client.ClientSocket.IsConnected())
                        {
                            try
                            {
                                signal.waitForSignal();
                                reader.processMsgs();
                            }
                            catch (Exception error)
                            {
                                // error in message processing thread, log error and disconnect
                                Log.Error("Error in message processing thread: " + error);
                            }
                        }

                        Log.Trace("IB message processing thread ended.");
                    }) { IsBackground = true };

                    messageProcessingThread.Start();

                    // pause for a moment to receive next valid ID message from gateway
                    if (!_waitForNextValidId.WaitOne(15000))
                    {
                        Log.Trace("InteractiveBrokersBrokerage.Connect(): Operation took longer than 15 seconds.");

                        // no response, disconnect and retry
                        _client.ClientSocket.eDisconnect();
                        messageProcessingThread.Join();

                        // max out at 65 attempts to connect ~1 minute
                        if (attempt++ < maxAttempts)
                        {
                            Thread.Sleep(1000);
                            continue;
                        }
                        
                        throw new TimeoutException("InteractiveBrokersBrokerage.Connect(): Operation took longer than 15 seconds.");
                    }

                    Log.Trace("IB next valid id received.");

                    if (!_client.Connected) throw new Exception("InteractiveBrokersBrokerage.Connect(): Connection returned but was not in connected state.");
                    break;
                }
                catch (Exception err)
                {
                    // max out at 65 attempts to connect ~1 minute
                    if (attempt++ < maxAttempts)
                    {
                        Thread.Sleep(1000);
                        continue;
                    }

                    // we couldn't connect after several attempts, log the error and throw an exception
                    Log.Error(err);

                    // add a blurb about TWS for connection refused errors
                    if (err.Message.Contains("Connection refused"))
                    {
                        throw new Exception(err.Message + ". Be sure to logout of Trader Workstation. " +
                            "IB only allows one active log in at a time. " +
                            "This can also be caused by requiring two-factor authentication. " +
                            "Be sure to disable this in IB Account Management > Security > SLS Opt out.", err);
                    }

                    throw;
                }
            }

            // define our event handler, this acts as stop to make sure when we leave Connect we have downloaded the full account
            EventHandler<IB.AccountDownloadEndEventArgs> clientOnAccountDownloadEnd = (sender, args) =>
            {
                Log.Trace("InteractiveBrokersBrokerage.AccountDownloadEnd(): Finished account download for " + args.Account);
                _accountHoldingsResetEvent.Set();
            };
            _client.AccountDownloadEnd += clientOnAccountDownloadEnd;

            // we'll wait to get our first account update, we need to be absolutely sure we 
            // have downloaded the entire account before leaving this function
            var firstAccountUpdateReceived = new ManualResetEvent(false);
            EventHandler<IB.UpdateAccountValueEventArgs> clientOnUpdateAccountValue = (sender, args) =>
            {
                firstAccountUpdateReceived.Set();
            };

            _client.UpdateAccountValue += clientOnUpdateAccountValue;

            // first we won't subscribe, wait for this to finish, below we'll subscribe for continuous updates
            _client.ClientSocket.reqAccountUpdates(true, _account); 

            // wait to see the first account value update
            firstAccountUpdateReceived.WaitOne(2500);

            // take pause to ensure the account is downloaded before continuing, this was added because running in
            // linux there appears to be different behavior where the account download end fires immediately.
            Thread.Sleep(2500);

            if (!_accountHoldingsResetEvent.WaitOne(15000))
            {
                throw new TimeoutException("InteractiveBrokersBrokerage.GetAccountHoldings(): Operation took longer than 15 seconds.");
            }

            // remove our end handler
            _client.AccountDownloadEnd -= clientOnAccountDownloadEnd;
            _client.UpdateAccountValue -= clientOnUpdateAccountValue;
        }
示例#8
0
        internal void TestVbGatewayConnection()
        {

            Utils.Logger.Debug("TestVbGatewayConnection() BEGIN");
            // start c:\Jts\StartIBGateway.bat 
            // IBGateway this version works: Build 952.1a, Aug 18, 2015 3:38:07 PM  // c:\Jts\StartIBGateway.bat 
            // this works too. Stable: Build 952.2h, Jan 29, 2016 4:40:48 PM        // c:\Jts\952\jars\StartIBGateway.bat , or simple "javaw.exe -cp jts.jar;total.jar ibgateway.GWClient" command line works
            // Latest (not Stable) doesn't work c:\Jts\955\jars\StartIBGateway.bat  or simple "javaw.exe -cp jts4launch.jar;total.jar ibgateway.GWClient" command line doesn't work, although the ibgateway.GWClient is there. Buggy.

            // see for samples:  "g:\temp\_programmingTemp\TWS API_972.12(2016-02-26)\samples\CSharp\IBSamples\Program.cs" 

            BrokerWrapperIb testImpl = new BrokerWrapperIb();
            EClientSocket client = testImpl.ClientSocket;
            
            int portID = (int)GatewayUserPort.GyantalMain;      // the IBGateways ports on Release Linux and Developer Windows local should be the same.
            client.eConnect("127.0.0.1", portID, 0, false);     // it uses connectionID=0, which may be not good. Real VBroker uses 41 and 42 userIDs.

            //Create a reader to consume messages from the TWS. The EReader will consume the incoming messages and put them in a queue
            var reader = new EReader(client, testImpl.Signal);
            reader.Start();
            //Once the messages are in the queue, an additional thread need to fetch them
            new Thread(() =>
            {
                while (client.IsConnected())
                {
                    testImpl.Signal.waitForSignal();
                    reader.processMsgs();
                }
            })
            { IsBackground = true }.Start();

            /*************************************************************************************************************************************************/
            /* One (although primitive) way of knowing if we can proceed is by monitoring the order's nextValidId reception which comes down automatically after connecting. */
            /*************************************************************************************************************************************************/
            while (testImpl.NextOrderId <= 0) { }

            Console.WriteLine("Connection seems to be OK. Requesting Account Summary...");

            /*** Requesting managed accounts***/
            client.reqManagedAccts();
            /*** Requesting accounts' summary ***/
            Thread.Sleep(2000);
            client.reqAccountSummary(9001, "All", AccountSummaryTags.GetAllTags());
            /*** Subscribing to an account's information. Only one at a time! ***/

            Thread.Sleep(6000);
            Console.WriteLine("Disconnecting...");
            client.eDisconnect();
        }