/// <summary> /// Initializes a new instance of the <see cref="OrderLogGenerator"/>. /// </summary> /// <param name="securityId">The identifier of the instrument, for which data shall be generated.</param> /// <param name="tradeGenerator">Tick trades generator using random method.</param> public OrderLogGenerator(SecurityId securityId, TradeGenerator tradeGenerator) : base(securityId) { //_lastOrderPrice = startPrice; TradeGenerator = tradeGenerator ?? throw new ArgumentNullException(nameof(tradeGenerator)); IdGenerator = new IncrementalIdGenerator(); }
/// <summary> /// Создать копию генератора. /// </summary> /// <returns>Копия.</returns> public override MarketDataGenerator Clone() { return(new OrderLogGenerator(SecurityId, (TradeGenerator)TradeGenerator.Clone()) { _lastOrderPrice = _lastOrderPrice, IdGenerator = IdGenerator }); }
/// <summary> /// Обработать сообщение. /// </summary> /// <param name="message">Сообщение.</param> /// <returns>Результат обработки. Если будет возрвщено <see langword="null"/>, /// то генератору пока недостаточно данных для генерации нового сообщения.</returns> public override Message Process(Message message) { if (message.Type == MessageTypes.Security) { TradeGenerator.Process(message); } return(base.Process(message)); }
/// <summary> /// Удалить генератор сделок, ранее зарегистрированный через <see cref="RegisterTrades"/>. /// </summary> /// <param name="generator">Генератор сделок.</param> public void UnRegisterTrades(TradeGenerator generator) { if (generator == null) { throw new ArgumentNullException("generator"); } _marketDataAdapter.TradeGenerators.Remove(generator.SecurityId); UnRegisterTrades(FindSecurity(generator.SecurityId)); }
/// <summary> /// Создать <see cref="OrderLogGenerator"/>. /// </summary> /// <param name="securityId">Идентификатор инструмента, для которого необходимо генерировать данные.</param> /// <param name="tradeGenerator">Генератор тиковых сделок случайным методом.</param> public OrderLogGenerator(SecurityId securityId, TradeGenerator tradeGenerator) : base(securityId) { if (tradeGenerator == null) throw new ArgumentNullException("tradeGenerator"); //_lastOrderPrice = startPrice; TradeGenerator = tradeGenerator; IdGenerator = new IncrementalIdGenerator(); }
/// <summary> /// Создать <see cref="OrderLogGenerator"/>. /// </summary> /// <param name="securityId">Идентификатор инструмента, для которого необходимо генерировать данные.</param> /// <param name="tradeGenerator">Генератор тиковых сделок случайным методом.</param> public OrderLogGenerator(SecurityId securityId, TradeGenerator tradeGenerator) : base(securityId) { if (tradeGenerator == null) { throw new ArgumentNullException("tradeGenerator"); } //_lastOrderPrice = startPrice; TradeGenerator = tradeGenerator; IdGenerator = new IncrementalIdGenerator(); }
/// <summary> /// Инициализировать состояние генератора. /// </summary> public override void Init() { TradeGenerator.Init(); base.Init(); }
/// <summary> /// Обработать сообщение. /// </summary> /// <param name="message">Сообщение.</param> /// <returns>Результат обработки. Если будет возрвщено <see langword="null"/>, /// то генератору пока недостаточно данных для генерации нового сообщения.</returns> protected override Message OnProcess(Message message) { DateTimeOffset time; switch (message.Type) { case MessageTypes.Level1Change: { var l1Msg = (Level1ChangeMessage)message; var value = l1Msg.Changes.TryGetValue(Level1Fields.LastTradePrice); if (value != null) { _lastOrderPrice = (decimal)value; } TradeGenerator.Process(message); time = l1Msg.ServerTime; break; } case MessageTypes.Execution: { var execMsg = (ExecutionMessage)message; switch (execMsg.ExecutionType) { case ExecutionTypes.Tick: _lastOrderPrice = execMsg.GetTradePrice(); break; default: return(null); } time = execMsg.ServerTime; break; } case MessageTypes.Time: { var timeMsg = (TimeMessage)message; time = timeMsg.ServerTime; break; } default: return(null); } if (!IsTimeToGenerate(time)) { return(null); } // TODO более реалистичную генерацию, так как сейчас объемы, цены и сделки c потолка var action = RandomGen.GetInt(0, 5); var isNew = action < 3 || _activeOrders.IsEmpty(); ExecutionMessage item; if (isNew) { var priceStep = SecurityDefinition.PriceStep ?? 0.01m; _lastOrderPrice += RandomGen.GetInt(-MaxPriceStepCount, MaxPriceStepCount) * priceStep; if (_lastOrderPrice <= 0) { _lastOrderPrice = priceStep; } item = new ExecutionMessage { OrderId = IdGenerator.GetNextId(), SecurityId = SecurityId, ServerTime = time, OrderState = OrderStates.Active, Volume = Volumes.Next(), Side = RandomGen.GetEnum <Sides>(), Price = _lastOrderPrice, ExecutionType = ExecutionTypes.OrderLog, }; _activeOrders.Enqueue((ExecutionMessage)item.Clone()); } else { var activeOrder = _activeOrders.Peek(); item = (ExecutionMessage)activeOrder.Clone(); item.ServerTime = time; var isMatched = action == 5; ExecutionMessage trade = null; if (isMatched) { trade = (ExecutionMessage)TradeGenerator.Process(message); } if (isMatched && trade != null) { item.Volume = RandomGen.GetInt(1, (int)activeOrder.GetVolume()); item.TradeId = trade.TradeId; item.TradePrice = trade.TradePrice; item.TradeStatus = trade.TradeStatus; // TODO //quote.Trade = TradeGenerator.Generate(time); //item.Volume = activeOrder.Volume; //if (item.Side == Sides.Buy && quote.Trade.Price > quote.Order.Price) // item.TradePrice = item.Price; //else if (item.Side == Sides.Sell && quote.Trade.Price < quote.Order.Price) // item.TradePrice = item.Price; activeOrder.Volume -= item.Volume; if (activeOrder.Volume == 0) { item.OrderState = OrderStates.Done; _activeOrders.Dequeue(); } else { item.OrderState = OrderStates.Active; } } else { item.OrderState = OrderStates.Done; item.IsCancelled = true; _activeOrders.Dequeue(); } } LastGenerationTime = time; return(item); }
/// <summary> /// Удалить генератор сделок, ранее зарегистрированный через <see cref="RegisterTrades"/>. /// </summary> /// <param name="generator">Генератор сделок.</param> public void UnRegisterTrades(TradeGenerator generator) { SendInGeneratorMessage(generator, false); }
/// <summary> /// Зарегистрировать генератор сделок. /// </summary> /// <param name="generator">Генератор сделок.</param> public void RegisterTrades(TradeGenerator generator) { SendInGeneratorMessage(generator, true); }
/// <summary> /// To delete the trades generator, registered earlier through <see cref="RegisterTrades"/>. /// </summary> /// <param name="generator">The trades generator.</param> public void UnRegisterTrades(TradeGenerator generator) { SendInGeneratorMessage(generator, false); }
/// <summary> /// To register the trades generator. /// </summary> /// <param name="generator">The trades generator.</param> public void RegisterTrades(TradeGenerator generator) { SendInGeneratorMessage(generator, true); }
public void UnRegisterTrades(TradeGenerator generator) => UnSubscribeGenerator(generator);
/// <summary> /// To register the trades generator. /// </summary> /// <param name="generator">The trades generator.</param> /// <returns>Subscription.</returns> //[Obsolete("Uses custom adapter implementation.")] public Subscription RegisterTrades(TradeGenerator generator) => SubscribeGenerator(generator);