예제 #1
0
        public static void GetStrategyId(FuturesContract futuresContract, Strategy strategy, SignalFile signalFile, SimpleLogger log)
        {
            var strategyInfo = from s in StrategyList
                               where s.Name == signalFile.StrategyName
                               select new { s.Id, s.Name, s.Ticker, s.OType, s.Contracts, s.MaxPosition, s.Enabled };

            var symbolMaxPosition = from s in StrategyList
                                    where s.Ticker == futuresContract.Symbol
                                    group s by s.Ticker into sg
                                    orderby sg.Key
                                    select new { sg.Key, Total = sg.Sum(x => x.MaxPosition) };

            foreach (var g in strategyInfo)
            {
                strategy.StrategyId          = g.Id;
                strategy.Symbol              = g.Ticker;
                strategy.StrategyName        = g.Name;
                strategy.OrderType           = g.OType;
                strategy.LotSize             = g.Contracts;
                strategy.StrategyMaxPosition = g.MaxPosition;
                strategy.Status              = g.Enabled;

                foreach (var c in symbolMaxPosition)
                {
                    strategy.MaxPositionForSymbol = c.Total;
                }
            }

            log.Info($"[STRATEGY INFO] StrategyId:{strategy.StrategyId} StrategyName:{strategy.StrategyName}");
        }
예제 #2
0
        private void ValidateParsedDataForTrade(SignalFile signalFile)
        {
            const int _max = 1000000;
            Stopwatch s1   = Stopwatch.StartNew();

            DateTime tradeDateTime = Convert.ToDateTime(string.Format("{0:MM-dd-yyyy}", signalFile.TradeDateTime.Trim()), CultureInfo.CurrentCulture);
            string   entryDateTime = tradeDateTime.ToString("MM-dd-yyyy");

            if (signalFile.TradeDate == DateToday.Today && entryDateTime == DateToday.Today)
            {
                //Map TS symbol to IB symbol and set contract details
                FuturesContract futuresContract = new FuturesContract();
                futuresContract = futures.GetContractDetails(contract, futuresContract, signalFile);

                //Map TS strategies to strategies defined in application data list
                Strategy strategy = new Strategy(log);
                Strategy.GetStrategyId(futuresContract, strategy, signalFile, log);

                if (InitializeValues(strategy, signalFile))
                {
                    //Check if app is connected to IB Api and get current IB positions
                    Positions positions = new Positions();
                    broker.UpdateIBpositions(strategy, positions, log);

                    //Check last position for strategy in Position_Data table
                    Transactions transactions = new Transactions();
                    Transactions.CheckLastPositionDataFromDB(transactions, strategy, signalFile, log);

                    //Check if strategy has exceeded maximum position
                    //Tuple MaxTradeFlag, dbPosConflict, strategyCurrentPosition
                    Tuple <bool, bool, int> db = positions.GetMaxPosition(strategy, signalFile, transactions, positions, log, @params);

                    //Display transaction conflict message
                    Transactions.CheckLastTrade(signalFile, transactions, log, positions, db);

                    //Set lot size based on current IB position
                    OrderDetails orderDetails = new OrderDetails();
                    orderDetails = OrderDetails.GetLotSize(db, orderDetails, strategy, signalFile, positions);

                    //Check if a limit order was never filled at the Broker and cancel any open order(s)
                    //Tuple MaxTradeFlag, dbPosConflict, strategyCurrentPosition
                    if (db.Item2) //db.Item1 ||
                    {
                        bool allOpenOrder = false;
                        CancelOpenOrders(strategy, db.Item2, orderDetails, allOpenOrder);
                    }

                    //If trade is for today and less than max position excute order
                    ProcessSignalForTrade(futuresContract, signalFile, orderDetails, strategy, db, log);
                }
            }
            s1.Stop();
            string diag = string.Format("Processed Order in: " + (s1.Elapsed.TotalMilliseconds * 1000000 / _max).ToString("0.00 ns"));

            log.Info(diag);
        }
예제 #3
0
        private void UpdateDBTables(FuturesContract futuresContract, SignalFile signalFile, OrderDetails orderDetails, Strategy strategy, double limitPrice)
        {
            int currentPositionForDB = GetCurrentPositionForDB(orderDetails, strategy);

            DBFunctions.UpdatePositionDataToDb(log, futuresContract, signalFile, orderDetails, limitPrice);

            DBFunctions.UpdateStrategyPosition(log, currentPositionForDB, strategy, orderDetails);

            DBFunctions.CalculateProfitandLoss(log, strategy, signalFile);
        }
