Files
zszq-trs/YLErpDAL/Modules/EodModule/SettlementModule/Base/EodSettlementContextBase.cs
T
2024-05-09 14:06:26 +08:00

237 lines
7.2 KiB
C#

using YLErp.Abstract.DataProviders;
using YLErp.Modules.DataProviderModule;
namespace YLErp.Modules.EodModule.SettlementModule
{
/// <summary>
/// 这是一个多线程运行环境下的收盘上下文类
/// </summary>
public abstract class EodSettlementContextBase
{
EodPriceProvider _eodPriceProvider;
EodPriceProvider _preEodPriceProvider;
ExchangeStatus _exchangeStatus;
protected EodSettlementContextBase(EodSettlementRequest request, CancellationToken cancellationToken)
{
Request = request ?? throw new ArgumentNullException(nameof(request));
CancellationToken = cancellationToken;
if (request.SettleDate.Year < 2000)
{
throw new ArgumentException("request参数错误:SettleDate");
}
if (!request.IsSettleOtcTrades && !request.IsSettleExchangeTrades)
{
throw new ArgumentException("request参数错误");
}
StartDate = request.SettleDate.AddYears(-3);
PreSettleDate = BLL.valuedateBLL.GetNonHolidayDefore(SettleDate.AddDays(-1));
SystemValue = BLL.valuedateBLL.SystemDate;
PredicateBuilder = new EodQueryPredicateBuilder(request);
}
public ExchangeStatus ExchangeStatus => _exchangeStatus ?? (_exchangeStatus = new ExchangeStatus(SettleDate, PreSettleDate));
/// <summary>
/// 任务终止令牌
/// </summary>
public CancellationToken CancellationToken { get; }
/// <summary>
/// 结算请求参数
/// </summary>
public EodSettlementRequest Request { get; }
/// <summary>
/// 请求用户信息
/// </summary>
public OptUserInfo UserInfo => Request.UserInfo;
/// <summary>
/// 结算日
/// </summary>
public DateTime SettleDate => Request.SettleDate;
/// <summary>
/// 需要收盘得客户
/// </summary>
public IEnumerable<int> ClienIds => Request.ClientIds;
/// <summary>
/// 结算日
/// </summary>
public string SettleDateStr => Request.SettleDate.ToString(ConsGlobal.DateFormat);
/// <summary>
/// 获取上个结算日(结算第一步就需要检查这个日期是否等于日历数据中的前一工作日)
/// </summary>
public DateTime PreSettleDate { get; }
/// <summary>
/// 获取上个结算日(结算第一步就需要检查这个日期是否等于日历数据中的前一工作日)
/// </summary>
public string PreSettleDateStr => PreSettleDate.ToString(ConsGlobal.DateFormat);
/// <summary>
/// 交易起始关注日
/// </summary>
public DateTime StartDate { get; }
/// <summary>
/// 系统参数
/// </summary>
public valuedate SystemValue { get; }
/// <summary>
/// 查询条件构造器
/// </summary>
public EodQueryPredicateBuilder PredicateBuilder { get; }
/// <summary>
/// 是否当前交易日
/// </summary>
public bool IsCurrentDay => SettleDate == SystemValue.ValueDate;
/// <summary>
/// 获取日终价格提供对象
/// </summary>
public EodPriceProvider GetEodPriceProvider()
{
if (_eodPriceProvider == null)
{
_eodPriceProvider = new EodPriceProvider(SettleDate, isDiviendPrice: false);
if (!Request.IsPartialSettlement)
{
_eodPriceProvider.Initialize();
}
}
return _eodPriceProvider;
}
/// <summary>
/// 收盘日上一交易日日终价格提供
/// </summary>
public EodPriceProvider GetPreEodPriceProvider()
{
if (_preEodPriceProvider == null)
{
_preEodPriceProvider = new EodPriceProvider(PreSettleDate);
_preEodPriceProvider.SetPreValueDate(PreSettleDate);
if (!Request.IsPartialSettlement)
{
_preEodPriceProvider.Initialize();
}
}
return _preEodPriceProvider;
}
#region----运行信息处理----
/// <summary>
/// 记录日志
/// </summary>
public void LogInfo(string message)
{
LogFactory.GetLogger("日终结算").Info(message);
}
/// <summary>
/// 记录日志
/// </summary>
public void LogError(string message, Exception ex = null)
{
LogFactory.GetLogger("日终结算").Error(message, ex);
}
/// <summary>
/// 激发错误异常
/// </summary>
public void RaiseError(string action, string error, Exception ex = null)
{
if (error == null)
{
error = "发生错误";
}
throw new EodSettleException($"[{action}]{error}", ex);
}
/// <summary>
/// 检查结算任务是否被取消
/// </summary>
public void CheckCanceled()
{
CancellationToken.ThrowIfCancellationRequested();
}
#endregion
public override string ToString()
{
return SettleDateStr;
}
}
/// <summary>
/// 日终结算错误
/// </summary>
public class EodSettleException : Exception
{
public EodSettleException(string message, Exception innerException)
: base(message, innerException)
{
}
}
/// <summary>
/// 交易所状态
/// </summary>
public class ExchangeStatus
{
readonly DateTime _preDate;
readonly Dictionary<string, (bool isholidy, DateTime exPreDate)> _dic;
public ExchangeStatus(DateTime valueDate, DateTime preDate)
{
_preDate = preDate;
_dic = new Dictionary<string, (bool, DateTime)>(StringComparer.OrdinalIgnoreCase);
foreach (var m in DataCacheProvider.GetMarketDataSource().AsQueryable())
{
if (!string.IsNullOrEmpty(m.ExchangeNo))
{
var calendar = m.CalendarName.TrimToNull() ?? ConsGlobal.DefaultCalendar;
var isholidy = QdpModule.QdpCalendarHelper.IsHoliday(valueDate, calendar);
var exPreDate = QdpModule.QdpCalendarHelper.GetNonHolidayDefore(_preDate, calendar);
_dic[m.ExchangeNo] = (isholidy, exPreDate);
}
}
}
/// <summary>
/// 交易所是否节假日
/// </summary>
public bool IsHoliday(string exchangeNo)
{
return !string.IsNullOrEmpty(exchangeNo) && _dic.TryGetValue(exchangeNo, out var state) && state.isholidy;
}
/// <summary>
/// 交易所的上一个交易日
/// </summary>
public DateTime GetPreDate(string exchangeNo)
{
return !string.IsNullOrEmpty(exchangeNo) && _dic.TryGetValue(exchangeNo, out var state) ? state.exPreDate : _preDate;
}
}
}