Example #1
0
        public override async Task <ExecuteMarketOrderResponse> ExecuteMarketOrder(MarketOrderRequest request, ServerCallContext context)
        {
            if (!_settings.InstrumentMappings.TryGetValue(request.AssetPair, out var assetPairId))
            {
                _logger.LogWarning("Asset pair not found. {assetPairId}", request.AssetPair);

                return(new ExecuteMarketOrderResponse
                {
                    Error = ErrorCode.Critical,
                    ErrorMessage = "Asset pair not found"
                });
            }

            var     orderId = $"{((int)request.TradeTypeTag).ToString()}{request.ComponentTag}{Guid.NewGuid().ToString().Remove(0, 1 + request.ComponentTag.Length)}";
            decimal size    = decimal.Parse(request.Size, CultureInfo.InvariantCulture);

            var response = await _b2C2RestClient.OrderAsync(new OrderRequest
            {
                ClientOrderId = orderId,
                Instrument    = assetPairId,
                Side          = size > 0
                    ? Side.Buy
                    : Side.Sell,
                Quantity   = Math.Abs(size),
                OrderType  = OrderType.MKT,
                ValidUntil = DateTime.UtcNow.AddSeconds(3)
            });

            var result = new ExecuteMarketOrderResponse
            {
                OrderId       = response.OrderId,
                RequestId     = response.ClientOrderId,
                AssetPairId   = request.AssetPair,
                Price         = response.ExecutedPrice.ToString(CultureInfo.InvariantCulture),
                FilledSize    = (response.Side == Side.Buy ? response.Quantity : -response.Quantity).ToString(CultureInfo.InvariantCulture),
                CancelledSize = "0",
                Timestamp     = response.Created.ToTimestamp(),
                Error         = ErrorCode.Ok
            };

            result.Trades.AddRange(MapTrades(response.Trades));

            return(result);
        }
        //[Fact]
        public async void OrderTest()
        {
            // arrange

            var orderRequest = new OrderRequest();

            orderRequest.ClientOrderId      = Guid.NewGuid().ToString();
            orderRequest.Instrument         = "BTCUSD.SPOT";
            orderRequest.Side               = Side.Buy;
            orderRequest.Quantity           = 0.01m;
            orderRequest.OrderType          = OrderType.MKT;
            orderRequest.ValidUntil         = DateTime.UtcNow.AddSeconds(10);
            orderRequest.AcceptableSlippage = 0;

            // act

            var orderResponse = await _restClient.OrderAsync(orderRequest);

            // assert

            Assert.NotNull(orderResponse);
            Assert.NotEmpty(orderResponse.OrderId);
            Assert.Equal(orderResponse.ClientOrderId, orderRequest.ClientOrderId);
            Assert.Equal(orderResponse.Instrument, orderRequest.Instrument);
            Assert.Equal(orderResponse.Side, orderRequest.Side);
            Assert.NotEqual(0, orderResponse.Price);
            Assert.NotEqual(default(decimal), orderResponse.ExecutedPrice);
            Assert.Equal(orderResponse.Quantity, orderRequest.Quantity);
            Assert.NotEqual(default(DateTime), orderResponse.Created);
            Assert.NotEmpty(orderResponse.Trades);

            var trade = orderResponse.Trades.Single();

            Assert.NotEmpty(trade.TradeId);
            Assert.NotEqual(default(string), trade.TradeId);
            Assert.Equal(trade.Instrument, orderRequest.Instrument);
            Assert.Equal(trade.Side, orderRequest.Side);
            Assert.NotEqual(default(decimal), trade.Price);
            Assert.Equal(trade.Quantity, orderRequest.Quantity);
            Assert.Equal(trade.Order, orderResponse.OrderId);
            Assert.NotEqual(orderResponse.Created, trade.Created);
            Assert.Null(trade.RfqId);
        }
        private async Task <ExternalTrade> ExecuteLimitOrderAsync(string assetPairId, decimal volume, decimal?price, Side side)
        {
            var startedAt = DateTime.UtcNow;

            string instrument = await GetInstrumentAsync(assetPairId);

            OrderResponse orderResponse = await WrapAsync(async() =>
            {
                var orderStartedAt = DateTime.UtcNow;

                var orderRequest = new OrderRequest();

                orderRequest.ClientOrderId = Guid.NewGuid().ToString();
                orderRequest.Side          = side;
                orderRequest.Instrument    = instrument;
                orderRequest.OrderType     = OrderType.MKT;
                orderRequest.Quantity      = volume;
                orderRequest.ValidUntil    = DateTime.UtcNow.AddSeconds(3);

                _log.Info("Order request", orderRequest);

                OrderResponse order = await _client.OrderAsync(orderRequest);

                var orderFinishedAt = DateTime.UtcNow;

                _log.Info("Order response", orderRequest);

                Trade orderTrade = order.Trades.Single();

                _log.Info("Order time", new
                {
                    AssetPairId     = assetPairId,
                    Volume          = volume,
                    TradeId         = orderTrade.TradeId,
                    ClientOrderId   = orderRequest.ClientOrderId,
                    OrderId         = order.OrderId,
                    OrderStartedAt  = orderStartedAt,
                    OrderFinishedAt = orderFinishedAt,
                    Latency         = (orderFinishedAt - orderStartedAt).TotalMilliseconds
                });

                return(order);
            });

            var finishedAt = DateTime.UtcNow;

            var trade = orderResponse.Trades.Single();

            var hedgingFinishedAt = DateTime.UtcNow;

            _log.Info("Total hedge trade time", new
            {
                TradeId              = trade.TradeId,
                TradeCreated         = trade.Created,
                OrderId              = orderResponse.OrderId,
                ClientOrderId        = orderResponse.ClientOrderId,
                OrderCreated         = orderResponse.Created,
                HedgeTradeStartedAt  = startedAt,
                HedgeTradeFinishedAt = finishedAt,
                HedgeTradeTotalTime  = (finishedAt - startedAt).TotalMilliseconds
            });

            PrometheusMetrics.HedgeB2C2OrderRequestLatency.Inc((finishedAt - startedAt).TotalMilliseconds);

            return(new ExternalTrade
            {
                Id = trade.TradeId,
                LimitOrderId = trade.Order,
                AssetPairId = trade.Instrument,
                Type = trade.Side == Side.Sell ? TradeType.Sell : TradeType.Buy,
                Time = trade.Created,
                Price = trade.Price,
                Volume = trade.Quantity,
                RequestId = trade.RfqId
            });
        }