예제 #4
0
 public Controller(EClientSocket clientSocket, SimpleLogger log, Parameters @params, Strategy strategy, Broker broker, Positions positions, FuturesContract futures, Prices prices, Transactions transactions, Slack slack)
 {
     this.@params      = @params;
     this.log          = log;
     this.clientSocket = clientSocket;
     this.strategy     = strategy;
     this.broker       = broker;
     this.futures      = futures;
     this.prices       = prices;
     this.transactions = transactions;
     this.slack        = slack;
 }
예제 #5
0
        private double GetPrices(FuturesContract futuresContract, SignalFile signalFile, Strategy strategy, OrderDetails orderDetails, Prices prices, Tuple <bool, bool, int> db)
        {
            double limitPrice = 0;

            if (prices.BidPrice > 0 && prices.AskPrice > 0)
            {
                limitPrice = GetBrokerLimitPrice(futuresContract, orderDetails, prices, strategy, db, signalFile);
            }
            else if (limitPrice <= 0)
            {
                limitPrice = GetSignalFileLimitPrice(futuresContract, orderDetails, signalFile, strategy, db);
            }

            return(limitPrice);
        }
예제 #6
0
        private void ProcessSignalForTrade(FuturesContract futuresContract, SignalFile signalFile, OrderDetails orderDetails, Strategy strategy, Tuple <bool, bool, int> db, SimpleLogger log)
        {
            if (!db.Item1 && [email protected])
            {
                slack.SendMessageToSlack($"[*{strategy.Symbol} {orderDetails.BuyOrSell}]*\n*{signalFile.LastFileLine}*", @params);

                //Cancel any open orders
                bool dbconflict   = false;
                bool allOpenOrder = true;
                CancelOpenOrders(strategy, dbconflict, orderDetails, allOpenOrder);

                //Send order to Broker
                double limitPrice = ExecuteOrder(futuresContract, signalFile, orderDetails, strategy, log, db);

                //Used to check order status @ Broker
                //CheckOrderStatus();

                //Update db with executed strategy order
                UpdateDBTables(futuresContract, signalFile, orderDetails, strategy, limitPrice);
            }
        }
예제 #7
0
        public static double GetTickSize(FuturesContract futuresContract)
        {
            switch (futuresContract.Symbol)
            {
            case "ES": return(0.25);

            case "MES": return(0.25);

            case "CL": return(0.01);

            case "GC": return(0.10);

            case "MGC": return(0.10);

            case "QM": return(0.025);

            case "RTY": return(0.10);

            case "YM": return(1.00);

            default: return(0.00);
            }
        }
예제 #8
0
        public static void UpdatePositionDataToDb(SimpleLogger log, FuturesContract futuresContract, SignalFile signalFile, OrderDetails orderDetails, double limitPrice)
        {
            try
            {
                var sqlite_conn = CreateConnection();

                SQLiteCommand sqlite_cmd;
                sqlite_cmd             = sqlite_conn.CreateCommand();
                sqlite_cmd.CommandText = "INSERT INTO Position_Data" +
                                         " VALUES (  '" + signalFile.TradeDate +
                                         "','" + signalFile.TradeDateTime +
                                         "','" + orderDetails.OrderId +
                                         "','" + signalFile.StrategyName +
                                         "','" + futuresContract.Exchange +
                                         "','" + orderDetails.BuyOrSell +
                                         "','" + orderDetails.OrderStatus +
                                         "'," + limitPrice.ToString("0." + new string('#', 20)) +
                                         ");";
                int result = sqlite_cmd.ExecuteNonQuery();

                if (result > 0)
                {
                    log.Db("Successfully updated Position_Data table.");
                }
                else
                {
                    log.Db("Failed to update Position_Data table.");
                }

                sqlite_conn.Close();
            }
            catch (SQLiteException ex)
            {
                log.Trace("Error " + ex.Message.ToString());
                log.Trace(ex.StackTrace.ToString());
            }
        }
