public async Task Run() { alpacaTradingClient = Environments.Paper.GetAlpacaTradingClient(new SecretKey(API_KEY, API_SECRET)) as AlpacaTradingClient; polygonDataClient = Environments.Paper.GetPolygonDataClient(API_KEY) as PolygonDataClient; // Connect to Alpaca's websocket and listen for updates on our orders. alpacaStreamingClient = Environments.Paper.GetAlpacaStreamingClient(new SecretKey(API_KEY, API_SECRET)) as AlpacaStreamingClient; alpacaStreamingClient.ConnectAndAuthenticateAsync().Wait(); alpacaStreamingClient.OnTradeUpdate += HandleTradeUpdate; var sort = new ListOrdersRequest(); sort.OrderListSorting = SortDirection.Ascending; // Kill Switch part one // First, cancel any existing orders so they don't impact our buying power. var orders = await alpacaTradingClient.ListOrdersAsync(sort, Token); foreach (var order in orders) { await alpacaTradingClient.DeleteOrderAsync(order.OrderId); } // Figure out when the market will close so we can prepare to sell beforehand. var calendars = (await alpacaTradingClient .ListCalendarAsync(new CalendarRequest().SetTimeInterval(DateTime.Today.GetInclusiveIntervalFromThat()))) .ToList(); var calendarDate = calendars.First().TradingDateEst; var closingTime = calendars.First().TradingCloseTimeEst; closingTime = new DateTime(calendarDate.Year, calendarDate.Month, calendarDate.Day, closingTime.Hour, closingTime.Minute, closingTime.Second); var today = DateTime.Today; // Get the first group of bars from today if the market has already been open. var bars = await polygonDataClient.ListAggregatesAsync( new AggregatesRequest(symbol, new AggregationPeriod(1, AggregationPeriodUnit.Minute)) .SetInclusiveTimeInterval(today, today.AddDays(1))); var lastBars = bars.Items.Skip(Math.Max(0, bars.Items.Count() - 20)); foreach (var bar in lastBars) { Debug.Assert(bar.TimeUtc != null, "bar.TimeUtc != null"); if (bar.TimeUtc.Value.Add(TimeSpan.FromHours(3)) == today) { closingPrices.Add(bar.Close); } } Console.WriteLine("Waiting for market open..."); await AwaitMarketOpen(); Console.WriteLine("Market opened."); // Connect to Polygon's websocket and listen for price updates. polygonStreamingClient = (PolygonStreamingClient)Environments.Live.GetPolygonStreamingClient(API_KEY); polygonStreamingClient.ConnectAndAuthenticateAsync().Wait(); Console.WriteLine("Polygon client opened."); polygonStreamingClient.MinuteAggReceived += async(agg) => { // If the market's close to closing, exit position and stop trading. TimeSpan minutesUntilClose = closingTime - DateTime.UtcNow; if (minutesUntilClose.TotalMinutes < 15) { Console.WriteLine("Reached the end of trading window."); await ClosePositionAtMarket(); await polygonStreamingClient.DisconnectAsync(); } else { // Decide whether to buy or sell and submit orders. await HandleMinuteAgg(agg); } }; polygonStreamingClient.SubscribeMinuteAgg(symbol); }
/// <summary> /// Connects the client to the broker's remote servers /// </summary> public override void Connect() { if (IsConnected) { return; } _sockClient.ConnectAsync().SynchronouslyAwaitTask(); if (_handlesMarketData) { _polygonStreamingClient.ConnectAndAuthenticateAsync().SynchronouslyAwaitTask(); } _isConnected = true; // create new thread to manage disconnections and reconnections var connectionMonitorStartedEvent = new AutoResetEvent(false); _cancellationTokenSource = new CancellationTokenSource(); _connectionMonitorThread = new Thread(() => { connectionMonitorStartedEvent.Set(); var nextReconnectionAttemptSeconds = 1; try { while (!_cancellationTokenSource.IsCancellationRequested) { var isAlive = true; try { isAlive = _sockClient.IsAlive; } catch (Exception) { // ignored } if (isAlive && _connectionLost) { _connectionLost = false; nextReconnectionAttemptSeconds = 1; OnMessage(BrokerageMessageEvent.Reconnected("Connection with Alpaca server restored.")); } else if (!isAlive) { if (_connectionLost) { try { Thread.Sleep(TimeSpan.FromSeconds(nextReconnectionAttemptSeconds)); _sockClient.ConnectAsync().SynchronouslyAwaitTask(); } catch (Exception exception) { // double the interval between attempts (capped to 1 minute) nextReconnectionAttemptSeconds = Math.Min(nextReconnectionAttemptSeconds * 2, 60); Log.Error(exception); } } else { _connectionLost = true; OnMessage( BrokerageMessageEvent.Disconnected( "Connection with Alpaca server lost. " + "This could be because of internet connectivity issues. ")); } } Thread.Sleep(1000); } } catch (Exception exception) { Log.Error(exception); } }) { IsBackground = true }; _connectionMonitorThread.Start(); connectionMonitorStartedEvent.WaitOne(); }
public async Task Run() { alpacaTradingClient = Environments.Paper.GetAlpacaTradingClient(API_KEY, new SecretKey(API_SECRET)); polygonDataClient = Environments.Paper.GetPolygonDataClient(API_KEY); // Connect to Alpaca's websocket and listen for updates on our orders. alpacaStreamingClient = Environments.Paper.GetAlpacaStreamingClient(API_KEY, API_SECRET); alpacaStreamingClient.ConnectAndAuthenticateAsync().Wait(); alpacaStreamingClient.OnTradeUpdate += HandleTradeUpdate; // First, cancel any existing orders so they don't impact our buying power. var orders = await alpacaTradingClient.ListOrdersAsync(); foreach (var order in orders) { await alpacaTradingClient.DeleteOrderAsync(order.OrderId); } // Figure out when the market will close so we can prepare to sell beforehand. var calendars = (await alpacaTradingClient.ListCalendarAsync(DateTime.Today)).ToList(); var calendarDate = calendars.First().TradingDate; var closingTime = calendars.First().TradingCloseTime; closingTime = new DateTime(calendarDate.Year, calendarDate.Month, calendarDate.Day, closingTime.Hour, closingTime.Minute, closingTime.Second); var today = DateTime.Today; // Get the first group of bars from today if the market has already been open. var bars = await polygonDataClient.ListMinuteAggregatesAsync(symbol, 1, today, today.AddDays(1)); var lastBars = bars.Items.Skip(Math.Max(0, bars.Items.Count() - 20)); foreach (var bar in lastBars) { if (bar.Time.Date == today) { closingPrices.Add(bar.Close); } } Console.WriteLine("Waiting for market open..."); await AwaitMarketOpen(); Console.WriteLine("Market opened."); // Connect to Polygon's websocket and listen for price updates. polygonStreamingClient = Environments.Live.GetPolygonStreamingClient(API_KEY); polygonStreamingClient.ConnectAndAuthenticateAsync().Wait(); Console.WriteLine("Polygon client opened."); polygonStreamingClient.MinuteAggReceived += async(agg) => { // If the market's close to closing, exit position and stop trading. TimeSpan minutesUntilClose = closingTime - DateTime.UtcNow; if (minutesUntilClose.TotalMinutes < 15) { Console.WriteLine("Reached the end of trading window."); await ClosePositionAtMarket(); await polygonStreamingClient.DisconnectAsync(); } else { // Decide whether to buy or sell and submit orders. await HandleMinuteAgg(agg); } }; polygonStreamingClient.SubscribeSecondAgg(symbol); }