public async Task <IEnumerable <Core.Model.Symbol> > GetSymbolsAsync(CancellationToken cancellationToken) { var binanceApi = new BinanceApi(); var result = await binanceApi.GetSymbolsAsync(cancellationToken).ConfigureAwait(false); var symbols = result.Select(s => new Core.Model.Symbol { Name = $"{s.BaseAsset.Symbol}{s.QuoteAsset.Symbol}", ExchangeSymbol = $"{s.BaseAsset.Symbol}{s.QuoteAsset.Symbol}", Exchange = Exchange.Binance, NotionalMinimumValue = s.NotionalMinimumValue, BaseAsset = new Core.Model.Asset { Symbol = s.BaseAsset.Symbol, Precision = s.BaseAsset.Precision }, Price = new Core.Model.InclusiveRange { Increment = s.Price.Increment /*, Minimum = s.Price.Minimum, Maximum = s.Price.Maximum*/ }, // HACK : remove Price Min and Max because it realtime calcs hits performance. Quantity = new Core.Model.InclusiveRange { Increment = s.Quantity.Increment, Minimum = s.Quantity.Minimum, Maximum = s.Quantity.Maximum }, QuoteAsset = new Core.Model.Asset { Symbol = s.QuoteAsset.Symbol, Precision = s.QuoteAsset.Precision }, Status = (Core.Model.SymbolStatus)s.Status, IsIcebergAllowed = s.IsIcebergAllowed, OrderTypes = (IEnumerable <Core.Model.OrderType>)s.OrderTypes }).ToList(); return(symbols); }
private async void FormSymbolList_LoadAsync(object sender, EventArgs e) { var api = new BinanceApi(); var symbols = await api.GetSymbolsAsync(); symbolList = symbols /*.Where(x => x.QuoteAsset.Symbol == "BTC")*/.OrderBy(x => x.BaseAsset.Symbol).Select(x => x.ToString()).ToList(); comboBoxSymbols.DataSource = symbols /*.Where(x => x.QuoteAsset.Symbol == "BTC")*/.OrderBy(x => x.BaseAsset.Symbol).Select(x => x.BaseAsset.Symbol + " - " + x.QuoteAsset.Symbol).ToList(); }
private static async Task Main() { var assets = new List <Asset>(); var api = new BinanceApi(); // Get the current timestamp. var timestamp = await api.GetTimestampAsync(); // Get latest currency pairs (symbols). var symbols = (await api.GetSymbolsAsync()).ToList(); // Get assets. foreach (var symbol in symbols) { if (!assets.Contains(symbol.BaseAsset)) { assets.Add(symbol.BaseAsset); } if (!assets.Contains(symbol.QuoteAsset)) { assets.Add(symbol.QuoteAsset); } } // Read the symbol template file. var lines = (await File.ReadAllLinesAsync("Symbol.template.cs")).ToList(); // Replace remarks. var index = lines.FindIndex(l => l.Contains("<remarks></remarks>")); lines[index] = $" /// <remarks>File generated by {nameof(BinanceCodeGenerator)} tool.</remarks>"; // Replace timestamp. index = lines.FindIndex(l => l.Contains("<<insert timestamp>>")); lines[index] = $" public static readonly long LastUpdateAt = {timestamp};"; index = lines.FindIndex(l => l.Contains("<<insert symbols>>")); lines.RemoveAt(index); // Sort symbols. symbols.Sort(); var groups = symbols.GroupBy(s => s.QuoteAsset); // Insert definition for each currency pair (symbol). foreach (var group in groups) { lines.Insert(index++, $" // {group.First().QuoteAsset}"); foreach (var symbol in group) { lines.Insert(index++, $" public static Symbol {symbol.BaseAsset}_{symbol.QuoteAsset} => Cache.Get(\"{symbol.BaseAsset}{symbol.QuoteAsset}\");"); } lines.Insert(index++, string.Empty); } lines.RemoveAt(index); index = lines.FindIndex(l => l.Contains("<<insert symbol definitions>>")); lines.RemoveAt(index); foreach (var symbol in symbols) { var orderTypes = string.Join(",", symbol.OrderTypes.Select(_ => "OrderType." + _)); lines.Insert(index++, $" new Symbol(SymbolStatus.{symbol.Status}, Asset.{symbol.BaseAsset}, Asset.{symbol.QuoteAsset}, ({Convert.ToString(symbol.Quantity.Minimum, CultureInfo.InvariantCulture)}m, {Convert.ToString(symbol.Quantity.Maximum, CultureInfo.InvariantCulture)}m, {Convert.ToString(symbol.Quantity.Increment, CultureInfo.InvariantCulture)}m), ({Convert.ToString(0, CultureInfo.InvariantCulture)}m, {Convert.ToString(0, CultureInfo.InvariantCulture)}m, {Convert.ToString(symbol.Price.Increment, CultureInfo.InvariantCulture)}m), {Convert.ToString(symbol.NotionalMinimumValue, CultureInfo.InvariantCulture)}m, {symbol.IsIcebergAllowed.ToString().ToLowerInvariant()}, new List<OrderType> {{{orderTypes}}}),"); } // Save the generated source code (replacing original). await File.WriteAllLinesAsync("../../../../../src/Binance/Symbol.cs", lines); // Read the asset template file. lines = (await File.ReadAllLinesAsync("Asset.template.cs")).ToList(); // Replace remarks. index = lines.FindIndex(l => l.Contains("<remarks></remarks>")); lines[index] = $" /// <remarks>File generated by {nameof(BinanceCodeGenerator)} tool.</remarks>"; // Replace timestamp. index = lines.FindIndex(l => l.Contains("<<insert timestamp>>")); lines[index] = $" public static readonly long LastUpdateAt = {timestamp};"; index = lines.FindIndex(l => l.Contains("<<insert assets>>")); lines.RemoveAt(index); // Sort assets. assets.Sort(); // Insert definition for each asset. foreach (var asset in assets) { lines.Insert(index++, $" public static Asset {asset} => Cache.Get(\"{asset}\");"); } index = lines.FindIndex(l => l.Contains("<<insert asset definitions>>")); lines.RemoveAt(index); foreach (var asset in assets) { lines.Insert(index++, $" new Asset(\"{asset}\", {Convert.ToString(asset.Precision, CultureInfo.InvariantCulture)}),"); } // Save the generated source code (replacing original). await File.WriteAllLinesAsync("../../../../../src/Binance/Asset.cs", lines); Console.WriteLine("Successfully generated new Symbol.cs and Asset.cs files."); Console.WriteLine(); Console.WriteLine(" ...press any key to close window."); Console.ReadKey(true); }
public override Boolean Initialize() { m_MessagePump.Signal(Resources.ExchangeInitialization); try { BinanceStatus status = m_Api.GetSystemStatusAsync().Result; if (status == BinanceStatus.Maintenance) { throw new Exception(Resources.ServerMaintenance); } TimeSpan delta = TimeSpan.Zero; for (Int32 i = 0; i < 5; ++i) { DateTime now = DateTime.Now; Boolean result = m_Api.PingAsync().Result; if (!result) { throw new Exception(Resources.ServerPing); } delta += DateTime.Now - now; } m_MessagePump.Signal(Utilities.FormatMessage(Resources.MessageConnectivityOK, delta.Milliseconds / 5)); } catch (Exception e) { m_MessagePump.Signal(Utilities.FormatMessage(Resources.ConnectivityKO, Utilities.GetExceptionMessage(e))); return(false); } try { m_User = new BinanceApiUser(Config.KeyApi, Config.KeySecret); m_MessagePump.Signal(Resources.LoginOK); } catch (Exception e) { m_MessagePump.Signal(Utilities.FormatMessage(Resources.LoginKO, Utilities.GetExceptionMessage(e))); return(false); } try { UpdateBalances(m_Api.GetAccountInfoAsync(m_User).Result); m_UserDataWebSocket = new UserDataWebSocketManager(); m_UserDataWebSocket.SubscribeAsync <AccountUpdateEventArgs>(m_User, x => UpdateBalances(x.AccountInfo)).Wait(); m_UserDataWebSocket.WaitUntilWebSocketOpenAsync().Wait(); if (m_Balances.Count == 0) { m_MessagePump.Signal(Resources.BalancesOK0); } else { m_MessagePump.Signal(Utilities.FormatMessage(Resources.BalancesKO, m_Balances.Count, (m_Balances.Count == 1 ? String.Empty : "s"))); foreach (KeyValuePair <String, Decimal> balance in m_Balances.OrderBy(x => x.Key)) { m_MessagePump.Signal($" - {balance.Value:F8} {balance.Key}"); } } } catch (Exception e) { m_MessagePump.Signal(Utilities.FormatMessage(Resources.BalancesKO, Utilities.GetExceptionMessage(e))); return(false); } try { Dictionary <String, Int32> symbolsData = new Dictionary <String, Int32>(); HashSet <String> assets = new HashSet <String>(); foreach (Symbol symbol in m_Api.GetSymbolsAsync().Result) { if (symbol.Status != SymbolStatus.Trading) { continue; } String baseAsset = symbol.BaseAsset; String quoteAsset = symbol.BaseAsset; String name = symbol.ToString(); if ((Config.TradingWhitelist.Count > 0) && (!Config.TradingWhitelist.Contains(baseAsset) || !Config.TradingWhitelist.Contains(quoteAsset))) { continue; } String mininumQuantity = symbol.Quantity.Minimum.ToString(CultureInfo.InvariantCulture); Int32 dustDecimals = Math.Max(0, mininumQuantity.IndexOf("1", StringComparison.OrdinalIgnoreCase) - 1); assets.Add(baseAsset); assets.Add(quoteAsset); symbolsData[name] = dustDecimals; } ConcurrentBag <Trade> trades = new ConcurrentBag <Trade>(); Parallel.ForEach(assets.SelectMany(x => assets, (a1, a2) => new { Asset1 = a1, Asset2 = a2 }), pair => { if (pair.Asset1 == pair.Asset2) { return; } TradeLeg leg1 = BuildTradeLeg(symbolsData, Config.InvestmentBaseAsset, pair.Asset1); if ((leg1 == null) || (leg1.Position != Config.TradingPositions[0])) { return; } TradeLeg leg2 = BuildTradeLeg(symbolsData, pair.Asset1, pair.Asset2); if ((leg2 == null) || (leg2.Position != Config.TradingPositions[1])) { return; } TradeLeg leg3 = BuildTradeLeg(symbolsData, pair.Asset2, Config.InvestmentBaseAsset); if ((leg3 == null) || (leg3.Position != Config.TradingPositions[2])) { return; } trades.Add(new Trade(leg1, leg2, leg3)); }); if (trades.Count == 0) { throw new Exception(Resources.NoTriangularRelationships); } m_Trades.AddRange(trades); m_MessagePump.Signal(Utilities.FormatMessage(Resources.TradesOK, m_Trades.Count, (m_Trades.Count == 1 ? String.Empty : "s"))); } catch (Exception e) { m_MessagePump.Signal(Utilities.FormatMessage(Resources.TradesKO, Utilities.GetExceptionMessage(e))); return(false); } try { List <String> symbols = m_Trades.Select(x => x.Leg1.Symbol) .Union(m_Trades.Select(x => x.Leg2.Symbol)) .Union(m_Trades.Select(x => x.Leg3.Symbol)) .Distinct().OrderBy(x => x).ToList(); foreach (String symbol in symbols) { m_OrderBooks[symbol] = new SortedOrderBook(m_Api.GetOrderBookAsync(symbol, Config.DataSize).Result); m_OrderBooksCache[symbol] = new DepthWebSocketCache(); m_OrderBooksCache[symbol].Error += (sender, e) => m_OrderBooks[symbol].Invalid = true; m_OrderBooksCache[symbol].OutOfSync += (sender, e) => m_OrderBooks[symbol].Invalid = true; m_OrderBooksCache[symbol].Subscribe(symbol, e => m_OrderBooks[symbol] = new SortedOrderBook(e.OrderBook)); Thread.Sleep(Config.DataStagger); } m_MessagePump.Signal(Utilities.FormatMessage(Resources.OrderBooksOK, symbols.Count, (symbols.Count == 1 ? String.Empty : "s"))); m_MessagePump.Signal(String.Empty); m_Initialized = true; return(true); } catch (Exception e) { m_MessagePump.Signal(Utilities.FormatMessage(Resources.OrderBooksKO, Utilities.GetExceptionMessage(e))); return(false); } }
private static async Task Main() { var assets = new List <Asset>(); long timestamp; List <Symbol> symbols; var api = new BinanceApi(); // Get the current timestamp. timestamp = await api.GetTimestampAsync(); // Get latest currency pairs (symbols). symbols = (await api.GetSymbolsAsync()).ToList(); // Get assets. foreach (var symbol in symbols) { if (!assets.Contains(symbol.BaseAsset)) { assets.Add(symbol.BaseAsset); } if (!assets.Contains(symbol.QuoteAsset)) { assets.Add(symbol.QuoteAsset); } } // Read the symbol template file. var lines = (await File.ReadAllLinesAsync("Symbol.template.cs")).ToList(); // Replace timestamp. var index = lines.FindIndex(l => l.Contains("<<insert timestamp>>")); lines[index] = $" public static readonly long LastUpdateAt = {timestamp};"; index = lines.FindIndex(l => l.Contains("<<insert symbols>>")); lines.RemoveAt(index); // Sort symbols. symbols.Sort(); var groups = symbols.GroupBy(s => s.QuoteAsset); // Insert definition for each currency pair (symbol). foreach (var group in groups) { lines.Insert(index++, $" // {group.First().QuoteAsset}"); foreach (var symbol in group) { lines.Insert(index++, $" public static readonly Symbol {symbol.BaseAsset}_{symbol.QuoteAsset} = new Symbol(Asset.{symbol.BaseAsset}, Asset.{symbol.QuoteAsset}, {symbol.BaseMinQuantity}m, {symbol.BaseMaxQuantity}m, {symbol.QuoteIncrement}m);"); } lines.Insert(index++, string.Empty); } lines.RemoveAt(index); index = lines.FindIndex(l => l.Contains("<<insert symbol definitions>>")); lines.RemoveAt(index); foreach (var symbol in symbols) { lines.Insert(index++, $" {{ \"{symbol}\", {symbol.BaseAsset}_{symbol.QuoteAsset} }},"); } // Save the generated source code (replacing original). await File.WriteAllLinesAsync("../../src/Binance/Symbol.cs", lines); // Read the asset template file. lines = (await File.ReadAllLinesAsync("Asset.template.cs")).ToList(); // Replace timestamp. index = lines.FindIndex(l => l.Contains("<<insert timestamp>>")); lines[index] = $" public static readonly long LastUpdateAt = {timestamp};"; index = lines.FindIndex(l => l.Contains("<<insert assets>>")); lines.RemoveAt(index); // Sort assets. assets.Sort(); // Insert definition for each asset. foreach (var asset in assets) { lines.Insert(index++, $" public static readonly Asset {asset} = new Asset(\"{asset}\", {asset.Precision});"); } index = lines.FindIndex(l => l.Contains("<<insert asset definitions>>")); lines.RemoveAt(index); foreach (var asset in assets) { lines.Insert(index++, $" {{ \"{asset}\", {asset} }},"); } // Save the generated source code (replacing original). await File.WriteAllLinesAsync("../../src/Binance/Asset.cs", lines); Console.WriteLine(); Console.WriteLine(" ...press any key to close window."); Console.ReadKey(true); }