using System;
using System.Collections.Generic;
using System.Linq;
using QuantConnect.Data;
using QuantConnect.Data.Consolidators;
using QuantConnect.Data.Market;
using QuantConnect.Util;
namespace QuantConnect.ToolBox
{
///
/// Class that uses consolidators to aggregate tick data data
///
public abstract class TickAggregator
{
protected TickAggregator(Resolution resolution, TickType tickType)
{
TickType = tickType;
Resolution = resolution;
}
///
/// Gets the tick type of the consolidator
///
public TickType TickType { get; protected set; }
///
/// The consolidator used to aggregate data from
/// higher resolutions to data in lower resolutions
///
public IDataConsolidator Consolidator { get; protected set; }
///
/// The consolidated data
///
public List Consolidated { get; protected set; }
///
/// The resolution that the data is being aggregated into
///
public Resolution Resolution { get; }
///
/// Updates the consolidator with the specified bar.
///
/// The latest data observation.
public virtual void Update(BaseData data)
{
Consolidator.Update(data);
}
///
/// Return all the consolidated data as well as the
/// bar the consolidator is currently working on
///
public List Flush()
{
var data = new List(Consolidated);
if (Consolidator.WorkingData != null)
{
data.Add(Consolidator.WorkingData as BaseData);
}
return data;
}
///
/// Creates the correct instances for the specified tick types and resolution.
/// will ignore and use
///
public static IEnumerable ForTickTypes(SecurityType securityType, Resolution resolution, params TickType[] tickTypes)
{
if (resolution == Resolution.Tick)
{
foreach (var tickType in tickTypes.Where(t => LeanData.IsValidConfiguration(securityType, resolution, t)))
{
// OI is special
if (tickType == TickType.OpenInterest)
{
yield return new OpenInterestTickAggregator(resolution);
continue;
}
yield return new IdentityTickAggregator(tickType);
}
yield break;
}
foreach (var tickType in tickTypes.Where(t => LeanData.IsValidConfiguration(securityType, resolution, t)))
{
switch (tickType)
{
case TickType.Trade:
yield return new TradeTickAggregator(resolution);
break;
case TickType.Quote:
yield return new QuoteTickAggregator(resolution);
break;
case TickType.OpenInterest:
yield return new OpenInterestTickAggregator(resolution);
break;
default:
throw new ArgumentOutOfRangeException(nameof(tickType), tickType, null);
}
}
}
}
///
/// Use to consolidate quote ticks into a specified resolution
///
public class QuoteTickAggregator : TickAggregator
{
public QuoteTickAggregator(Resolution resolution)
: base(resolution, TickType.Quote)
{
Consolidated = new List();
Consolidator = new TickQuoteBarConsolidator(resolution.ToTimeSpan());
Consolidator.DataConsolidated += (sender, consolidated) =>
{
Consolidated.Add(consolidated as QuoteBar);
};
}
}
///
/// Use to consolidate trade ticks into a specified resolution
///
public class TradeTickAggregator : TickAggregator
{
public TradeTickAggregator(Resolution resolution)
: base(resolution, TickType.Trade)
{
Consolidated = new List();
Consolidator = new TickConsolidator(resolution.ToTimeSpan());
Consolidator.DataConsolidated += (sender, consolidated) =>
{
Consolidated.Add(consolidated as TradeBar);
};
}
}
///
/// Use to consolidate open interest ticks into a specified resolution
///
public class OpenInterestTickAggregator : TickAggregator
{
public OpenInterestTickAggregator(Resolution resolution)
: base(resolution, TickType.OpenInterest)
{
Consolidated = new List();
Consolidator = new OpenInterestConsolidator(resolution.ToTimeSpan());
Consolidator.DataConsolidated += (sender, consolidated) =>
{
Consolidated.Add(consolidated as OpenInterest);
};
}
}
///
/// Use to yield ticks unmodified into the consolidated data collection
///
public class IdentityTickAggregator : TickAggregator
{
public IdentityTickAggregator(TickType tickType)
: base(Resolution.Tick, tickType)
{
Consolidated = new List();
Consolidator = FilteredIdentityDataConsolidator.ForTickType(tickType);
Consolidator.DataConsolidated += (sender, consolidated) =>
{
Consolidated.Add(consolidated as Tick);
};
}
}
}