Files
zszq-trs/YLErpWeb/Controllers/underlying_managerController.cs
T

599 lines
23 KiB
C#

using YLErp.BLL.Calculation;
using YLErp.DBModels;
using YLErp.Modules.DataProviderModule;
using YLErp.Modules.MarginModule;
using YLErp.Modules.UnderlyingModule;
using YLErp.Modules.VolatilityModule;
using YLErp.QdpModule;
namespace YLErp.Web.Controllers
{
public class underlying_managerController : BaseController
{
public static List<SelectListItem> GetVarieties()
{
return VarietyBLL.GetAllvarietyModel().Where(x => x.VarietyCode != "组合标的")
.Select(x => new SelectListItem { Text = x.ShortName, Value = x.id.ToString() }).ToList();
}
[MyAuthorize("基础参数管理-标的管理")]
public ActionResult underlying_managerList()
{
return View();
}
[HttpPost]
public JsonResult underlying_managerQuery(UnderlyingManagerReq req)
{
var bll = new underlying_managerBLL();
var sList = bll.SearchList(req);
return Json(sList);
}
/// <summary>
/// 根据主键获取
/// </summary>
[HttpPost]
public JsonResult underlying_managerGetById(int id, DateTime? exerciseDate = null)
{
var data = DataCacheProvider.GetUnderlyingDataSource().GetData(id);
if (data.IsCommoditySpot() && exerciseDate != null)
{
data.Price = CalculatorHelper.GetCommoditySpotPriceByValueDate(valuedateBLL.ValueDate, exerciseDate.Value, false, data.UnderlyingCode);
}
data.Variety = yldb.variety.Find(data.UnderlyingTypeId);
if (data.UnderlyingInstrumentType != ConsGlobal.InstrumentType.CommodityFutures)
{
data.MaturityDate = DateTime.Today.AddYears(3);
}
return Json(data);
}
/// <summary>
/// 根据品种id获取盯市主力合约
/// </summary>
[HttpPost]
public JsonResult GetMainUnderlyingByVarietyId(int id)
{
var variety = yldb.variety.Where(n => n.id == id).Select(n => new { n.VarietyCode }).FirstOrDefault();
var mainUnderlyingCode = variety == null ? "" : variety.VarietyCode == "AU99" ? "AU9999" : variety.VarietyCode + "00";
var data = yldb.underlying_manager.Where(x => x.UnderlyingTypeId == id && x.UnderlyingCode == mainUnderlyingCode).FirstOrDefault();
data = data ?? new underlying_manager();
return Json(data);
}
private double priceByTradeid(int tradeId, DateTime tradeDate)
{
var trade = yldb.trade.Where(O => O.id == tradeId).FirstOrDefault();
var p1 = underlyingGetByCode(trade.UnderlyingCode, tradeDate);
if (PS.Config.ErpElement.ForwardTradePriceModel == Configuration.Enums.ForwardTradePriceModel.STANDARD && !string.IsNullOrWhiteSpace(trade.BasisUnderlyingCode))
{
var p2 = underlyingGetByCode(trade.BasisUnderlyingCode, tradeDate);
p1 -= p2;
}
return p1;
}
/// <summary>
/// 获取报价参数和合约信息
/// </summary>
private double underlyingGetByCode(string underlyingCode, DateTime? tradeDate = null)
{
var data = DataCacheProvider.GetUnderlyingDataSource().GetData(underlyingCode);
if (data != null)
{
if (tradeDate != null && tradeDate != valuedateBLL.ValueDate)
{
if (EodPriceQueryService.TryGetEodPrice(Convert.ToDateTime(tradeDate), data.UnderlyingCode, out var eodPrice))
{
return eodPrice.ClosePrice;
}
}
else
{
DataCacheProvider.GetUnderlyingDataSource().TryGetPrice(data.UnderlyingCode, out var price);
return price;
}
}
return 0;
}
/// <summary>
/// 获取报价参数和合约信息
/// </summary>
[HttpPost]
public JsonResult underlyingGetById(int id, string voltype, DateTime? tradeDate = null)
{
var data = yldb.underlying_manager.Find(id);
if (data != null)
{
var retUnderlying = new underlying_managershow
{
underlying_manager = data
};
// 获取不超过到期日的实行日
// 1个月,2周,1周,到日期这样的规则向前计算
if (!tradeDate.HasValue)
{
tradeDate = valuedateBLL.ValueDate;
}
data.ExerciseDate = QdpCalendarHelper.GetUnderlyingExerciseDate(data.MaturityDate ?? DateTime.Today.AddMonths(1), tradeDate.Value);
retUnderlying.underlying_manager.Variety = VarietyBLL.GetAllvarietyModel().FirstOrDefault(v => v.id == data.UnderlyingTypeId);
retUnderlying.rules = new UnderlyingParameterService(CurUser).InitialUnderlyingParameter(data.id);
if (!string.IsNullOrEmpty(voltype))
{
var request = new SingleVolatilityRequest
{
QuotationDate = tradeDate.Value,
UnderlyingCode = data.UnderlyingCode,
TradeVolWithBidAsk = false,
UserGroup = CurUser.UserGroup,
VolType = voltype
};
retUnderlying.vols = new VolatilityQueryService(CurUser).GetVolatility(request, true).FirstOrDefault();
//retUnderlying.vols = VolatilityApiHelper.GetVols(tradeDate.Value, new List<string> { voltype }, new List<string> { data.UnderlyingCode }, CurUser.UserGroup).FirstOrDefault();
}
if (data.IsBasket() || data.IsSynthetic())
{
DataCacheProvider.GetUnderlyingDataSource().TryGetPrice(data.UnderlyingCode, out var price);
retUnderlying.underlying_manager.Price = price;
}
if (tradeDate != null && tradeDate != valuedateBLL.ValueDate)
{
if (EodPriceQueryService.TryGetEodPrice(Convert.ToDateTime(tradeDate), data.UnderlyingCode, out var eodPrice))
{
retUnderlying.underlying_manager.Price = eodPrice.ClosePrice;
}
}
return Json(retUnderlying);
}
else
{
return JsonError("标的信息缺失");
}
}
public JsonResult TryGetTradeForwardFinalPrice(int tradeId, int underlyingId, string voltype, DateTime? tradeDate = null)
{
var message = "";
if (!tradeDate.HasValue)
{
tradeDate = valuedateBLL.ValueDate;
}
var observationDates = (from tf in yldb.trade_forward
join t in yldb.trade on tf.TradeId equals t.id
where t.id == tradeId
select tf.ObservationDates).FirstOrDefault();
if (string.IsNullOrEmpty(observationDates))
{
return JsonSuccess("", new { Price = priceByTradeid(tradeId, tradeDate.Value) });
}
var observationDatesList = QdpHelper.GetObservationDatesFromString(observationDates).ToList();
observationDatesList.Sort();
var dateStart = observationDatesList.FirstOrDefault();
if (dateStart >= DateTime.Now)
{
//获取实时价格
return JsonSuccess("", new { Price = priceByTradeid(tradeId, tradeDate.Value) });
}
var dateEnd = observationDatesList.LastOrDefault().AddDays(1);
var tradeDates = QdpCalendarHelper.AllBizDays(dateStart, dateEnd);
tradeDates = observationDatesList.Intersect(tradeDates).ToList();
var trade = yldb.trade.Where(O => O.id == tradeId).FirstOrDefault();
var Prices = EodPriceQueryService.GetEodPriceByUnserialDates(tradeDates, underlyingId);
if (Prices == null || !Prices.Any())
{
message += string.Join(",", tradeDates.Select(o => o.ToShortDateString())) + ":无价格";
return JsonError(message + ";均价计算失败");
}
if (PS.Config.ErpElement.ForwardTradePriceModel == Configuration.Enums.ForwardTradePriceModel.STANDARD && !string.IsNullOrWhiteSpace(trade.BasisUnderlyingCode))
{
var bUmId = DataCacheProvider.GetUnderlyingDataSource().GetData(trade.BasisUnderlyingCode).id;
var P2s = EodPriceQueryService.GetEodPriceByUnserialDates(tradeDates, bUmId);
if (Prices.Count != P2s.Count)
{
return JsonError("均价计算失败,标的1和标的2价格数量不一致!");
}
for (var i = 0; i < Prices.Count; i++)
{
if (Prices[i].ValueDate != P2s[i].ValueDate)
{
return JsonError("均价计算失败,标的1和标的2价格序列日期不一致!");
}
Prices[i].ClosePrice -= P2s[i].ClosePrice;
}
}
var NoPriceDate = tradeDates.Except(Prices.Select(o => o.ValueDate));
if (NoPriceDate.Count() > 0)
{
message += string.Join(",", NoPriceDate.Select(o => o.ToShortDateString())) + ":无价格";
}
var price = Prices.Select(o => o.ClosePrice).Average();
if (!string.IsNullOrWhiteSpace(message))
{
message += ";已从计算中剔除";
}
//return
var retUnderlying = new
{
Price = price,
message
};
return JsonSuccess(message, retUnderlying);
}
public JsonResult GetUnderlyingPrices(List<underlying_manager> underlyings, DateTime valuedate)
{
var underlyingCodes = underlyings.Select(x => x.UnderlyingCode).ToArray();
underlyings = DataCacheProvider.GetUnderlyingDataSource()
.AsQueryable().Where(x => underlyingCodes.Contains(x.UnderlyingCode)).ToList();
if (valuedate < valuedateBLL.ValueDate)
{
var eodPriceProvider = new EodPriceProvider(valuedate).Initialize(underlyingCodes);
foreach (var underlying in underlyings)
{
underlying.Price = eodPriceProvider.GetPrice(underlying.UnderlyingCode, SettlementTypeEnum.ClosePrice);
}
}
return JsonSuccessData(underlyings);
}
/// <summary>
/// 获取报价参数和合约信息
/// </summary>
public JsonResult GetUnderlyingPriceByCode(string code, int tradeId = 0, DateTime? valuedate = null)
{
var data = DataCacheProvider.GetUnderlyingDataSource().GetData(code);
if (data == null)
{
return JsonError("标的信息缺失");
}
var price = data.Price ?? 0;
var systemDate = valuedateBLL.ValueDate;
var trade = yldb.trade.Where(n => n.id == tradeId)?.FirstOrDefault();
var settlementFlag = (int?)trade?.SettlementFlag ?? 0;
var settlementType = (int?)trade?.SettlementType ?? 0;
//厦门象屿参考价时10点15分切换交易日
if (PS.Config.Company == Configuration.CompanyEnum.厦门象屿
&& settlementType == (int)SettlementTypeEnum.ReferencePrice)
{
systemDate = Modules.SpecialModule.XiaMenXiangYuHelper.GetRefernceValueDate();
}
if (valuedate == null || valuedate > systemDate)
{
return JsonSuccessData(data.Price);
}
if (data.IsBond())
{
//系统日期当天优先取日终价格如果取不到则使用行情价格
if (EodPriceQueryService.TryGetBondEodPrice(valuedate.Value, code, out var eodPrice))
{
price = eodPrice.GetPrice((SettlementTypeEnum)settlementType);
}
else
{
price = price * Convert.ToDouble(ConsGlobal.bondPriceMultiple);
}
return JsonSuccessData(price);
}
else
{
//系统日期当天优先取日终价格如果取不到则使用行情价格
if (EodPriceQueryService.TryGetEodPrice(valuedate.Value, code, out var eodPrice))
{
price = eodPrice.GetPrice((SettlementTypeEnum)settlementType);
}
}
if (valuedate != systemDate)
{
return JsonError("获取不到日终价格");
}
return JsonSuccessData(price);
}
/// <summary>
/// 获取报价参数和合约信息
/// </summary>
[HttpPost]
public JsonResult syntheticUnderlyingGetByCode(string underlyingCode, DateTime? tradeDate = null)
{
var data = DataCacheProvider.GetUnderlyingDataSource().GetData(underlyingCode);
if (data != null)
{
new UnderlyingParameterService(CurUser).InitialUnderlyingParameter(data.id);
var retData = new underlying_managershow();
// 获取不超过到期日的实行日
// 1个月,2周,1周,到日期这样的规则向前计算
if (!tradeDate.HasValue)
{
tradeDate = valuedateBLL.ValueDate;
}
data.ExerciseDate = QdpCalendarHelper.GetUnderlyingExerciseDate(data.MaturityDate ?? DateTime.Today, tradeDate.Value);
var synthetic = new SyntheticUnderlyingPriceService(CurUser).GetPriceModel(underlyingCode);
data.Price = synthetic.Price;
retData.synthetic = synthetic;
retData.underlying_manager = data;
retData.underlying_manager.Variety = VarietyBLL.GetAllvarietyModel()
.FirstOrDefault(x => x.id == data.UnderlyingTypeId) ?? new Variety { VarietyCode = "组合标的", VarietyName = "组合标的", ShortName = "" };
return JsonSuccess(null, retData);
}
else
{
return JsonError("标的信息缺失");
}
}
/// <summary>
/// 更新underlying_manager
/// </summary>
[HttpPost]
public JsonResult UpdateById(int id, UnderlyingManagerReq data)
{
new underlying_managerBLL().UpdateSingle(id, data);
//启用时如果没有波动率,设置波动率为规则 OTC-5469
return JsonSuccess("更新成功", data);
}
/// <summary>
/// 批量更新underlying_manager
/// </summary>
public JsonResult UpdateByIds(int[] ids, UnderlyingManagerReq data)
{
if (ids == null && ids.Length == 0)
{
return JsonError("请选择要更新的标的", data);
}
var launchState = data.LaunchState;
if (data.isCheckAll)
{
//id从条件中选
var bll = new underlying_managerBLL();
var userVarieties = CurUser.GetUserVarietyIds();
data.rows = 9999999;
data.page = 1;
data.LaunchState = null;//查询时,不需要根据这个
var sList = bll.SearchList(data, userVarieties);
ids = sList.rows.Select(r => r.id).ToArray();
}
var unlist = yldb.underlying_manager.Where(u => ids.Contains(u.id)).ToList();
unlist.ForEach(x => x.LaunchState = launchState);
yldb.SaveChanges();
return JsonSuccess("更新成功", data);
}
/// <summary>
/// 启用/取消启用所有ST股
/// </summary>
public JsonResult UpdateLaunchStateForSTStock(UnderlyingManagerReq data)
{
var allST = yldb.underlying_manager.Where(x => x.UnderlyingInstrumentType == "Stock" && x.UnderlyingName.Contains("ST"));
foreach (var u in allST)
{
u.LaunchState = data.LaunchState;
}
yldb.SaveChanges();
return JsonSuccess("更新成功");
}
public ActionResult underlying_managerView(string enid)
{
var intid = DataProtectHelper.DecryptInt(enid);
var r = new UnderlyingDalService(CurUser).GetDetail(intid);
var blocks = yldb.UnderlyingBlockConfig.Select(n => new { n.id, n.Name }).ToArray();
foreach (var item in blocks)
{
ViewData["block" + item.id] = item.Name;
}
new Modules.DicForTranslationModule.DicForTranslationService(CurUser).GetTransWord(r);
return View(r);
}
public ActionResult underlying_managerEdit(string enid)
{
var model = new UnderlyingEditModel
{
Markets = JsDataModel.GetMarkets()
};
if (string.IsNullOrEmpty(enid) || enid == "0")
{
model.Underlying = new underlying_manager()
{
VolumeStep = 1 //新增默认步进数量为1
};
}
else
{
var intid = DataProtectHelper.DecryptInt(enid);
var udm = yldb.underlying_manager.Find(intid);
if (udm == null)
{
return ShowError("数据不存在");
}
if (udm.IsFutures())
{
if (udm.MaturityDate == null && !string.IsNullOrEmpty(udm.UnderlyingCode))
{
udm.MaturityDate = QdpHelper.defaultMaturityDateFromContract(udm.UnderlyingCode);
}
}
else if (udm.IsBond())
{
model.Bond = JsonHelper.Deserialize<UnderlyingBond>(udm.ExJson);
}
model.Underlying = udm;
}
new Modules.DicForTranslationModule.DicForTranslationService(CurUser).GetTransWord(model.Underlying);
return View(model);
}
[HttpPost]
public JsonResult underlying_managerEditJson(UnderlyingSaveModel model)
{
if (model == null)
{
return JsonError("数据不能为空");
}
if (string.IsNullOrEmpty(model.UnderlyingInstrumentType))
{
return JsonError("资产类型 必须填写");
}
if (ConsGlobal.InstrumentType.IsBond(model.UnderlyingInstrumentType))
{
model.ExJson = JsonHelper.Serialize(model.Bond);
}
var r = new UnderlyingDalService(CurUser).SaveUnderlyingData(model);
YLErp.Modules.UnderlyingModule.UnderlyingHelper.ClearMarginRateCache(model.UnderlyingCode);
return JsonSuccess("更新成功", r);
}
public JsonResult GetUnderlyingByCode(string code)
{
if (string.IsNullOrWhiteSpace(code))
{
return JsonError("请输入代码");
}
var underlying = underlying_managerBLL.GetAllLiveunderlying_managerModel().FirstOrDefault(u => u.UnderlyingCode == code);
if (underlying == null)
{
return JsonError("系统中没有相关的标的");
}
return JsonSuccess("", underlying);
}
/// <summary>
/// 预付金参数
/// </summary>
public ActionResult MarginParams()
{
return View();
}
/// <summary>
/// 导入预付金参数
/// </summary>
public ActionResult ImportMarginParams(IFormFile file)
{
MarginParamsImportResult result = null;
if (Path.GetExtension(file?.FileName)?.ToLowerInvariant() != ".xlsx")
{
ViewData["ERROR"] = "请上传xlsx格式文件";
}
else
{
try
{
using var openStream = file.OpenReadStream();
result = new MarginParamsImportService(CurUser).ImportUnderlying(openStream);
}
catch (Exception ex)
{
LogFactory.GetLogger("ImportMarginParams").Error(ex);
ViewData["ERROR"] = "导入出错:" + ex.Message;
}
}
return View("MarginParams", result);
}
/// <summary>
/// 导入标的
/// </summary>
public JsonResult UploadUnderlying()
{
if (Request.Form.Files.Count == 0)
{
return JsonError("上传文件不存在");
}
var file = Request.Form.Files[0];
if (!System.IO.Path.GetExtension(file.FileName).Equals(".xlsx", StringComparison.OrdinalIgnoreCase))
{
return JsonError("请上传Excel(.xlsx)格式文件");
}
using var openStream = file.OpenReadStream();
new UnderlyingImportService(CurUser).ImportExcel(openStream, out var TotalNum, out var SuccessNum);
return Json(new
{
success = true,
totalNum = TotalNum,
successNum = SuccessNum,
});
}
/// <summary>
/// 导出预付金参数
/// </summary>
public ActionResult ExportMarginParams()
{
var bytes = new MarginParamsExportService(CurUser).UnderlyingExport();
return File(bytes, xlsxMimeType, "标的预付金参数.xlsx");
}
public JsonResult SubmitParameters(IEnumerable<underlying_parameter> datas)
{
_ = new UnderlyingParameterService(CurUser).SaveDatas(datas);
return JsonSuccess("更新成功", datas);
}
public ActionResult pop_parameterEdit(int under_id)
{
var Underlying = yldb.underlying_manager.Find(under_id);
ViewBag.Underlying = Underlying;
ViewBag.Underlying_Params = new UnderlyingParameterService(CurUser).InitialUnderlyingParameter(under_id);
return View(Underlying);
}
public JsonResult AjaxSetUnderlyingPrice(int id, double price)
{
var um = yldb.underlying_manager.Find(id);
if (um == null)
{
throw new ServiceException("没有找到标的");
}
um.Price = price;
yldb.SaveChanges();
return JsonSuccess();
}
}
}