using BaseOUDAL; using Org.BouncyCastle.Ocsp; using Qdp.Pricing.Library.Base.Utilities; using System; using System.Collections.Generic; using System.Data; using System.Linq; using System.Linq.Dynamic.Core; using YLErp.Helpers; using YLErp.Model; using YLErp.Office; using Newtonsoft.Json; using OfficeOpenXml; using YieldChain.Commons; using YLErp.Abstract; using Microsoft.Extensions.DependencyInjection; using YLErp.Cache; namespace YLErp.Modules.SwapModule { public class SwapRateService : YLBaseService { IKafkaProduce kafkaProduceHelper; public SwapRateService(OptUserInfo userInfo) : base(userInfo) { kafkaProduceHelper = YLServiceLocator.ServiceProvider.GetService(); } /// /// 查询阶梯费率 /// public SearchListResult SearchList(SwapRateSearchRequest req) { var predicate = PredicateBuilder.Create(n => 1 == 1); if (req.OptDateStart.HasValue) { predicate = predicate.And(n => n.opt_time >= req.OptDateStart.Value); } if (req.OptDateEnd.HasValue) { predicate = predicate.And(n => n.opt_time <= req.OptDateEnd.Value); } if (req.ClientIds.Count > 0) { predicate = predicate.And(n => req.ClientIds.Contains(n.ClientId)); } if (!string.IsNullOrEmpty(req.ClientNumber)) { predicate = predicate.And(x => x.ClientNumber.Contains(req.ClientNumber.Trim())); } if (req.TakeEffectDate.HasValue) { predicate = predicate.And(n => n.TakeEffectDate == req.TakeEffectDate); } if (!string.IsNullOrEmpty(req.OptName)) { predicate = predicate.And(n => n.opt_name == req.OptName); } var rateQuery = DbContext.swap_rate.Where(predicate); var clientQuery = DataCacheProvider.GetClientDataSource().AsQueryable(); if (string.IsNullOrEmpty(req.sidx)) { req.sidx = "create_time"; req.sord = "desc"; } var retListResult = rateQuery.ToSearchList(req); foreach (var item in retListResult.rows) { var client = clientQuery.FirstOrDefault(x => x.id == item.ClientId); item.ClientName = client?.Name; } return retListResult; } /// /// 保存互换费率 /// /// /// public void SaveSwapRate(SwapRate req, IYLCache ylCache) { var changeClient = DataCacheProvider.GetClientDataSource().GetData(req.ClientId); req.ClientNumber = changeClient?.Number; req.ClientName = changeClient?.Name; ValidateSwapRate(req); string changeStr = string.Empty; string changeTitle = "新增"; if (req.id > 0) { var swapRate = DbContext.swap_rate.Find(req.id); if (swapRate == null) { throw new ServiceException("未找到该阶梯费率"); } var client = DataCacheProvider.GetClientDataSource().GetData(swapRate.ClientId); swapRate.ClientNumber = client?.Number; swapRate.ClientName = client?.Name; var changeList = DataChangeHelper.GetDataChanges(swapRate, req); changeStr = changeList.ToJson(); changeTitle = "编辑"; swapRate.ClientId = req.ClientId; swapRate.ClientNumber = req.ClientNumber; swapRate.TakeEffectDate = req.TakeEffectDate; swapRate.TempRateIsPercent = req.TempRateIsPercent; swapRate.TempRate = req.TempRate; swapRate.BaseRate = req.BaseRate; swapRate.BaseRateIsPercent = req.BaseRateIsPercent; swapRate.DiscountAccDown = req.DiscountAccDown; swapRate.DiscountRateIsPercent = req.DiscountRateIsPercent; swapRate.DiscountRate = req.DiscountRate; // swapRate.FrontDeskCharge = req.FrontDeskCharge; // swapRate.FrontDeskChargeIsPercent = req.FrontDeskChargeIsPercent; // swapRate.BackDeskCharge = req.BackDeskCharge; // swapRate.BackDeskChargeIsPercent = req.BackDeskChargeIsPercent; swapRate.OfflineRate = req.OfflineRate; swapRate.SetOpt(UserId, UserName); // 盘中修改了阶梯费率,存储到redis中 ylCache.StringSetWithNoPrefix("TRS:Update:ClientRate:" + swapRate.ClientId, swapRate.id, TimeSpan.FromHours(8)); } else { req.SetCreator(UserId, UserName); req.SetOpt(UserId, UserName); DbContext.swap_rate.Add(req); } DbContext.SaveChanges(); new SwapRateLogService(UserInfo).AddSwapRateLog(0, req.id, changeTitle, changeStr, null); } /// /// 校验数据 /// /// /// private void ValidateSwapRate(SwapRate req) { if (req.BaseRate == null && req.TempRate == null) { throw new ServiceException("临时费率或基础费率不能为空"); } if (req.DiscountRate.HasValue && req.DiscountAccDown == null) { throw new ServiceException("优惠累计量下限不能为空"); } if (!req.DiscountRate.HasValue && req.DiscountAccDown.HasValue) { throw new ServiceException("优惠累计量下限有值的情况,优惠汇率不能为空"); } if (DbContext.swap_rate.Any(x => x.ClientId == req.ClientId && x.id != req.id && x.TakeEffectDate == req.TakeEffectDate)) { throw new ServiceException($"该客户在{req.TakeEffectDate:D}已经存在阶梯费率"); } } /// /// 删除阶梯费率 /// /// /// public int DeleteSwapRate(int id) { var swapRate = DbContext.swap_rate.Find(id); if (swapRate == null) { throw new ServiceException("未找到该阶梯费率"); } DbContext.swap_rate.Remove(swapRate); DbContext.SaveChanges(); return swapRate.ClientId; } /// /// 获取详细 /// /// /// /// public SwapRate GetSwapRate(int id) { var swapRate = DbContext.swap_rate.Find(id); if (swapRate == null) { throw new ServiceException("未找到该阶梯费率"); } var client = DataCacheProvider.GetClientDataSource().GetData(swapRate.ClientId); swapRate.ClientName = client?.Name; swapRate.ClientNumber = client?.Number; return swapRate; } /// /// 阶梯费率导入 excel /// /// 上传的文件 /// 总条数 /// 成功条数 public List ImportSwapRateFromExcel(Stream streamIn, out int totalNum, out int successNum) { totalNum = 0; successNum = 0; var rowIndex = 0; List clientIds = new List(); var trans = DbContext.Database.BeginTransaction(); try { var ds = Office.ExcelHelper.ReadExcelAsDataSet(streamIn, new[] { 0 }, 0); if (ds.Tables.Count < 1 || ds.Tables[0].Rows.Count < 2) { throw new ServiceException("读取导入数据失败:数据为空") { Tag = "111" }; } var table = ds.Tables[0]; var reader = new DataRowReaderHelper(table); rowIndex = 1; totalNum = table.Rows.Count - rowIndex; var clientList = DataCacheProvider.GetClientDataSource().AsQueryable().ToList(); foreach (var row in table.Rows.Cast().Skip(rowIndex)) { rowIndex++; if (row.ItemArray.All(n => string.IsNullOrWhiteSpace(n?.ToString()))) { totalNum--; continue; } reader.SetDataRow(row, rowIndex); var swapRate = new SwapRate(); swapRate.ClientNumber = reader.GetString("客户编号", true); swapRate.TakeEffectDate = reader.GetDate("生效日期", true).Value; var client = clientList.FirstOrDefault(x => x.Number == swapRate.ClientNumber); if (client == null) { throw new ServiceException($"找不到客户编号为{swapRate.ClientNumber}的客户"); } swapRate.ClientId = client.id; clientIds.Add(client.id); var tempRate = reader.GetString("临时费率"); if (!string.IsNullOrEmpty(tempRate)) { decimal rate = 0; if (tempRate.EndsWith("%")) { swapRate.TempRateIsPercent = true; tempRate = tempRate.Replace("%", ""); decimal.TryParse(tempRate, out rate); rate = rate / 100; } else { swapRate.TempRateIsPercent = true; decimal.TryParse(tempRate, out rate); } swapRate.TempRate = rate; } var baseRate = reader.GetString("基础费率"); if (!string.IsNullOrEmpty(baseRate)) { decimal rate = 0; if (baseRate.EndsWith("%")) { swapRate.BaseRateIsPercent = true; baseRate = baseRate.Replace("%", ""); decimal.TryParse(baseRate, out rate); rate = rate / 100; } else { swapRate.BaseRateIsPercent = true; decimal.TryParse(baseRate, out rate); } swapRate.BaseRate = rate; } var disAccRate = reader.GetString("优惠费率"); if (!string.IsNullOrEmpty(disAccRate)) { decimal rate = 0; if (disAccRate.EndsWith("%")) { swapRate.DiscountRateIsPercent = true; disAccRate = disAccRate.Replace("%", ""); decimal.TryParse(disAccRate, out rate); rate = rate / 100; } else { swapRate.DiscountRateIsPercent = true; decimal.TryParse(disAccRate, out rate); } swapRate.DiscountRate = rate; } //var frontRate = reader.GetString("现券对冲交易费用"); //if (!string.IsNullOrEmpty(frontRate)) //{ // if (frontRate.EndsWith("‱")) // { // swapRate.FrontDeskChargeIsPercent = true; // frontRate = frontRate.Replace("‱", ""); // } // decimal.TryParse(frontRate, out var rate); // swapRate.FrontDeskCharge = rate * 0.0001m; //} //var backRate = reader.GetString("现券对冲结算费用"); //if (!string.IsNullOrEmpty(backRate)) //{ // if (backRate.EndsWith("‱")) // { // swapRate.BackDeskChargeIsPercent = true; // backRate = backRate.Replace("‱", ""); // } // decimal.TryParse(backRate, out var rate); // swapRate.BackDeskCharge = rate * 0.0001m; //} swapRate.DiscountAccDown = reader.GetDecimal("优惠累计量下限"); // 处理线下费率 var offlineRate = reader.GetString("线下费率"); LogFactory.GetLogger("导入阶梯费率").Info($"第{rowIndex}行,原始线下费率值: '{offlineRate}', IsNullOrEmpty: {string.IsNullOrEmpty(offlineRate)}"); if (!string.IsNullOrEmpty(offlineRate)) { LogFactory.GetLogger("导入阶梯费率").Info($"第{rowIndex}行,线下费率非空,准备解析: '{offlineRate}'"); decimal rate = 0; if (offlineRate.EndsWith("%")) { LogFactory.GetLogger("导入阶梯费率").Info($"第{rowIndex}行,线下费率是百分比格式: '{offlineRate}'"); offlineRate = offlineRate.Replace("%", ""); if (decimal.TryParse(offlineRate, out rate)) { rate /= 100; LogFactory.GetLogger("导入阶梯费率").Info($"第{rowIndex}行,百分比解析成功: {offlineRate}% -> {rate}"); } else { LogFactory.GetLogger("导入阶梯费率").Error($"第{rowIndex}行,百分比数值解析失败: '{offlineRate}'"); rate = 0; } } else { LogFactory.GetLogger("导入阶梯费率").Info($"第{rowIndex}行,线下费率不是百分比格式: '{offlineRate}', 尝试直接解析"); // 如果不是百分比格式,直接尝试解析为小数 if (!decimal.TryParse(offlineRate, out rate)) { // 解析失败时的处理 LogFactory.GetLogger("导入阶梯费率").Error($"第{rowIndex}行,线下费率解析失败: '{offlineRate}'"); rate = 0; } else { LogFactory.GetLogger("导入阶梯费率").Info($"第{rowIndex}行,直接解析成功: {offlineRate} -> {rate}"); } } swapRate.OfflineRate = rate; LogFactory.GetLogger("导入阶梯费率").Info($"第{rowIndex}行,最终设置OfflineRate为: {rate}"); } else { LogFactory.GetLogger("导入阶梯费率").Info($"第{rowIndex}行,线下费率为null或空字符串"); } ValidateSwapRate(swapRate); swapRate.SetCreator(UserId, UserName); swapRate.SetOpt(UserId, UserName); DbContext.swap_rate.Add(swapRate); DbContext.SaveChanges(); new SwapRateLogService(UserInfo).AddSwapRateLog(0, swapRate.id, "新增", null, "导入"); successNum++; } trans.Commit(); trans.Dispose(); return clientIds; } catch (Exception ex) { trans.Rollback(); trans.Dispose(); LogFactory.GetLogger("导入阶梯费率").Error(ex); throw new ServiceException($"第{rowIndex}行,发生错误:{ex.Message}"); } } /// /// 阶梯费率导出 /// /// /// /// public byte[] exprotSwapRateExcel(SwapRateSearchRequest req) { //获取数据 var ret = SearchList(req); List list = new List(); foreach (var item in ret.rows) { SwapRateExportModel exportModel = new SwapRateExportModel(); exportModel.ClientNumber = item.ClientNumber; exportModel.ClientName = item.ClientName; exportModel.TakeEffectDate = item.TakeEffectDate.OtcFormatDate(); exportModel.BaseRate = item.BaseRateIsPercent ? item.BaseRate.OtcFormatPercent(4) : item.BaseRate.OtcFormatMoney(true); exportModel.TempRate = item.TempRateIsPercent ? item.TempRate.OtcFormatPercent(4) : item.TempRate.OtcFormatMoney(true); exportModel.DiscountRate = item.DiscountRateIsPercent ? item.DiscountRate.OtcFormatPercent(4) : item.DiscountRate.OtcFormatMoney(true); exportModel.DiscountAccDown = item.DiscountAccDown.OtcFormatMoney(true); //exportModel.FrontDeskCharge = item.FrontDeskChargeIsPercent == true ? item.FrontDeskCharge.OtcFormatTenThousandsPercent(4) : item.FrontDeskCharge.OtcFormatMoney(true); //exportModel.BackDeskCharge = item.BackDeskChargeIsPercent == true ? item.BackDeskCharge.OtcFormatTenThousandsPercent(4) : item.BackDeskCharge.OtcFormatMoney(true); exportModel.OfflineRate = item.OfflineRate.OtcFormatPercent(4); list.Add(exportModel); } var tplFilePath = OtcAppContext.MapPath("/App_Docs"); var sourceFileName = Path.Combine(tplFilePath, "导出模板", "阶梯费率导出模板.xlsx"); var modelDict = new Dictionary(); var model = new { list = list }; modelDict.Add("Sheet1", model); ExcelPackage.LicenseContext = LicenseContext.NonCommercial; return new ExcelTemplateGenerator().SetTemplateFile(sourceFileName).SetTemplateData(modelDict).Output(); } } }