public async Task <OrderDto> PlaceOrderAsync(Instrument instrument, double price, double quantity, TradeSide side, OrderType orderType) { if (!ExchangeConfig.SupportedInstruments.ContainsKey(instrument)) { _logger.Log(LogLevel.Error, $"{ExchangeConfig.ExchangeName} does not support the {instrument} instrument"); return(null); } if (!ExchangeConfig.SupportedOrderTypes.ContainsKey(orderType)) { _logger.Log(LogLevel.Error, $"{ExchangeConfig.ExchangeName} does not support orders of type {orderType}"); return(null); } IRequest request = null; var ot = ExchangeConfig.SupportedOrderTypes[orderType]; switch (orderType) { case OrderType.Market: request = new PlaceMarketOrderRequest { Symbol = _exchangeApi.ToSymbol(instrument), OrderQty = quantity, Side = side.ToString(), OrderType = ot }; break; case OrderType.Limit: request = new PlaceLimitOrderRequest { Symbol = _exchangeApi.ToSymbol(instrument), OrderQty = quantity, Side = side.ToString(), Price = price, OrderType = ot }; break; case OrderType.LimitMarket: break; case OrderType.Stop: break; default: throw new ArgumentOutOfRangeException(nameof(orderType), orderType, null); } var channelPath = ExchangeConfig.SupportedRestChannels[ExchangeChannel.Order]; return(await _exchangeApi.PostAsync <OrderDto, OrderResponse>(channelPath, request)); }
public async Task <IActionResult> PlaceLimitOrder(PlaceLimitOrderRequest request) { var walletId = User.GetWalletId(); var result = await _validationService.ValidateLimitOrderAsync(walletId, request.AssetPairId, request.Side, request.Price, request.Volume); if (result != null) { throw HftApiException.Create(result.Code, result.Message).AddField(result.FieldName); } var order = new LimitOrderModel { Id = Guid.NewGuid().ToString(), AssetPairId = request.AssetPairId, ClientId = walletId, Price = (double)request.Price, CancelPreviousOrders = false, Volume = (double)Math.Abs(request.Volume), OrderAction = request.Side }; MeResponseModel response = await _matchingEngineClient.PlaceLimitOrderAsync(order); if (response == null) { throw HftApiException.Create(HftApiErrorCode.MeRuntime, "ME not available"); } (HftApiErrorCode code, string message) = response.Status.ToHftApiError(); if (code == HftApiErrorCode.Success) { return(Ok(ResponseModel <LimitOrderResponse> .Ok(new LimitOrderResponse { OrderId = response.TransactionId }))); } throw HftApiException.Create(code, message); }
public async Task Should_place_limit_order() { var balanceSetResponse = await _sandboxService.SetCurrencyBalance(new SandboxSetCurrencyBalanceRequest { Balance = 200, Currency = Currency.Usd }); ValidateRestResponse(balanceSetResponse); var request = new PlaceLimitOrderRequest { Lots = 1, Operation = OperationType.Buy, Price = 180 }; var response = await _orderService.PlaceLimitOrder("BBG000D9D830", request, CancellationToken.None); ValidateRestResponse(response); Assert.NotNull(response.Order); Assert.Equal(OrderStatus.Fill, response.Order.Status); }
public Task <LimitOrderResponse> PlaceLimitOrder(string figi, PlaceLimitOrderRequest request, CancellationToken cancellationToken = default) { return(_rest.Post <PlaceLimitOrderRequest, LimitOrderResponse>($"orders/limit-order?figi={figi}", request, cancellationToken)); }