예제 #9
0
        public static void Main(string[] args)
        {
            EWrapperImpl  ibClient     = new EWrapperImpl();
            EClientSocket clientSocket = ibClient.ClientSocket;


            Console.ForegroundColor = ConsoleColor.DarkGreen;
            string logo = @"
 /$$$$$$$  /$$                     /$$        /$$$$$$                      /$$   /$$               /$$       /$$$$$$                        
| $$__  $$| $$                    | $$       /$$__  $$                    |__/  | $$              | $$      |_  $$_/                        
| $$  \ $$| $$  /$$$$$$   /$$$$$$$| $$   /$$| $$  \__/  /$$$$$$   /$$$$$$  /$$ /$$$$$$    /$$$$$$ | $$        | $$   /$$$$$$$   /$$$$$$$    
| $$$$$$$ | $$ /$$__  $$ /$$_____/| $$  /$$/| $$       |____  $$ /$$__  $$| $$|_  $$_/   |____  $$| $$        | $$  | $$__  $$ /$$_____/    
| $$__  $$| $$| $$  \ $$| $$      | $$$$$$/ | $$        /$$$$$$$| $$  \ $$| $$  | $$      /$$$$$$$| $$        | $$  | $$  \ $$| $$          
| $$  \ $$| $$| $$  | $$| $$      | $$_  $$ | $$    $$ /$$__  $$| $$  | $$| $$  | $$ /$$ /$$__  $$| $$        | $$  | $$  | $$| $$          
| $$$$$$$/| $$|  $$$$$$/|  $$$$$$$| $$ \  $$|  $$$$$$/|  $$$$$$$| $$$$$$$/| $$  |  $$$$/|  $$$$$$$| $$       /$$$$$$| $$  | $$|  $$$$$$$ /$$
|_______/ |__/ \______/  \_______/|__/  \__/ \______/  \_______/| $$____/ |__/   \___/   \_______/|__/      |______/|__/  |__/ \_______/|__/
                                                                | $$                                                                        
                                                                | $$                                                                        
                                                                |__/                                                                        

                            ";

            Console.WriteLine(logo);
            Console.ResetColor();

            Console.Write("BlockShift Trading App");
            Console.Write("\n");
            Console.Write("DISCLAIMER: USING THIS SOFTWARE AT MY OWN RISK\n");
            Console.Write("\n");

            try
            {
                ConsoleWindow.QuickEditMode(false);

                Parameters @params = new Parameters(Path.Combine(Environment.CurrentDirectory, "config.conf"));

                SimpleLogger log = new SimpleLogger();

                Slack slack = new Slack(@params);

                Prices prices = new Prices(log, @params);

                FuturesContract futures = new FuturesContract(@params);

                Strategy strategy = new Strategy(log);

                Broker broker = new Broker(clientSocket, log, @params, slack);

                Positions positions = new Positions(log, @params, slack);

                Transactions transactions = new Transactions(log);

                Controller ctl = new Controller(clientSocket, log, @params, strategy, broker, positions, futures, prices, transactions, slack);

                broker.ConnectionToBroker(strategy, positions);

                ctl.Run();
            }
            catch (Exception ex)
            {
                Console.Write(ex.Message.ToString());
                Console.Write(ex.StackTrace.ToString());
            }


            Console.ReadLine();
        }
