public async Task StopAsync() { if (ExchangeClient == null || MarketDataClient == null) { return; } Log.Information("Stop terminal services"); TaskPerformer.Stop(); TaskPerformer.Clear(); await Task.WhenAll( ExchangeClient.CloseAsync(), MarketDataClient.CloseAsync()); ExchangeClient.Connected -= OnExchangeConnectedEventHandler; ExchangeClient.Disconnected -= OnExchangeDisconnectedEventHandler; ExchangeClient.AuthOk -= OnExchangeAuthOkEventHandler; ExchangeClient.AuthNonce -= OnExchangeAuthNonceEventHandler; ExchangeClient.Error -= OnExchangeErrorEventHandler; ExchangeClient.OrderReceived -= OnExchangeOrderEventHandler; ExchangeClient.SwapReceived -= OnSwapReceivedEventHandler; MarketDataClient.Connected -= OnMarketDataConnectedEventHandler; MarketDataClient.Disconnected -= OnMarketDataDisconnectedEventHandler; MarketDataClient.AuthOk -= OnMarketDataAuthOkEventHandler; MarketDataClient.AuthNonce -= OnMarketDataAuthNonceEventHandler; MarketDataClient.Error -= OnMarketDataErrorEventHandler; MarketDataClient.QuotesReceived -= OnQuotesReceivedEventHandler; MarketDataClient.EntriesReceived -= OnEntriesReceivedEventHandler; MarketDataClient.SnapshotReceived -= OnSnapshotReceivedEventHandler; }
public void SubscribeToMarketData(SubscriptionType type) { MarketDataClient.SubscribeAsync(new List <Subscription> { new Subscription { Type = type } }); }
private async void OnMarketDataAuthNonceEventHandler(object sender, EventArgs args) { try { var auth = await Account .CreateAuthRequestAsync( nonce : MarketDataClient.Nonce, keyIndex : Account.UserSettings.AuthenticationKeyIndex) .ConfigureAwait(false); MarketDataClient.AuthAsync(auth); } catch (Exception e) { Log.Error(e, "MarketData auth error"); } }
protected override Position Build() { Position?existingPosition = Database.GetPosition(Symbol); if (existingPosition?.LongQuantity == Quantity) { return(existingPosition); } else { bool isValid = MarketDataClient.ValidateWithinTodaysRangeAndGetQuote(Symbol, (float)Last, out _); if (isValid) { return(new Position(Symbol, Quantity, (float)Average)); } else { Log.Information("Found invalid symbol/price in parsed position: Symbol {Symbol}. Builder {@Builder}", Symbol, this); return(BuildModelFromSimilarUsedSymbol()); } } }
protected override FilledOrder Build() { UnvalidatedFilledOrder unvalidatedOrder = new UnvalidatedFilledOrder(Symbol, (float)FilledPrice, Instruction, OrderType, (float)Limit, Quantity, Time); FilledOrder? existingOrder = Database.GetTodaysFilledOrders().FirstOrDefault(order => unvalidatedOrder.StrictEquals(order)); if (existingOrder != null) { return(existingOrder); } else { bool isValid = MarketDataClient.ValidateWithinTodaysRangeAndGetQuote(unvalidatedOrder, out OptionQuote? quote); if (isValid) { return(new FilledOrder(unvalidatedOrder, quote)); } else { Log.Information("Found invalid symbol/price in parsed order: Symbol {Symbol}. Builder {@Builder}", Symbol, this); return(BuildModelFromSimilarUsedSymbol()); } } }
public LottoXClient(RagingBullConfig rbConfig, OCRConfig ocrConfig, PortfolioDatabase database, MarketDataClient marketDataClient) : base(rbConfig, database, marketDataClient) { PositionBuilder positionBuilder = new PositionBuilder(marketDataClient, database); FilledOrderBuilder orderBuilder = new FilledOrderBuilder(marketDataClient, database); ImageToPositionsConverter = new ImageToPositionsConverter(ocrConfig, positionBuilder); ImageToOrdersConverter = new ImageToOrdersConverter(ocrConfig, orderBuilder); QuantityConsistencyClient = new ImageConsistencyClient(); HeaderConsistencyClient = new ImageConsistencyClient(); OrderConsistencyClient = new ImageConsistencyClient(); }
protected override bool ValidateWithSymbolOverride(string overrideSymbol, out OptionQuote?quote) { return(MarketDataClient.ValidateWithinTodaysRangeAndGetQuote(overrideSymbol, (float)Last, out quote)); }
public PositionBuilder(MarketDataClient client, PortfolioDatabase database) : base(client, database) { }
protected override async Task ExecuteAsync(CancellationToken stoppingToken) { //TimeSortedCollection<FilledOrder> liveOrders = new TimeSortedCollection<FilledOrder>(); //liveOrders.Add(new FilledOrder("NIO_201204C55", (float)0.5, "BUY_TO_OPEN", "LIMIT", (float)0.5, 50, new DateTime(2020, 12, 1, 12, 25, 33))); //liveOrders.Add(new FilledOrder("NIO_201204C60", (float)0.5, "BUY_TO_OPEN", "LIMIT", (float)0.5, 50, new DateTime(2020, 12, 1, 12, 22, 30))); //liveOrders.Add(new FilledOrder("NIO_201204C62", (float)0.5, "BUY_TO_OPEN", "LIMIT", (float)0.5, 50, new DateTime(2020, 12, 1, 12, 22, 30))); //liveOrders.Add(new FilledOrder("NIO_201204C65", (float)0.5, "BUY_TO_OPEN", "LIMIT", (float)0.5, 50, new DateTime(2020, 12, 1, 12, 30, 00))); //LivePortfolioClient.IdentifyNewAndUpdatedOrders(liveOrders, 260); //IEnumerable<Position> positions = BrokerClient.GetPositions(); //OptionQuote quote; //try //{ // quote = MarketDataClient.GetOptionQuote("AAPL_201218C140"); // //OptionQuote quote = MarketDataClient.GetQuote("AAPL_121819C140"); //} //catch (Exception ex) //{ // Log.Information(ex, "hello"); //} //Order o1 = new Order("AAPL_201218C150", 1, InstructionType.SELL_TO_CLOSE, OrderType.MARKET, (float)0.08); //BrokerClient.PlaceOrder(o1); //Log.Information("Placing Order: {@Order}", o1); //IList<Position> positions = await ((LottoXClient)LivePortfolioClient).GetPositionsFromImage("C:/Users/Admin/WindowsServices/MarketCode/LottoXService/screenshots/portfolio-4380.png"); //Order o1 = new Order("AAPL_201231C150", 1, InstructionType.BUY_TO_OPEN, OrderType.LIMIT, (float).03); //Order o2 = new Order("CMG_201231C150", 1, InstructionType.BUY_TO_OPEN, OrderType.LIMIT, (float).03); //BrokerClient.PlaceOrder(o1); //BrokerClient.PlaceOrder(o2); BrokerClient.CancelExistingBuyOrders("ZM_210115C550"); Log.Information("RETURNING EARLY"); return; if (!MarketDataClient.IsMarketOpenToday()) { Log.Information("Market closed today"); return; } //Log.Information("NOT LOGGING IN"); await LivePortfolioClient.Login(); TimeSpan marketOpenTime = new TimeSpan(9, 30, 0); TimeSpan marketCloseTime = new TimeSpan(16, 0, 0); int invalidPortfolioStateCount = 0; int errorCount = 0; //string seedOrdersFilename = "C:/Users/Admin/WindowsServices/MarketCode/LottoXService/screenshots/orders-4173.png"; string seedOrdersFilename = ""; while (!stoppingToken.IsCancellationRequested) { TimeSpan now = DateTime.Now.TimeOfDay; if (now >= marketCloseTime) { Log.Information("Market now closed!"); ElmahClient.Dispose(); //Log.Information("NOT BREAKING ON MARKET CLOSED"); break; } else if (now <= marketOpenTime) { Log.Information("Market not open yet!"); // Or, wait until 9:30am await Task.Delay(30 * 1000, stoppingToken); continue; } try { Task _ = ElmahClient.Heartbeats.HealthyAsync(new Guid(_elmahConfig.LogId), _elmahConfig.HeartbeatId); TimeSortedCollection <PositionDelta> deltas; if (seedOrdersFilename.Length > 0) { Log.Information("*********Seeding live orders with file " + seedOrdersFilename); deltas = await LivePortfolioClient.GetLiveDeltasFromPositions(seedOrdersFilename); seedOrdersFilename = ""; } else if (errorCount > 0 || invalidPortfolioStateCount > 0) { Log.Information("***Getting live deltas after error"); deltas = await LivePortfolioClient.GetLiveDeltasFromPositions(); } else if (await LivePortfolioClient.HaveOrdersChanged(null)) { Log.Information("***Change in top orders detected- getting live orders"); deltas = await LivePortfolioClient.GetLiveDeltasFromPositions(); } else { deltas = new TimeSortedCollection <PositionDelta>(); } foreach (PositionDelta delta in deltas) { Order?order = OrderManager.DecideOrder(delta); if (order != null) { if (order.Instruction == InstructionType.SELL_TO_CLOSE) { BrokerClient.CancelExistingBuyOrders(order.Symbol); } BrokerClient.PlaceOrder(order); } } invalidPortfolioStateCount = 0; errorCount = 0; } catch (InvalidPortfolioStateException) { invalidPortfolioStateCount++; if (invalidPortfolioStateCount == 2) { Log.Error("Portfolio found invalid {InvalidCount} times", invalidPortfolioStateCount); } else if (invalidPortfolioStateCount > 2) { Log.Fatal("Portfolio found invalid {InvalidCount} times", invalidPortfolioStateCount); break; } await LivePortfolioClient.Login(); continue; } catch (PortfolioDatabaseException) { //Assume the exception is already logged break; } catch (OptionParsingException ex) { Log.Fatal(ex, "Error parsing option symbol. Symbol {Symbol}. Terminating program.", ex.Symbol); break; } catch (ArgumentException ex) { Log.Fatal(ex, "Arument exception encountered- terminating program."); break; } catch (ModelBuilderException ex) { Log.Error(ex, "ModelBuilderException encountered"); errorCount++; if (errorCount > 2) { Log.Fatal(ex, "Too many consecutive errors encountered. Terminating program. Error count = {ErrorCount}", errorCount); break; } } catch (Exception ex) { errorCount++; if (errorCount <= 2) { Log.Error(ex, "Unexpected error: count = {ErrorCount}", errorCount); } else if (errorCount > 2) { Log.Fatal(ex, "Too many consecutive errors encountered. Terminating program. Error count = {ErrorCount}", errorCount); break; } } await Task.Delay(15 *1000, stoppingToken); } _hostApplicationLifetime.StopApplication(); }
public FilledOrderBuilder(MarketDataClient client, PortfolioDatabase database) : base(client, database) { Instruction = ""; OrderType = ""; }
public LtxModelBuilder(MarketDataClient marketDataClient, PortfolioDatabase database) { Symbol = ""; MarketDataClient = marketDataClient; Database = database; }
public RagingBullClient(RagingBullConfig config, PortfolioDatabase positionDB, MarketDataClient marketDataClient) : base(positionDB, marketDataClient) { Email = config.Email; Password = config.Password; PortfolioUrl = config.PortfolioUrl; ChromePath = config.ChromePath; }