using YieldChain.Commons;
using YLErp.Abstract.DataProviders;
using YLErp.Models;
namespace YLErp.Modules.DataProviderModule
{
///
/// 期权现价提供
///
public class ExchangeOptionPriceProvider : IPriceProvider
{
readonly bool _initializeAll;
readonly IDictionary _priceDic;
///
///
///
/// 是否初始化全部数据
public ExchangeOptionPriceProvider(bool initializeAll = true)
{
_initializeAll = initializeAll;
_priceDic = initializeAll
? InnerDataProvider.Default.GetPriceDic()
: new Dictionary(StringComparer.OrdinalIgnoreCase);
}
///
///
///
public double GetPrice(string optionCode)
{
return (InnerGetPrice(optionCode)?.Price) ?? 0;
}
///
///
///
public bool TryGetPrice(string optionCode, out double price)
{
var data = InnerGetPrice(optionCode);
if (data != null)
{
price = data.Price;
return true;
}
price = 0;
return false;
}
///
///
///
public bool TryGetPriceModel(string optionCode, out PriceModel priceModel)
{
return null != (priceModel = InnerGetPrice(optionCode));
}
private PriceModel InnerGetPrice(string optionCode)
{
if (string.IsNullOrEmpty(optionCode))
{
return null;
}
if (_priceDic.TryGetValue(optionCode, out var data))
{
return data;
}
if (_initializeAll)
{
return null;
}
using var db = DbContextFactory.GetYLDbContext();
data = db.exchange_list_option.Where(n => n.ContractCode == optionCode)
.Select(n => new PriceModel
{
InstrumentCode = n.ContractCode,
Price = n.Price ?? 0,
PriceTime = n.PriceTime
}).FirstOrDefault();
_priceDic[optionCode] = data;
return data;
}
///
/// 内部数据提供以保证行情可以及时更新
///
class InnerDataProvider
{
readonly ThrottleAction _updateThrottle;
readonly Dictionary _priceDic;
private InnerDataProvider()
{
_updateThrottle = new ThrottleAction(UpdatePrice, 10);
_priceDic = new Dictionary();
}
private void UpdatePrice()
{
using var db = DbContextFactory.GetYLDbContext();
var date = DateTime.Today.AddDays(-10);
var arr = db.exchange_list_option.Where(n => n.MaturityDate > date && n.ContractCode != null)
.Select(n => new PriceModel
{
InstrumentCode = n.ContractCode,
Price = n.Price ?? 0,
PriceTime = n.PriceTime
}).ToArray();
foreach (var item in arr)
{
_priceDic[item.InstrumentCode] = item;
}
}
public IDictionary GetPriceDic()
{
_updateThrottle.Execute();
return new Dictionary(_priceDic);
}
///
/// 单例
///
public static readonly InnerDataProvider Default;
static InnerDataProvider()
{
Default = new InnerDataProvider();
}
}
}
}