예제 #10
0
        private double GetSignalFileLimitPrice(FuturesContract futuresContract, OrderDetails orderDetails, SignalFile signalFile, Strategy strategy, Tuple <bool, bool, int> db)
        {
            double tick;
            double limitPrice = signalFile.LimitPrice;

            switch (strategy.Symbol)
            {
            case "QM":
                tick = FuturesContract.GetTickSize(futuresContract);
                decimal nearOf = 0.025M;

                //tick *= (signalFile.EMAAngle < 40 && signalFile.EMAAngle > -40) ? @params.crudeSpread : 4;
                tick *= (signalFile.Trend < 40) ? @params.crudeSpread : 4;

                if (orderDetails.BuyOrSell == "BUY")
                {
                    limitPrice -= tick;
                }
                else if (orderDetails.BuyOrSell == "SELL")
                {
                    limitPrice += tick;
                }

                decimal _limitPrice = Convert.ToDecimal(limitPrice);
                _limitPrice = Precision.UltimateRoundingFunction(_limitPrice, nearOf, 0.49M);
                limitPrice  = Convert.ToDouble(_limitPrice);

                return(limitPrice);

            case "MES":
                tick  = FuturesContract.GetTickSize(futuresContract);
                tick *= (signalFile.EMAAngle <40 && signalFile.EMAAngle> -40) ? @params.sp500Spread : @params.sp500Spread / 2;

                if (signalFile.Adx < 15)
                {
                    if (orderDetails.BuyOrSell == "BUY")
                    {
                        limitPrice -= tick;
                    }
                    else if (orderDetails.BuyOrSell == "SELL")
                    {
                        limitPrice += tick;
                    }
                }

                return(limitPrice);

            case "MGC":
                tick = FuturesContract.GetTickSize(futuresContract);

                if (signalFile.Adx < 15)
                {
                    tick *= 1;

                    if (orderDetails.BuyOrSell == "BUY")
                    {
                        limitPrice -= tick;
                        return(limitPrice);
                    }
                    else if (orderDetails.BuyOrSell == "SELL")
                    {
                        limitPrice += tick;
                        return(limitPrice);
                    }
                }
                else
                {
                    tick *= 2;

                    if (orderDetails.BuyOrSell == "BUY")
                    {
                        limitPrice += tick;
                        return(limitPrice);
                    }
                    else if (orderDetails.BuyOrSell == "SELL")
                    {
                        limitPrice -= tick;
                        return(limitPrice);
                    }
                }

                break;
            }
            return(limitPrice);
        }
예제 #11
0
        private double GetBrokerLimitPrice(FuturesContract futuresContract, OrderDetails orderDetails, Prices prices, Strategy strategy, Tuple <bool, bool, int> db, SignalFile signalFile)
        {
            double tick       = FuturesContract.GetTickSize(futuresContract);
            double limitPrice = 0;

            switch (strategy.Symbol)
            {
            case "QM":
                //tick *= (db.Item3 == 0 || db.Item3 != 0) ? @params.crudeSpread : 1;
                //if (signalFile.Macd == 1)
                //{
                //    tick *= (signalFile.Trend < 40 && orderDetails.BuyOrSell == "SELL") ? @params.crudeSpread : 4;
                //}
                //else if (signalFile.Macd == 2)
                //{
                //    tick *= (signalFile.Trend < 40 && orderDetails.BuyOrSell == "SELL") ? @params.crudeSpread : 3;
                //}
                //if (signalFile.Macd == -1)
                //{
                //    tick *= (signalFile.Trend < 40 && orderDetails.BuyOrSell == "BUY") ? @params.crudeSpread : 4;
                //}
                //else if (signalFile.Macd == -2)
                //{
                //    tick *= (signalFile.Trend < 40 && orderDetails.BuyOrSell == "BUY") ? @params.crudeSpread : 3;
                //}

                if (orderDetails.BuyOrSell == "BUY")
                {
                    //If Up trend than our bid is spread = 2 and offer is  @params.crudeSpread = 5
                    //tick *= (signalFile.EMAAngle < 40 && signalFile.EMAAngle > -40) ? @params.crudeSpread : 8;
                    tick *= (signalFile.Trend < 40) ? @params.crudeSpread : 4;

                    limitPrice  = Math.Min(prices.BidPrice, signalFile.LimitPrice);    //prices.BidPrice;
                    limitPrice -= tick;
                }
                else if (orderDetails.BuyOrSell == "SELL")
                {
                    //If Down trend than our offer is spread = 2 and out bid is @params.crudeSpread = 5
                    //tick *= (signalFile.EMAAngle < 40 && signalFile.EMAAngle > -40) ? @params.crudeSpread : 8;
                    tick *= (signalFile.Trend < 40) ? @params.crudeSpread : 4;

                    limitPrice  = Math.Max(prices.AskPrice, signalFile.LimitPrice);    //prices.AskPrice;
                    limitPrice += tick;
                }
                return(limitPrice);

            case "MES":
                //tick *= (db.Item3 == 0 || db.Item3 != 0) ? @params.sp500Spread : 1;
                //tick *= (signalFile.EMAAngle < 40 && signalFile.EMAAngle > -40) ? @params.sp500Spread : @params.sp500Spread ;
                tick *= (signalFile.Trend < 40) ? @params.sp500Spread : 5;

                if (orderDetails.BuyOrSell == "BUY")
                {
                    limitPrice  = Math.Min(prices.BidPrice, signalFile.LimitPrice);
                    limitPrice -= tick;
                }
                else if (orderDetails.BuyOrSell == "SELL")
                {
                    limitPrice  = Math.Max(prices.AskPrice, signalFile.LimitPrice);
                    limitPrice += tick;
                }
                return(limitPrice);
            }
            return(limitPrice);
        }
