376 lines
16 KiB
C#
376 lines
16 KiB
C#
using BaseOUDAL;
|
|
using YieldChain.Security;
|
|
using YLErp.BLL;
|
|
using YLErp.DBModels.Enums;
|
|
using YLErp.Model;
|
|
|
|
namespace YLErp.Modules.ScenarioModule
|
|
{
|
|
/// <summary>
|
|
/// 情景分析数据查询服务
|
|
/// </summary>
|
|
public class TradeScenarioQueryService : YLBaseService
|
|
{
|
|
public TradeScenarioQueryService(OptUserInfo userInfo) : base(userInfo)
|
|
{
|
|
|
|
}
|
|
|
|
//获取日终持仓
|
|
private SearchListResult<TradePositionMerge> GetEodPosition(TradeScenarioSearchModel searchModel)
|
|
{
|
|
var predicate = PredicateBuilder.Create<eod_trade_position>(
|
|
t => t.ValueDate == searchModel.PositionDate
|
|
&& !ScenarioHelper.ExcludeTradeTypes.Contains(t.TradeType) && t.UnderlyingCode != null);
|
|
if (searchModel.UserAssets != null || searchModel.UserClients != null)
|
|
{
|
|
predicate = predicate.And(n => searchModel.UserAssets.Contains(n.BookId) || searchModel.UserClients.Contains(n.ClientId));
|
|
}
|
|
if (searchModel.UnderlyingIds != null && searchModel.UnderlyingIds.Any(n => n > 0))
|
|
{
|
|
predicate = predicate.And(x => searchModel.UnderlyingIds.Contains(x.UnderlyingId));
|
|
}
|
|
|
|
|
|
if (searchModel.VarietyIds != null && searchModel.VarietyIds.Any(n => n > 0))
|
|
{
|
|
predicate = predicate.And(
|
|
x => DbContext.underlying_manager.Any(n => n.UnderlyingCode == x.UnderlyingCode && searchModel.VarietyIds.Contains(n.UnderlyingTypeId)));
|
|
}
|
|
|
|
if (searchModel.TradeTypes != null && searchModel.TradeTypes.Any(n => !string.IsNullOrEmpty(n)))
|
|
{
|
|
if (searchModel.TradeTypes.Contains("场外期权"))
|
|
{
|
|
predicate = predicate.And(x => x.TradeId > 0 || searchModel.TradeTypes.Contains(x.TradeType));
|
|
}
|
|
else
|
|
{
|
|
predicate = predicate.And(x => searchModel.TradeTypes.Contains(x.TradeType));
|
|
}
|
|
}
|
|
|
|
if (searchModel.AssetIds != null && searchModel.AssetIds.Any())
|
|
{
|
|
predicate = predicate.And(x => searchModel.AssetIds.Contains(x.BookId));
|
|
}
|
|
|
|
if (searchModel.ClientIds != null && searchModel.ClientIds.Any())
|
|
{
|
|
predicate = predicate.And(x => searchModel.ClientIds.Contains(x.ClientId));
|
|
}
|
|
|
|
var tradePredicate = PredicateBuilder.Create<trade>(t => t.ValidState != ConsGlobal.InValid);
|
|
|
|
var query = from et in DbContext.eod_trade_position.Where(predicate)
|
|
join td in DbContext.trade.Where(tradePredicate) on et.TradeId equals td.id into temptd
|
|
from td in temptd.DefaultIfEmpty()
|
|
orderby td.TradeNumber descending, et.UnderlyingCode
|
|
select new
|
|
{
|
|
et.id,
|
|
et.TradeId,
|
|
et.ClientId,
|
|
et.BookId,
|
|
et.TradeType,
|
|
et.UnderlyingId,
|
|
et.UnderlyingCode,
|
|
BuySell = td != null ? td.BuySell : et.PositionType == "long" ? "买入" : "卖出",
|
|
|
|
td.TradeNumber,
|
|
td.ExerciseDate,
|
|
td.OptionType,
|
|
td.Strike,
|
|
td.IsMoneynessOption,
|
|
td.TradeDate,
|
|
// Notional = td == null ? (et.PositionType == "long" ? et.Amount : - et.Amount) : et.Amount,
|
|
Notional = et.Amount,
|
|
ExchangeOptionCode = et.ExchangeOptionCode
|
|
};
|
|
|
|
var searchResult = query.ToSearchList(searchModel);
|
|
|
|
var list = new List<TradePositionMerge>(searchResult.rows.Count());
|
|
|
|
foreach (var td in searchResult.rows)
|
|
{
|
|
var underlying = DataCacheProvider.GetUnderlyingDataSource().GetData(td.UnderlyingCode);
|
|
if (underlying == null)
|
|
{
|
|
continue;
|
|
}
|
|
|
|
var tm = new TradePositionMerge
|
|
{
|
|
id = td.id + "_历史",
|
|
//EncryptId = DataProtect.Encrypt(td.id) + "_历史",
|
|
TradeEncryptId = td.TradeId > 0 ? DataProtect.Encrypt(td.TradeId) : string.Empty,
|
|
TradeNumber = td.TradeNumber,
|
|
BookId = td.BookId,
|
|
ClientId = td.ClientId,
|
|
ClientName = DataCacheProvider.GetClientDataSource().GetData(td.ClientId)?.Name,
|
|
AssetBookName = DataCacheProvider.GetAssetUnitDataSource().GetData(td.BookId)?.Name,
|
|
BuySell = td.BuySell,
|
|
ExerciseDate = td.ExerciseDate,
|
|
OptionType = td.OptionType,
|
|
Strike = td.Strike,
|
|
IsMoneynessOption = td.IsMoneynessOption,
|
|
TradeDate = td.TradeDate,
|
|
TradeType = td.TradeType,
|
|
UnderlyingCode = td.UnderlyingCode,
|
|
UnderlyingId = underlying.id,
|
|
VarietyId = underlying.UnderlyingTypeId,
|
|
UnderlyingAssetClass = underlying.UnderlyingType,
|
|
|
|
TradeAmount = 0,
|
|
};
|
|
|
|
tm.TradeAmount = td.Notional / underlying.CountRatio;
|
|
|
|
if (td.TradeType == "场内期权")
|
|
{
|
|
var exchangeOption = DataCacheProvider.GetExchangeListOptionDataSource().GetData(td.ExchangeOptionCode);
|
|
if (exchangeOption == null)
|
|
{
|
|
continue;
|
|
}
|
|
tm.ExerciseDate = exchangeOption.MaturityDate;
|
|
tm.OptionType = exchangeOption.OptionType;
|
|
tm.Strike = exchangeOption.Strike;
|
|
}
|
|
|
|
tm.CountRatio = underlying.CountRatio;
|
|
list.Add(tm);
|
|
}
|
|
|
|
return new SearchListResult<TradePositionMerge>(searchResult, list);
|
|
}
|
|
|
|
//获取日间持仓
|
|
private SearchListResult<TradePositionMerge> GetIntradayPosition(TradeScenarioSearchModel searchModel)
|
|
{
|
|
var blQuery = true;
|
|
|
|
#region----场外交易持仓过滤条件----
|
|
|
|
var tdPredicate = PredicateBuilder.Create<trade>(
|
|
t => t.ExerciseDate >= valuedateBLL.ValueDate && ConsTrade.NeedMarginTradeStatusList.Contains(t.TradeStatus)
|
|
&& !ScenarioHelper.ExcludeTradeTypes.Contains(t.TradeType) && t.ClientId > 0 && t.ValidState != "InValid");
|
|
if (searchModel.UserAssets != null || searchModel.UserClients != null)
|
|
{
|
|
tdPredicate = tdPredicate.And(a => searchModel.UserAssets.Contains(a.AssetId) || searchModel.UserClients.Contains(a.ClientId));
|
|
}
|
|
|
|
if (searchModel.TradeTypes != null && searchModel.TradeTypes.Any(n => !string.IsNullOrEmpty(n)))
|
|
{
|
|
if (!searchModel.TradeTypes.Contains("场外期权"))
|
|
{
|
|
blQuery = false;
|
|
tdPredicate = PredicateBuilder.False<trade>();
|
|
}
|
|
}
|
|
|
|
if (blQuery)
|
|
{
|
|
if (searchModel.ClientIds != null && searchModel.ClientIds.Any(n => n > 0))
|
|
{
|
|
tdPredicate = tdPredicate.And(x => searchModel.ClientIds.Contains(x.ClientId));
|
|
}
|
|
|
|
if (searchModel.UnderlyingIds != null && searchModel.UnderlyingIds.Any(n => n > 0))
|
|
{
|
|
tdPredicate = tdPredicate.And(x => searchModel.UnderlyingIds.Contains(x.UnderlyingId));
|
|
}
|
|
|
|
if (searchModel.AssetIds != null&&searchModel.AssetIds.Any())
|
|
{
|
|
tdPredicate = tdPredicate.And(x => searchModel.AssetIds.Contains(x.AssetId));
|
|
}
|
|
|
|
if (searchModel.VarietyIds != null && searchModel.VarietyIds.Any(n => n > 0))
|
|
{
|
|
tdPredicate = tdPredicate.And(
|
|
x => DbContext.underlying_manager.Any(n => n.UnderlyingCode == x.UnderlyingCode && searchModel.VarietyIds.Contains(n.UnderlyingTypeId)));
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region----场内交易持仓过滤条件----
|
|
|
|
blQuery = true;
|
|
|
|
var exPredicate = PredicateBuilder.True<TradePosition>();
|
|
|
|
if (searchModel.ClientIds != null && searchModel.ClientIds.Any(n => n > 0))
|
|
{
|
|
blQuery = false;
|
|
}
|
|
|
|
if (blQuery && searchModel.TradeTypes != null && searchModel.TradeTypes.Any(n => !string.IsNullOrEmpty(n)))
|
|
{
|
|
var tradeTypes = searchModel.TradeTypes.Intersect(ConsTrade.TradeTypesForHedge).ToArray();
|
|
if (blQuery = tradeTypes.Any())
|
|
{
|
|
exPredicate = exPredicate.And(x => tradeTypes.Contains(x.TradeType));
|
|
}
|
|
}
|
|
|
|
if (blQuery)
|
|
{
|
|
if (searchModel.UserAssets != null)
|
|
{
|
|
exPredicate = exPredicate.And(x => searchModel.UserAssets.Contains(x.BookId));
|
|
}
|
|
if (searchModel.UnderlyingIds != null && searchModel.UnderlyingIds.Any(n => n > 0))
|
|
{
|
|
exPredicate = exPredicate.And(x => searchModel.UnderlyingIds.Contains(x.UnderlyingId));
|
|
}
|
|
|
|
if (searchModel.AssetIds != null && searchModel.AssetIds.Any())
|
|
{
|
|
exPredicate = exPredicate.And(x => searchModel.AssetIds.Contains(x.BookId));
|
|
}
|
|
|
|
if (searchModel.VarietyIds != null && searchModel.VarietyIds.Any(n => n > 0))
|
|
{
|
|
exPredicate = exPredicate.And(
|
|
x => DbContext.underlying_manager.Any(n => n.UnderlyingCode == x.UnderlyingCode && searchModel.VarietyIds.Contains(n.UnderlyingTypeId)));
|
|
}
|
|
}
|
|
else
|
|
{
|
|
exPredicate = PredicateBuilder.False<TradePosition>();
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region----查询Linq----
|
|
|
|
var tdQuery = from td in DbContext.trade.Where(tdPredicate)
|
|
select new
|
|
{
|
|
torder = 1,
|
|
id = (long)td.id,
|
|
td.ClientId,
|
|
td.AssetId,
|
|
td.TradeType,
|
|
td.UnderlyingId,
|
|
td.UnderlyingCode,
|
|
BuySell = td.BuySell,
|
|
|
|
td.TradeNumber,
|
|
td.ExerciseDate,
|
|
td.OptionType,
|
|
td.Strike,
|
|
td.IsMoneynessOption,
|
|
td.TradeDate,
|
|
Notional = td.Notional,
|
|
|
|
ExchangeOptionCode = string.Empty
|
|
};
|
|
|
|
var extdQuery = from td in DbContext.TradePosition.Where(exPredicate)
|
|
select new
|
|
{
|
|
torder = 2,
|
|
id = td.id,
|
|
ClientId = 0,
|
|
AssetId = td.BookId,
|
|
td.TradeType,
|
|
td.UnderlyingId,
|
|
td.UnderlyingCode,
|
|
BuySell = td.PositionType == PositionTypeFlag.Long ? "买入" : "卖出",
|
|
|
|
TradeNumber = string.Empty,
|
|
ExerciseDate = default(DateTime?),
|
|
OptionType = string.Empty,
|
|
Strike = default(double?),
|
|
IsMoneynessOption = "否",
|
|
TradeDate = default(DateTime?),
|
|
Notional = td.Position,
|
|
|
|
ExchangeOptionCode = td.InstrumentCode
|
|
};
|
|
|
|
#endregion
|
|
|
|
var searchResult = tdQuery.Concat(extdQuery).OrderBy(n => n.torder)
|
|
.ThenByDescending(n => n.TradeNumber).ThenByDescending(n => n.UnderlyingCode).ToSearchList(searchModel);
|
|
|
|
var list = new List<TradePositionMerge>(searchResult.rows.Count());
|
|
|
|
foreach (var td in searchResult.rows)
|
|
{
|
|
var underlying = DataCacheProvider.GetUnderlyingDataSource().GetData(td.UnderlyingCode);
|
|
if (underlying == null)
|
|
{
|
|
continue;
|
|
}
|
|
|
|
var isOtcTrade = td.torder == 1;
|
|
|
|
var tm = new TradePositionMerge
|
|
{
|
|
id = td.id + (isOtcTrade ? "_场外" : "_场内"),
|
|
TradeEncryptId = string.Empty,
|
|
TradeNumber = td.TradeNumber,
|
|
BookId = td.AssetId,
|
|
ClientId = td.ClientId,
|
|
ClientName = DataCacheProvider.GetClientDataSource().GetData(td.ClientId)?.Name,
|
|
AssetBookName = DataCacheProvider.GetAssetUnitDataSource().GetData(td.AssetId)?.Name,
|
|
BuySell = td.BuySell,
|
|
ExerciseDate = td.ExerciseDate,
|
|
OptionType = td.OptionType,
|
|
Strike = td.Strike,
|
|
IsMoneynessOption = td.IsMoneynessOption,
|
|
TradeDate = td.TradeDate,
|
|
TradeType = td.TradeType,
|
|
UnderlyingCode = td.UnderlyingCode,
|
|
UnderlyingId = underlying.id,
|
|
VarietyId = underlying.UnderlyingTypeId,
|
|
UnderlyingAssetClass = underlying.UnderlyingType,
|
|
|
|
TradeAmount = 0,
|
|
};
|
|
|
|
tm.TradeAmount = td.Notional / underlying.CountRatio;
|
|
|
|
if (isOtcTrade)
|
|
{
|
|
tm.TradeEncryptId = DataProtect.Encrypt(td.id);
|
|
}
|
|
else if (td.TradeType == "场内期权")
|
|
{
|
|
var exchangeOption = DataCacheProvider.GetExchangeListOptionDataSource().GetData(td.ExchangeOptionCode);
|
|
if (exchangeOption == null)
|
|
{
|
|
continue;
|
|
}
|
|
tm.ExerciseDate = exchangeOption.MaturityDate;
|
|
tm.OptionType = exchangeOption.OptionType;
|
|
tm.Strike = exchangeOption.Strike;
|
|
}
|
|
tm.CountRatio = underlying.CountRatio;
|
|
list.Add(tm);
|
|
}
|
|
|
|
return new SearchListResult<TradePositionMerge>(searchResult, list);
|
|
}
|
|
|
|
public SearchListResult<TradePositionMerge> GetDatas(TradeScenarioSearchModel req, out bool isEodPosition)
|
|
{
|
|
if (req.PositionDate != null && req.PositionDate < valuedateBLL.ValueDate)
|
|
{
|
|
isEodPosition = true;
|
|
return GetEodPosition(req);
|
|
}
|
|
else
|
|
{
|
|
isEodPosition = false;
|
|
return GetIntradayPosition(req);
|
|
}
|
|
}
|
|
}
|
|
}
|