using System; using System.Collections.Generic; using System.Linq; using System.Text; namespace TIWebApi.Clients.MarketData { internal class Subscriptions { private Dictionary _subscribedSymbols; public Subscriptions() { _subscribedSymbols = new Dictionary(); } public bool Contains(string source, string symbol) { return _subscribedSymbols.ContainsKey(symbol) && _subscribedSymbols[symbol].HasSource(source); } public bool Add(string source, string symbol) { //Return true If we are adding this symbol for the first time //then we need to subscribe to it at the server if (_subscribedSymbols.ContainsKey(symbol)) { _subscribedSymbols[symbol].AddSource(source); return false; } else { _subscribedSymbols.Add(symbol, new Subscription(source, symbol)); return true; } } public bool Reduce(string source, string symbol) { //Return true indicating no more subscriptions for the symbol so we can unsubscribe if (!_subscribedSymbols.ContainsKey(symbol)) return true; _subscribedSymbols[symbol].ReduceSource(source); if (_subscribedSymbols[symbol].Count == 0) { _subscribedSymbols.Remove(symbol); return true; } else { return false; } } public List ReduceSymbolListForSource(string source, int retainCount) { //Select a date ordered list of source symbols //that are past the retainCount var symbolsToUnsubscribe = _subscribedSymbols .Where(s => s.Value.HasSource(source)) .OrderByDescending(s => s.Value.SourceCreatedWhen(source)) .Select(s => s.Key) .Skip(retainCount) .ToList() ; return symbolsToUnsubscribe; } public List ReduceSource(string source ) { var symbols = new List(); foreach( var subscription in _subscribedSymbols.Values) { if(subscription.ReduceSource(source)) { symbols.Add(subscription.Symbol); } } foreach(var symbol in symbols) { _subscribedSymbols.Remove(symbol); } return symbols; } public List AllKeys() { return _subscribedSymbols.Keys.ToList(); } public IReadOnlyCollection AllValues() { return _subscribedSymbols.Values.ToList(); } public override string ToString() { var sb = new StringBuilder(); foreach(var subscription in _subscribedSymbols.Values ) { sb.Append($"{subscription} "); } return sb.ToString(); } public int Count { get { return _subscribedSymbols.Keys.Count; } } public void Pump (string symbol) { try { if (_subscribedSymbols.ContainsKey(symbol)){ _subscribedSymbols[symbol].MessageCount++; } } catch (Exception) { } } } }