예제 #12
0
        private double ExecuteOrder(FuturesContract futuresContract, SignalFile signalFile, OrderDetails orderDetails, Strategy strategy, SimpleLogger log, Tuple <bool, bool, int> db)
        {
            Prices prices = new Prices();

            prices = prices.StartListener(clientSocket, contract, strategy, prices, log);

            double limitPrice = GetPrices(futuresContract, signalFile, strategy, orderDetails, prices, db);

            if (limitPrice <= 0)
            {
                limitPrice = signalFile.LimitPrice;
                log.Warning($"LimitPrice for {strategy.StrategyName} is null using signalFile price {signalFile.LimitPrice}");
            }

            //Use market orders overnight so we don't miss getting filled
            //string orderType = OverNight(signalFile, db);

            //if (string.IsNullOrEmpty(orderType))
            //{
            //    orderType = strategy.OrderType;
            //}

            Order        parent    = new Order();
            Order        openOrder = new Order();
            List <Order> orders    = new List <Order>();

            if (db.Item3 != 0) //If there is a position
            {
                //Use market orders overnight so we don't miss getting filled
                string orderType = OverNight(signalFile, db);

                //if (string.IsNullOrEmpty(orderType))
                //{
                //    orderType = strategy.OrderType;
                //}

                //Close position with market order
                parent = new Order()
                {
                    OrderId = OrderDetails.NextOrderId++,

                    Action        = orderDetails.BuyOrSell,
                    OrderType     = (string.IsNullOrEmpty(orderType) ? strategy.OrderType : orderType),     //strategy.OrderType, //"MKT",
                    TotalQuantity = strategy.LotSize,
                    LmtPrice      = (orderDetails.BuyOrSell == "SELL") ? prices.BidPrice : prices.AskPrice, //limitPrice,
                    AuxPrice      = (orderDetails.BuyOrSell == "SELL") ? prices.BidPrice : prices.AskPrice, //limitPrice,
                    Tif           = "GTC",

                    Transmit = true
                };

                openOrder = new Order()
                {
                    OrderId       = OrderDetails.NextOrderId++,
                    Action        = orderDetails.BuyOrSell,
                    OrderType     = strategy.OrderType, //(strategy.OrderType == "MKT" ? strategy.OrderType : orderType),
                    TotalQuantity = strategy.LotSize,
                    LmtPrice      = limitPrice,
                    AuxPrice      = limitPrice,
                    Tif           = "GTC",
                    Transmit      = true
                };

                orders = new List <Order>()
                {
                    parent,
                    openOrder
                };
            }
            else
            {
                openOrder = new Order()
                {
                    OrderId = OrderDetails.NextOrderId++,

                    Action        = orderDetails.BuyOrSell,
                    OrderType     = strategy.OrderType, //(strategy.OrderType == "MKT" ? strategy.OrderType : orderType),
                    TotalQuantity = orderDetails.LotSize,
                    LmtPrice      = limitPrice,
                    AuxPrice      = limitPrice,
                    Tif           = "GTC",

                    Transmit = true
                };
                orders = new List <Order>()
                {
                    openOrder
                };
            }

            foreach (Order o in orders)
            {
                clientSocket.placeOrder(o.OrderId, contract, o);
            }

            orderDetails.OrderId     = parent.OrderId.ToString();
            orderDetails.OrderStatus = "Submitted";

            if (db.Item3 != 0)
            {
                log.Signal($"Sent Closing {parent.Action} {parent.OrderType} Order for {strategy.Symbol} LimitPrice:{parent.LmtPrice} LotSize:{parent.TotalQuantity} OrderId:{parent.OrderId}");
                log.Signal($"Sent Opening {openOrder.Action} {openOrder.OrderType} Order for {strategy.Symbol} LimitPrice:{openOrder.LmtPrice} LotSize:{openOrder.TotalQuantity} OrderId:{openOrder.OrderId}");
            }
            else
            {
                log.Signal($"Sent Opening {openOrder.Action} {openOrder.OrderType} Order for {strategy.Symbol} LimitPrice:{openOrder.LmtPrice} LotSize:{openOrder.TotalQuantity} OrderId:{openOrder.OrderId}");
            }

            OrderDetails.OrderIdList.DataList.Add(orderDetails.OrderId);

            return(limitPrice);
        }
