Example #1
0
        private Task <decimal> CalculateUSDT(KeyValuePair <string, decimal> account, decimal ethUsdt)
        {
            var amount = 0m;

            // 如果持有币种为usdt
            if ("usdt".Equals(account.Key))
            {
                amount = account.Value;
            }
            else
            {
                // 如果该币在usdt交易区,则折算为usdt
                if (this.usdt.Contains(account.Key.ToUpper()))
                {
                    var depth = exchange.GetOrderBook(account.Key + "/usdt", 1);
                    var bids  = depth.Bids.OrderByDescending(a => a.Value.Price);
                    amount = account.Value * bids.ElementAt(0).Value.Price;
                }
                // 如果该币在eth交易区,则先折算为eth,再折算为usdt
                else if (this.eth.Contains(account.Key.ToUpper()))
                {
                    var depth = exchange.GetOrderBook(account.Key + "/eth", 1);
                    var bids  = depth.Bids.OrderByDescending(a => a.Value.Price);
                    amount += account.Value * bids.ElementAt(0).Value.Price *ethUsdt;
                }
            }
            return(Task.FromResult <decimal>(amount));
        }
Example #2
0
        static decimal GetFirstAsk(string market)
        {
            var depth = exchange.GetOrderBook(market, 1);
            var asks  = depth.Asks.OrderByDescending(a => a.Value.Price);

            return(asks.ElementAt(0).Value.Price);
        }
Example #3
0
        /// <summary>
        /// Get full order book bids and asks via web socket. This is efficient and will only use the order book deltas.
        /// </summary>
        /// <param name="callback">Callback of symbol, order book</param>
        /// <param name="maxCount">Max count of bids and asks - not all exchanges will honor this parameter</param>
        /// <param name="symbol">Ticker symbols or null/empty for all of them (if supported)</param>
        /// <returns>Web socket, call Dispose to close</returns>
        public static IDisposable GetOrderBookWebSocket(this IExchangeAPI api, Action <ExchangeOrderBook> callback, int maxCount = 20, params string[] symbols)
        {
            // Gets a delta socket for a collection of order books, then maintains a full order book.
            // The suggested way to use this is:
            // 1. Open this socket and begin buffering events you receive
            // 2. Get a depth snapshot of the order books you care about
            // 3. Drop any event where SequenceNumber is less than or equal to the snapshot last update id
            // Notes:
            // * Confirm with the Exchange's API docs whether the data in each event is the absolute quantity or differential quantity
            // * If the quantity is 0, remove the price level
            // * Receiving an event that removes a price level that is not in your local order book can happen and is normal.
            //

            Dictionary <string, ExchangeOrderBook> fullBooks = new Dictionary <string, ExchangeOrderBook>();

            void innerCallback(ExchangeOrderBook book)
            {
                // see if we have a full order book for the symbol
                if (!fullBooks.TryGetValue(book.Symbol, out ExchangeOrderBook fullBook))
                {
                    fullBooks[book.Symbol] = fullBook = api.GetOrderBook(book.Symbol, 1000);
                    fullBook.Symbol        = book.Symbol;
                }

                // update deltas as long as the full book is at or before the delta timestamp
                if (fullBook.SequenceId <= book.SequenceId)
                {
                    foreach (var ask in book.Asks)
                    {
                        if (ask.Value.Amount <= 0m || ask.Value.Price <= 0m)
                        {
                            fullBook.Asks.Remove(ask.Value.Price);
                        }
                        else
                        {
                            fullBook.Asks[ask.Value.Price] = ask.Value;
                        }
                    }
                    foreach (var bid in book.Bids)
                    {
                        if (bid.Value.Amount <= 0m || bid.Value.Price <= 0m)
                        {
                            fullBook.Bids.Remove(bid.Value.Price);
                        }
                        else
                        {
                            fullBook.Bids[bid.Value.Price] = bid.Value;
                        }
                    }
                    fullBook.SequenceId = book.SequenceId;
                }
                callback(fullBook);
            };

            return(api.GetOrderBookDeltasWebSocket(innerCallback, maxCount, symbols));
        }
Example #4
0
        /// <summary>Get full order book bids and asks via web socket. This is efficient and will
        /// only use the order book deltas (if supported by the exchange).</summary>
        /// <param name="callback">Callback containing full order book</param>
        /// <param name="maxCount">Max count of bids and asks - not all exchanges will honor this
        /// parameter</param>
        /// <param name="symbols">Ticker symbols or null/empty for all of them (if supported)</param>
        /// <returns>Web socket, call Dispose to close</returns>
        public static IWebSocket GetOrderBookWebSocket(this IExchangeAPI api, Action <ExchangeOrderBook> callback, int maxCount = 20, params string[] symbols)
        {
            // Notes:
            // * Confirm with the Exchange's API docs whether the data in each event is the absolute quantity or differential quantity
            // * Receiving an event that removes a price level that is not in your local order book can happen and is normal.
            var fullBooks = new ConcurrentDictionary <string, ExchangeOrderBook>();

            void innerCallback(ExchangeOrderBook freshBook)
            {
                bool foundFullBook = fullBooks.TryGetValue(freshBook.Symbol, out ExchangeOrderBook fullOrderBook);

                switch (api.Name)
                {
                // Fetch an initial book the first time and apply deltas on top
                case ExchangeName.Bittrex:
                case ExchangeName.Binance:
                case ExchangeName.Poloniex:
                {
                    // If we don't have an initial order book for this symbol, fetch it
                    if (!foundFullBook)
                    {
                        fullBooks[freshBook.Symbol] = fullOrderBook = api.GetOrderBook(freshBook.Symbol, 1000);
                        fullOrderBook.Symbol        = freshBook.Symbol;
                    }

                    // update deltas as long as the full book is at or before the delta timestamp
                    if (fullOrderBook.SequenceId <= freshBook.SequenceId)
                    {
                        ApplyDelta(freshBook.Asks, fullOrderBook.Asks);
                        ApplyDelta(freshBook.Bids, fullOrderBook.Bids);
                        fullOrderBook.SequenceId = freshBook.SequenceId;
                    }

                    break;
                }

                // First response from exchange will be the full order book.
                // Subsequent updates will be deltas
                case ExchangeName.BitMEX:
                case ExchangeName.Okex:
                {
                    if (!foundFullBook)
                    {
                        fullBooks[freshBook.Symbol] = fullOrderBook = freshBook;
                        fullOrderBook.Symbol        = freshBook.Symbol;
                    }
                    else
                    {
                        ApplyDelta(freshBook.Asks, fullOrderBook.Asks);
                        ApplyDelta(freshBook.Bids, fullOrderBook.Bids);
                    }

                    break;
                }

                // Websocket always returns full order book
                case ExchangeName.Huobi:
                {
                    fullBooks[freshBook.Symbol] = fullOrderBook = freshBook;
                    break;
                }
                }

                callback(fullOrderBook);
            }

            IWebSocket socket = api.GetOrderBookDeltasWebSocket(innerCallback, maxCount, symbols);

            socket.Connected += (s) =>
            {
                // when we re-connect, we must invalidate the order books, who knows how long we were disconnected
                //  and how out of date the order books are
                fullBooks.Clear();
            };
            return(socket);
        }