private static Type GetDbType(Level1Fields field) { switch (field) { case Level1Fields.LastTrade: case Level1Fields.BestBid: case Level1Fields.BestAsk: return(null); case Level1Fields.BidsCount: case Level1Fields.AsksCount: case Level1Fields.TradesCount: case Level1Fields.State: return(typeof(int)); case Level1Fields.LastTradeId: return(typeof(long)); case Level1Fields.LastTradeOrigin: return(typeof(int?)); case Level1Fields.BestBidTime: case Level1Fields.BestAskTime: case Level1Fields.LastTradeTime: return(typeof(DateTimeOffset)); default: return(typeof(decimal)); } }
private static void ApplyCellStyle(ExcelWorker worker, Level1Fields field, int column) { switch (field) { case Level1Fields.LastTrade: case Level1Fields.BestAsk: case Level1Fields.BestBid: break; case Level1Fields.LastTradeId: case Level1Fields.BidsCount: case Level1Fields.AsksCount: case Level1Fields.TradesCount: worker.SetStyle(column, typeof(long)); break; case Level1Fields.LastTradeTime: case Level1Fields.BestAskTime: case Level1Fields.BestBidTime: worker.SetStyle(column, typeof(DateTimeOffset)); break; default: worker.SetStyle(column, typeof(decimal)); break; } }
private IEnumerable <CandleMessage> ProcessCandlePart(Level1Fields part, CandleMessage message) { _transform.Part = part; _transform.Process(message); return(_builder.Process(this, _transform)); }
/// <inheritdoc /> public object GetSecurityValue(Security security, Level1Fields field) { if (security == null) { throw new ArgumentNullException(nameof(security)); } return(SafeGetConnector().GetSecurityValue(security, field)); }
/// <summary> /// To get market data value for the strategy instrument. /// </summary> /// <typeparam name="T">The type of the market data field value.</typeparam> /// <param name="strategy">Strategy.</param> /// <param name="field">Market-data field.</param> /// <returns>The field value. If no data, the <see langword="null" /> will be returned.</returns> public static T GetSecurityValue <T>(this Strategy strategy, Level1Fields field) { if (strategy == null) { throw new ArgumentNullException(nameof(strategy)); } return(strategy.GetSecurityValue <T>(strategy.Security, field)); }
private static void ApplyCellStyle(ExcelWorker worker, Level1Fields field, int column) { var type = field.ToType(); if (type != null && !type.IsEnum) { worker.SetStyle(column, type); } }
/// <inheritdoc /> public object GetSecurityValue(Security security, Level1Fields field) { if (security == null) { throw new ArgumentNullException(nameof(security)); } return(MarketDataProvider.GetSecurityValue(security, field)); }
object IMarketDataProvider.GetSecurityValue(Security security, Level1Fields field) { switch (field) { case Level1Fields.ImpliedVolatility: return(security.ImpliedVolatility); } return(null); }
object IMarketDataProvider.GetSecurityValue(Security security, Level1Fields field) { switch (field) { case Level1Fields.ImpliedVolatility: return security.ImpliedVolatility; } return null; }
private IEnumerable <CandleMessage> ProcessCandlePart(Level1Fields part, CandleMessage message) { _transform.Part = part; _transform.Process(message); foreach (var builtCandle in _builder.Process(_subscription, _currentCandle, _transform)) { _currentCandle = builtCandle; yield return(builtCandle); } }
/// <summary> /// Initializes a new instance of the <see cref="QuoteCandleBuilderSourceValue"/>. /// </summary> /// <param name="message">Messages containing quotes.</param> /// <param name="type">Type of candle depth based data.</param> public QuoteCandleBuilderSourceValue(QuoteChangeMessage message, Level1Fields type) { QuoteChange = message; Type = type; switch (Type) { case Level1Fields.BestBidPrice: { var bid = message.GetBestBid(); if (bid != null) { _price = bid.Price; _volume = bid.Volume; } break; } case Level1Fields.BestAskPrice: { var ask = message.GetBestAsk(); if (ask != null) { _price = ask.Price; _volume = ask.Volume; } break; } case Level1Fields.SpreadMiddle: { var bid = message.GetBestBid(); var ask = message.GetBestAsk(); if (bid != null && ask != null) { _price = (ask.Price + bid.Price) / 2; //_volume = pair.Bid.Volume; } break; } default: throw new ArgumentOutOfRangeException(); } }
/// <summary> /// Is the specified <see cref="Level1Fields"/> was obsolete. /// </summary> /// <param name="field"><see cref="Level1Fields"/> value.</param> /// <returns><see langword="true" />, if obsolete, otherwise, not obsolete.</returns> public static bool IsObsolete(this Level1Fields field) { switch (field) { case Level1Fields.LastTrade: case Level1Fields.BestBid: case Level1Fields.BestAsk: case Level1Fields.ExtensionInfo: return(true); } return(false); }
private static Type GetDbType(Level1Fields field) { var type = field.ToType(); if (type == null) { return(null); } if (type.IsEnum) { type = type.GetEnumUnderlyingType(); } return(type.IsClass ? type : typeof(Nullable <>).Make(type)); }
public static TriggerType ToOec(this Level1Fields type) { switch (type) { case Level1Fields.LastTradePrice: return(TriggerType.Last); case Level1Fields.BestBidPrice: return(TriggerType.Bid); case Level1Fields.BestAskPrice: return(TriggerType.Ask); default: throw new ArgumentOutOfRangeException("type"); } }
/// <summary> /// Initializes a new instance of the <see cref="Level1ChangeCandleBuilderSourceValue"/>. /// </summary> /// <param name="message">The message containing the level1 market data.</param> /// <param name="field">Level one market-data field, which is used as an candle value.</param> public Level1ChangeCandleBuilderSourceValue(Level1ChangeMessage message, Level1Fields field) { if (message == null) { throw new ArgumentNullException(nameof(message)); } Level1Change = message; Field = field; _volume = null; switch (field) { case Level1Fields.BestBidPrice: case Level1Fields.BestAskPrice: { var price = GetValue(message, field); if (price != null) { _price = price.Value; } break; } case Level1Fields.SpreadMiddle: { var bid = GetValue(message, Level1Fields.BestBidPrice); var ask = GetValue(message, Level1Fields.BestAskPrice); if (bid != null && ask != null) { _price = (ask.Value + bid.Value) / 2; } break; } default: throw new ArgumentOutOfRangeException(); } }
public static IBSocket SendLevel1Field(this IBSocket socket, Level1Fields field) { switch (field) { case CandleDataTypes.Trades: return(socket.Send("TRADES")); case CandleDataTypes.Midpoint: return(socket.Send("MIDPOINT")); case CandleDataTypes.Bid: return(socket.Send("BID")); case CandleDataTypes.Ask: return(socket.Send("ASK")); case CandleDataTypes.BidAsk: return(socket.Send("BID_ASK")); case CandleDataTypes.HistoricalVolatility: return(socket.Send("HISTORICAL_VOLATILITY")); case CandleDataTypes.ImpliedVolatility: return(socket.Send("OPTION_IMPLIED_VOLATILITY")); case CandleDataTypes.YieldAsk: return(socket.Send("YIELD_ASK")); case CandleDataTypes.YieldBid: return(socket.Send("YIELD_BID")); case CandleDataTypes.YieldBidAsk: return(socket.Send("YIELD_BID_ASK")); case CandleDataTypes.YieldLast: return(socket.Send("YIELD_LAST")); default: throw new ArgumentOutOfRangeException(nameof(field)); } }
private void SessionHolderOnLevel1(string symbol, string exchange, Level1Fields field, decimal value, DateTimeOffset time) { try { SendOutMessage( new Level1ChangeMessage { SecurityId = new SecurityId { SecurityCode = symbol, BoardCode = exchange, }, ServerTime = time } .TryAdd(field, value)); } catch (Exception ex) { SendOutError(ex); } }
object IMarketDataProvider.GetSecurityValue(Security security, Level1Fields field) { switch (field) { case Level1Fields.OpenInterest: return security.OpenInterest; case Level1Fields.ImpliedVolatility: return security.ImpliedVolatility; case Level1Fields.HistoricalVolatility: return security.HistoricalVolatility; case Level1Fields.Volume: return security.Volume; case Level1Fields.LastTradePrice: return security.LastTrade == null ? (decimal?)null : security.LastTrade.Price; case Level1Fields.LastTradeVolume: return security.LastTrade == null ? (decimal?)null : security.LastTrade.Volume; case Level1Fields.BestBidPrice: return security.BestBid == null ? (decimal?)null : security.BestBid.Price; case Level1Fields.BestBidVolume: return security.BestBid == null ? (decimal?)null : security.BestBid.Volume; case Level1Fields.BestAskPrice: return security.BestAsk == null ? (decimal?)null : security.BestAsk.Price; case Level1Fields.BestAskVolume: return security.BestAsk == null ? (decimal?)null : security.BestAsk.Volume; } return null; }
object IMarketDataProvider.GetSecurityValue(Security security, Level1Fields field) { switch (field) { case Level1Fields.OpenInterest: return(security.OpenInterest); case Level1Fields.ImpliedVolatility: return(security.ImpliedVolatility); case Level1Fields.HistoricalVolatility: return(security.HistoricalVolatility); case Level1Fields.Volume: return(security.Volume); case Level1Fields.LastTradePrice: return(security.LastTrade?.Price); case Level1Fields.LastTradeVolume: return(security.LastTrade?.Volume); case Level1Fields.BestBidPrice: return(security.BestBid?.Price); case Level1Fields.BestBidVolume: return(security.BestBid?.Volume); case Level1Fields.BestAskPrice: return(security.BestAsk?.Price); case Level1Fields.BestAskVolume: return(security.BestAsk?.Volume); } return(null); }
object IMarketDataProvider.GetSecurityValue(Security security, Level1Fields field) => null;
/// <summary> /// To create candles from the order books collection. /// </summary> /// <param name="depths">Market depths.</param> /// <param name="series">Candles series.</param> /// <param name="type">Type of candle depth based data.</param> /// <param name="onlyFormed">Process only formed candles.</param> /// <returns>Candles.</returns> public static IEnumerable <Candle> ToCandles(this IEnumerable <MarketDepth> depths, CandleSeries series, Level1Fields type = Level1Fields.SpreadMiddle, bool onlyFormed = true) { return(depths .ToMessages <MarketDepth, QuoteChangeMessage>() .ToCandles(series, type, onlyFormed) .ToCandles <Candle>(series.Security, series.CandleType)); }
/// <summary> /// To create candles from the order books collection. /// </summary> /// <param name="depths">Market depths.</param> /// <param name="series">Candles series.</param> /// <param name="type">Type of candle depth based data.</param> /// <param name="onlyFormed">Process only formed candles.</param> /// <returns>Candles.</returns> public static IEnumerable <CandleMessage> ToCandles(this IEnumerable <QuoteChangeMessage> depths, CandleSeries series, Level1Fields type = Level1Fields.SpreadMiddle, bool onlyFormed = true) { return(new CandleMessageEnumerable(series.ToMarketDataMessage(true), onlyFormed, depths, type)); }
private decimal? GetSecurityValue(Level1Fields field) { return (decimal?)MarketDataProvider.GetSecurityValue(Security, field); }
public CandleMessageEnumerable(MarketDataMessage mdMsg, bool onlyFormed, IEnumerable <QuoteChangeMessage> depths, Level1Fields type) : base(() => new CandleMessageEnumerator(mdMsg, onlyFormed, depths, new QuoteCandleBuilderValueTransform { Type = type })) { if (mdMsg == null) { throw new ArgumentNullException(nameof(mdMsg)); } if (depths == null) { throw new ArgumentNullException(nameof(depths)); } }
private decimal?GetSecurityValue(Level1Fields field) { return((decimal?)MarketDataProvider.GetSecurityValue(Security, field)); }
private static string GetChangesField(Level1Fields field) { return($"{nameof(Level1ChangeMessage.Changes)}[{field}]"); }
public object GetSecurityValue(Security security, Level1Fields field) { return new { }; }
/// <summary> /// Is the specified <see cref="Level1Fields"/> is related to best bid. /// </summary> /// <param name="field">Field.</param> /// <returns>Check result.</returns> public static bool IsBestBidField(this Level1Fields field) => field == Level1Fields.BestBidPrice || field == Level1Fields.BestBidTime || field == Level1Fields.BestBidVolume;
public static IBSocket SendLevel1Field(this IBSocket socket, Level1Fields field) { switch (field) { case CandleDataTypes.Trades: return socket.Send("TRADES"); case CandleDataTypes.Midpoint: return socket.Send("MIDPOINT"); case CandleDataTypes.Bid: return socket.Send("BID"); case CandleDataTypes.Ask: return socket.Send("ASK"); case CandleDataTypes.BidAsk: return socket.Send("BID_ASK"); case CandleDataTypes.HistoricalVolatility: return socket.Send("HISTORICAL_VOLATILITY"); case CandleDataTypes.ImpliedVolatility: return socket.Send("OPTION_IMPLIED_VOLATILITY"); case CandleDataTypes.YieldAsk: return socket.Send("YIELD_ASK"); case CandleDataTypes.YieldBid: return socket.Send("YIELD_BID"); case CandleDataTypes.YieldBidAsk: return socket.Send("YIELD_BID_ASK"); case CandleDataTypes.YieldLast: return socket.Send("YIELD_LAST"); default: throw new ArgumentOutOfRangeException("field"); } }
private void ProcessBestQuote(string symbol, string exchange, double price, int size, int numOfOrders, UpdateType updateType, int ssboe, int usecs, Level1Fields priceField, Level1Fields volumeField) { var secId = new SecurityId { SecurityCode = symbol, BoardCode = exchange }; var time = RithmicUtils.ToTime(ssboe, usecs); SendOutMessage(new Level1ChangeMessage { SecurityId = secId, ServerTime = time, } .TryAdd(priceField, price.ToDecimal()) .TryAdd(volumeField, (decimal)size)); switch (updateType) { // [gene.sato] For best bid/ask the update type does not apply. // The update type is for market depth/level 2 updates. case UpdateType.Undefined: // break; case UpdateType.Solo: { //SendOutMessage(new Level1ChangeMessage //{ // SecurityId = secId, // ServerTime = time, //} //.TryAdd(priceField, price.ToDecimal()) //.TryAdd(volumeField, (decimal)size)); break; } case UpdateType.Begin: case UpdateType.Middle: case UpdateType.Aggregated: { var pair = _quotes .SafeAdd(secId) .SafeAdd(time, key => new RefPair <BidInfo, AskInfo>()); pair.Second = new AskInfo { Price = price, NumOrders = numOfOrders, Size = size, }; break; } case UpdateType.End: FlushQuotes(secId); break; case UpdateType.Clear: break; default: throw new ArgumentOutOfRangeException(); } }
/// <inheritdoc /> public override void Load(SettingsStorage settings) { base.Load(settings); Field = settings.GetValue <Level1Fields>(nameof(Field)); }
/// <summary> /// Подписаться на получение исторических значений инструмента с заданной периодичностью. /// </summary> /// <param name="message">Сообщение о подписке или отписки на маркет-данные.</param> /// <param name="field">Поле маркет-данных. Поддерживаются следующие значения: /// <list type="number"> /// <item> /// <description><see cref="CandleDataTypes.Trades"/>.</description> /// </item> /// <item> /// <description><see cref="CandleDataTypes.Bid"/>.</description> /// </item> /// <item> /// <description><see cref="CandleDataTypes.Ask"/>.</description> /// </item> /// <item> /// <description><see cref="CandleDataTypes.Midpoint"/>.</description> /// </item> /// <item> /// <description><see cref="CandleDataTypes.BidAsk"/>.</description> /// </item> /// <item> /// <description><see cref="CandleDataTypes.ImpliedVolatility"/>.</description> /// </item> /// <item> /// <description><see cref="CandleDataTypes.HistoricalVolatility"/>.</description> /// </item> /// </list></param> /// <param name="useRth">Получать данные только по торговому времени. По-умолчанию используется торговое время.</param> private void SubscribeHistoricalCandles(MarketDataMessage message, Level1Fields field, bool useRth = true) { if (message == null) throw new ArgumentNullException("message"); //if (message.CandleType != typeof(TimeFrameCandle)) // throw new ArgumentException("Interactive Brokers не поддерживает свечи типа {0}.".Put(series.CandleType), "series"); if (!(message.Arg is TimeSpan)) throw new ArgumentException(LocalizedStrings.WrongCandleArg.Put(message.Arg), "message"); var timeFrame = (TimeSpan)message.Arg; //var security = SessionHolder.Securities[message.SecurityId]; ProcessRequest(RequestMessages.SubscribeHistoricalData, ServerVersions.V16, ServerVersions.V6, socket => { socket .Send(message.TransactionId) .SendIf(ServerVersions.V68, s => socket.SendContractId(message.SecurityId)) .SendSecurity(message) .SendIf(ServerVersions.V68, s => socket.Send(message.Class)) .SendIncludeExpired(message.ExpiryDate) .SendEndDate(message.To ?? DateTimeOffset.MaxValue) .SendTimeFrame(timeFrame) .Send(ConvertPeriodtoIb(message.From ?? DateTimeOffset.MinValue, message.To ?? DateTimeOffset.MaxValue)) .Send(useRth) .SendLevel1Field(field); if (socket.ServerVersion > ServerVersions.V16) { //Send date times as seconds since 1970 socket.Send(2); } // TODO WeightedIndexSecurity indexSecurity = null;//security as WeightedIndexSecurity; if (indexSecurity != null) socket.SendCombo(indexSecurity); if (socket.ServerVersion >= ServerVersions.V70) { //StringBuilder chartOptionsStr = new StringBuilder(); //int chartOptionsCount = chartOptions == null ? 0 : chartOptions.size(); //if (chartOptionsCount > 0) //{ // for (int i = 0; i < chartOptionsCount; ++i) // { // TagValue tagValue = (TagValue)chartOptions.get(i); // chartOptionsStr.append(tagValue.m_tag); // chartOptionsStr.append("="); // chartOptionsStr.append(tagValue.m_value); // chartOptionsStr.append(";"); // } //} //send(chartOptionsStr.toString()); socket.Send(string.Empty); } }); }
/// <summary> /// Подписаться на получение свечек реального времени. /// </summary> /// <param name="message"></param> /// <param name="field">Поля маркет-данных, на основе которых будут строяться свечи. Поддерживаются следующие значения: /// <list type="number"> /// <item> /// <description><see cref="CandleDataTypes.Trades"/>.</description> /// </item> /// <item> /// <description><see cref="CandleDataTypes.Bid"/>.</description> /// </item> /// <item> /// <description><see cref="CandleDataTypes.Ask"/>.</description> /// </item> /// <item> /// <description><see cref="CandleDataTypes.Midpoint"/>.</description> /// </item> /// </list> /// </param> /// <param name="useRth">Строить свечи только по торговому времени. По-умолчанию используется торговое время.</param> private void SubscribeRealTimeCandles(MarketDataMessage message, Level1Fields field = CandleDataTypes.Trades, bool useRth = true) { if (message == null) throw new ArgumentNullException("message"); //var security = SessionHolder.Securities[message.SecurityId]; ProcessRequest(RequestMessages.SubscribeRealTimeCandles, ServerVersions.V34, ServerVersions.V3, socket => socket .Send(message.TransactionId) .SendIf(ServerVersions.V68, s => socket.SendContractId(message.SecurityId)) .SendSecurity(message) .SendIf(ServerVersions.V68, s => socket.Send(message.Class)) .Send(5) // Поддерживается только 5 секундный тайм-фрейм. .SendLevel1Field(field) .Send(useRth) .SendIf(ServerVersions.V70, s => { //StringBuilder realTimeBarsOptionsStr = new StringBuilder(); //int realTimeBarsOptionsCount = realTimeBarsOptions == null ? 0 : realTimeBarsOptions.size(); //if (realTimeBarsOptionsCount > 0) //{ // for (int i = 0; i < realTimeBarsOptionsCount; ++i) // { // TagValue tagValue = (TagValue)realTimeBarsOptions.get(i); // realTimeBarsOptionsStr.append(tagValue.m_tag); // realTimeBarsOptionsStr.append("="); // realTimeBarsOptionsStr.append(tagValue.m_value); // realTimeBarsOptionsStr.append(";"); // } //} //send(realTimeBarsOptionsStr.toString()); socket.Send(string.Empty); })); }
/// <summary> /// Загрузить настройки. /// </summary> /// <param name="settings">Хранилище настроек.</param> public override void Load(SettingsStorage settings) { base.Load(settings); Field = settings.GetValue<Level1Fields>("Field"); }
/// <summary> /// Получить значение маркет-данных для инструмента. /// </summary> /// <param name="security">Инструмент.</param> /// <param name="field">Поле маркет-данных.</param> /// <returns>Значение поля. Если данных нет, то будет возвращено <see langword="null"/>.</returns> public object GetSecurityValue(Security security, Level1Fields field) { return(Connector.GetSecurityValue(security, field)); }
/// <summary> /// Is the specified <see cref="Level1Fields"/> is related to last trade. /// </summary> /// <param name="field">Field.</param> /// <returns>Check result.</returns> public static bool IsLastTradeField(this Level1Fields field) => field == Level1Fields.LastTradeId || field == Level1Fields.LastTradeTime || field == Level1Fields.LastTradeOrigin || field == Level1Fields.LastTradePrice || field == Level1Fields.LastTradeUpDown || field == Level1Fields.LastTradeVolume;
private static SecurityChangedRule CreateSecurityCondition(Security security, IMarketDataProvider provider, Level1Fields field, Unit offset, bool isLess) { if (security == null) { throw new ArgumentNullException(nameof(security)); } if (offset == null) { throw new ArgumentNullException(nameof(offset)); } if (offset.Value == 0) { throw new ArgumentException(LocalizedStrings.Str1051, nameof(offset)); } if (offset.Value < 0) { throw new ArgumentException(LocalizedStrings.Str1052, nameof(offset)); } var price = (decimal?)provider.GetSecurityValue(security, field); if (price == null && offset.Type != UnitTypes.Limit) { throw new InvalidOperationException(LocalizedStrings.Str1053); } if (isLess) { var finishPrice = (decimal)(offset.Type == UnitTypes.Limit ? offset : price - offset); return(new SecurityChangedRule(security, provider, s => { var quote = (decimal?)provider.GetSecurityValue(s, field); return quote != null && quote < finishPrice; })); } else { var finishPrice = (decimal)(offset.Type == UnitTypes.Limit ? offset : price + offset); return(new SecurityChangedRule(security, provider, s => { var quote = (decimal?)provider.GetSecurityValue(s, field); return quote != null && quote > finishPrice; })); } }
/// <summary> /// Is the specified <see cref="Level1Fields"/> is related to best ask. /// </summary> /// <param name="field">Field.</param> /// <returns>Check result.</returns> public static bool IsBestAskField(this Level1Fields field) => field == Level1Fields.BestAskPrice || field == Level1Fields.BestAskTime || field == Level1Fields.BestAskVolume;
private void ProcessBestQuote(string symbol, string exchange, double price, int size, int numOfOrders, UpdateType updateType, int ssboe, int usecs, Level1Fields priceField, Level1Fields volumeField) { var secId = new SecurityId { SecurityCode = symbol, BoardCode = exchange }; var time = RithmicUtils.ToTime(ssboe, usecs); SendOutMessage(new Level1ChangeMessage { SecurityId = secId, ServerTime = time, } .TryAdd(priceField, price.ToDecimal()) .TryAdd(volumeField, (decimal)size)); switch (updateType) { // [gene.sato] For best bid/ask the update type does not apply. // The update type is for market depth/level 2 updates. case UpdateType.Undefined: // break; case UpdateType.Solo: { //SendOutMessage(new Level1ChangeMessage //{ // SecurityId = secId, // ServerTime = time, //} //.TryAdd(priceField, price.ToDecimal()) //.TryAdd(volumeField, (decimal)size)); break; } case UpdateType.Begin: case UpdateType.Middle: case UpdateType.Aggregated: { var pair = _quotes .SafeAdd(secId) .SafeAdd(time, key => new RefPair<BidInfo, AskInfo>()); pair.Second = new AskInfo { Price = price, NumOrders = numOfOrders, Size = size, }; break; } case UpdateType.End: FlushQuotes(secId); break; case UpdateType.Clear: break; default: throw new ArgumentOutOfRangeException(); } }