예제 #13
0
        //public  string OrderType { get; set; }
        //public  int MaxPosition { get; set; }
        //public  int LotSize { get; set; }
        public FuturesContract GetContractDetails(Contract contract, FuturesContract futuresContract, SignalFile signalFile)
        {
            if (signalFile.Symbol.Contains("ES"))
            {
                signalFile.Symbol = "ES";

                //switch (signalFile.StrategyName)
                //{
                //    case "MES TMA_Slope Kase Bar 3.75":
                contract.LocalSymbol = string.Empty;
                contract.Symbol      = "MES"; //MES  ***USE MICRO CONTRACT FOR GO LIVE
                contract.SecType     = @params.sp500SecType;
                contract.LastTradeDateOrContractMonth = @params.sp500Expiry;
                contract.Exchange = @params.sp500Exchange;
                contract.Currency = @params.sp500Currency;

                futuresContract.Symbol   = contract.Symbol;
                futuresContract.Exchange = @params.sp500Exchange;

                //break;
                //default:
                //    contract.LocalSymbol = string.Empty;
                //    contract.Symbol = signalFile.Symbol; //MES  ***USE MICRO CONTRACT FOR GO LIVE
                //    contract.SecType = @params.sp500SecType;
                //    contract.LastTradeDateOrContractMonth = @params.sp500Expiry;
                //    contract.Exchange = @params.sp500Exchange;
                //    contract.Currency = @params.sp500Currency;

                //    Symbol = contract.Symbol;
                //    Exchange = @params.sp500Exchange;
                //    break;
                //}
            }
            else if (signalFile.Symbol.Contains("QM"))
            {
                signalFile.Symbol    = "QM";
                contract.LocalSymbol = string.Empty;
                contract.Symbol      = signalFile.Symbol;
                contract.SecType     = @params.crudeSecType;
                contract.LastTradeDateOrContractMonth = @params.crudeExpiry;
                contract.Exchange = @params.crudeExchange;
                contract.Currency = @params.crudeCurrency;

                futuresContract.Symbol   = contract.Symbol;
                futuresContract.Exchange = @params.crudeExchange;
            }
            else if (signalFile.Symbol.Contains("CL"))
            {
                signalFile.Symbol    = "CL";
                contract.LocalSymbol = string.Empty;
                contract.Symbol      = signalFile.Symbol;
                contract.SecType     = @params.crudeSecType;
                contract.LastTradeDateOrContractMonth = @params.crudeExpiry;
                contract.Exchange = @params.crudeExchange;
                contract.Currency = @params.crudeCurrency;

                futuresContract.Symbol   = contract.Symbol;
                futuresContract.Exchange = @params.crudeExchange;
            }
            else if (signalFile.Symbol.Contains("GC"))
            {
                signalFile.Symbol    = "GC";
                contract.LocalSymbol = string.Empty;
                contract.Symbol      = "MGC"; //signalFile.Symbol;
                contract.SecType     = @params.goldSecType;
                contract.LastTradeDateOrContractMonth = @params.goldExpiry;
                contract.Exchange = @params.goldExchange;
                contract.Currency = @params.goldCurrency;

                futuresContract.Symbol   = contract.Symbol;
                futuresContract.Exchange = @params.goldExchange;
            }
            else if (signalFile.Symbol.Contains("TY"))
            {
                signalFile.Symbol    = "ZN";
                contract.LocalSymbol = string.Empty;
                contract.Symbol      = signalFile.Symbol;
                contract.SecType     = "FUT";
                contract.LastTradeDateOrContractMonth = @params.crudeExpiry;
                contract.Exchange = "ECBOT";
                contract.Currency = "USD";

                futuresContract.Symbol   = signalFile.Symbol;
                futuresContract.Exchange = "ECBOT";
            }

            return(futuresContract);
        }