internal List <HiddenOrderEntry> GetStopOrders( string user, string accountId, string instrument, OrderSide orderSide) { return(HiddenOrders.Find(order => order.User.Equals(user) && order.AccountId.Equals(accountId) && order.Instrument.Equals(instrument) && order.Side == orderSide ).ToList()); }
public object FindOpenOrderCreatedByVersionNumber(long cancelOrderCreatedOnVersionNumber) { var targetOrder = OrderBook.Find( Builders <OrderBookEntry> .Filter.Eq(e => e.CreatedOnVersionId, cancelOrderCreatedOnVersionNumber) ).SingleOrDefault(); if (targetOrder != null) { return(targetOrder); } else { // There has to be one or the other var hiddenOrder = HiddenOrders.Find( Builders <HiddenOrderEntry> .Filter.Eq(e => e.CreatedOnVersionId, cancelOrderCreatedOnVersionNumber) ).Single(); return(hiddenOrder); } }
/// <summary> /// Cancels an active order, inserting a relevant order history entry. /// </summary> /// <param name="cancelOrderCreatedOnVersionNumber">Version number of creation of the order to be canceled</param> /// <param name="orderHistoryTime">Time of the cancellation event</param> /// <param name="openOrder">Found open order</param> /// <returns>Remaining unmatched order amount of paid coin depending on side</returns> internal decimal CancelOrderByCreatedOnVersionNumber( long cancelOrderCreatedOnVersionNumber, DateTime orderHistoryTime, out object openOrder) { decimal remainingUnmatchedAmount; openOrder = FindOpenOrderCreatedByVersionNumber(cancelOrderCreatedOnVersionNumber); if (openOrder is OrderBookEntry limitOrder) { InsertOrderHistoryEntry(limitOrder.FilledQty, limitOrder, OrderStatus.Cancelled, orderHistoryTime); remainingUnmatchedAmount = limitOrder.Qty - limitOrder.FilledQty; if (limitOrder.Side == OrderSide.Buy) { remainingUnmatchedAmount *= limitOrder.LimitPrice; } OrderBook.DeleteOne( Builders <OrderBookEntry> .Filter.Eq(e => e.Id, limitOrder.Id) ); } else if (openOrder is HiddenOrderEntry stopOrder) { InsertOrderHistoryEntry(stopOrder, OrderStatus.Cancelled, orderHistoryTime); remainingUnmatchedAmount = stopOrder.Qty; if (stopOrder.Side == OrderSide.Buy) { remainingUnmatchedAmount *= stopOrder.StopPrice; } HiddenOrders.DeleteOne( Builders <HiddenOrderEntry> .Filter.Eq(e => e.Id, stopOrder.Id) ); } else { throw new Exception( $"Couldn't cancel order created on version number {cancelOrderCreatedOnVersionNumber}, as there was no such order open"); } return(remainingUnmatchedAmount); }
internal void CreateOrder(CreateOrderEventEntry createOrder) { _logger.LogDebug("Called create order @ version number " + createOrder.VersionNumber); switch (createOrder.Type) { case OrderType.Limit: var limitOrder = new OrderBookEntry { EntryTime = createOrder.EntryTime, CreatedOnVersionId = createOrder.VersionNumber, User = createOrder.User, AccountId = createOrder.AccountId, Instrument = createOrder.Instrument, Qty = createOrder.Qty, Side = createOrder.Side, FilledQty = 0m, LimitPrice = createOrder.LimitPrice.Value, // TODO from stop loss and take profit //ChildrenIds DurationType = createOrder.DurationType, Duration = createOrder.Duration, }; OrderBook.InsertOne(limitOrder); break; case OrderType.Stop: var stopOrder = new HiddenOrderEntry { EntryTime = createOrder.EntryTime, CreatedOnVersionId = createOrder.VersionNumber, User = createOrder.User, AccountId = createOrder.AccountId, Instrument = createOrder.Instrument, Qty = createOrder.Qty, Side = createOrder.Side, StopPrice = createOrder.StopPrice.Value, // TODO from stop loss and take profit //ChildrenIds DurationType = createOrder.DurationType, Duration = createOrder.Duration, }; HiddenOrders.InsertOne(stopOrder); break; case OrderType.Market: OrderHistory.InsertOne( new OrderHistoryEntry { CreateTime = createOrder.EntryTime, CloseTime = createOrder.EntryTime, User = createOrder.User, AccountId = createOrder.AccountId, Instrument = createOrder.Instrument, Qty = createOrder.Qty, Side = createOrder.Side, // Closed market order Type = OrderType.Market, // The market order will be filled by the following match orders FilledQty = createOrder.FilledMarketOrderQty, // The most expensive accepted limit price will be shown to the user LimitPrice = createOrder.LimitPrice.Value, StopPrice = null, // TODO from stop loss and take profit //ChildrenIds DurationType = createOrder.DurationType, Duration = createOrder.Duration, Status = OrderStatus.Filled, } ); break; default: throw new ArgumentOutOfRangeException(nameof(createOrder.Type)); } _logger.LogDebug("Persisted create order @ version number " + createOrder.VersionNumber); }