605 lines
25 KiB
C#
605 lines
25 KiB
C#
using BaseOUDAL;
|
|
using DocumentFormat.OpenXml.Office2010.Excel;
|
|
using OfficeOpenXml.Drawing;
|
|
using Org.BouncyCastle.Ocsp;
|
|
using System.Text;
|
|
using YieldChain.Helpers;
|
|
using YLErp.BLL;
|
|
using YLErp.BLL.Eod;
|
|
using YLErp.DBModels.Enums;
|
|
using YLErp.Model.Enum;
|
|
using YLErp.Modules.RiskModule;
|
|
using YLErp.Modules.SalesModule;
|
|
using YLErp.Modules.SwapModule;
|
|
using YLErp.Modules.SystemModule;
|
|
|
|
namespace YLErp.Modules.TradeModule.DealModule
|
|
{
|
|
/// <summary>
|
|
/// 交易确认服务
|
|
/// </summary>
|
|
public class TradeConfirmService : TradeServiceBase
|
|
{
|
|
readonly DateTime confirmDate;
|
|
readonly ClientDBContext clientDB;
|
|
|
|
public TradeConfirmService(YLBaseService baseService) : base(baseService)
|
|
{
|
|
confirmDate = SystemValueDate;
|
|
clientDB = DbContextFactory.GetClientDbContext(OptUser);
|
|
}
|
|
|
|
public TradeConfirmService(OptUserInfo userInfo) : base(userInfo)
|
|
{
|
|
confirmDate = SystemValueDate;
|
|
clientDB = DbContextFactory.GetClientDbContext(OptUser);
|
|
}
|
|
|
|
public TradeConfirmService(OptUserInfo userInfo, YLContext dbContext) : base(userInfo, dbContext)
|
|
{
|
|
confirmDate = SystemValueDate;
|
|
clientDB = DbContextFactory.GetClientDbContext(OptUser);
|
|
}
|
|
|
|
/// <summary>
|
|
/// 2021-02-04改造:批量确认因为耗时太长,用户多页面(交易列表,今日交易)并发确认导致生成多条期权费资金记录
|
|
/// </summary>
|
|
public TradeConfirmResultModel tradeConfirm(IEnumerable<int> tradeids, bool ignoreMoneyCheck = false, bool isSkipApproval = false)
|
|
{
|
|
if (tradeids is null || !tradeids.Any(n => n > 0))
|
|
{
|
|
throw new ArgumentException("tradeids 参数无效", nameof(tradeids));
|
|
}
|
|
|
|
//将交易ID集合转换为Set结构
|
|
var idSet = tradeids.ToHashSet();
|
|
var isBatch = idSet.Count > 1;
|
|
|
|
//首先查找是否有父交易ID存在的情况,找出父交易下面的所有子交易ID集合
|
|
var subTds = DbContext.trade.Where(n => n.ParentTradeId > 0 && n.ValidState != "InValid" && idSet.Contains(n.ParentTradeId) && (n.IsGroup == 0 || n.IsGroup == 2 && n.TradeType == "收益互换") && n.TradeStatus != "确认成交")
|
|
.Select(n => new { n.id, n.ParentTradeId, n.IsGroup }).ToArray();
|
|
|
|
if (subTds.Any())
|
|
{
|
|
foreach (var std in subTds)
|
|
{
|
|
idSet.Add(std.id);
|
|
if (std.IsGroup == 0)
|
|
{
|
|
idSet.Remove(std.ParentTradeId);
|
|
}
|
|
}
|
|
}
|
|
|
|
var hasTradeProcess = HasTradeProcess();
|
|
|
|
var sbError = new StringBuilder();
|
|
var result = new TradeConfirmResultModel
|
|
{
|
|
confirmedTradeIds = new List<int>(),
|
|
changeConfirmPaths = new List<string>()
|
|
};
|
|
|
|
HashSet<int> idCache = new HashSet<int>();
|
|
foreach (var tid in idSet)
|
|
{
|
|
var lockKeyId = "tradeConfirm_" + tid;
|
|
|
|
//对每个交易单独处理基本上可以解决并发问题
|
|
//为了更加保险增加多线程并发锁定
|
|
lock (Helpers.LockHelper.Acquire(lockKeyId, 300))
|
|
{
|
|
var pid = subTds.Where(O => O.id == tid).FirstOrDefault()?.ParentTradeId ?? 0;
|
|
var temp = ConfirmTrade(tid: tid,
|
|
isBatch: isBatch,
|
|
hasTradeProcess: hasTradeProcess,
|
|
ignoreMoneyCheck: ignoreMoneyCheck,
|
|
isSkipApproval: isSkipApproval,
|
|
confirmedTradeIds: result.confirmedTradeIds,
|
|
changeConfirmPaths: result.changeConfirmPaths,
|
|
continueQuotaCheck: idCache.Contains(pid));
|
|
if (pid > 0)
|
|
{
|
|
idCache.Add(pid);
|
|
}
|
|
|
|
result.type = temp.RetCode.ToString();
|
|
|
|
if (temp.RetCode == TradeOpenRetCode.LackOfMoney)
|
|
{
|
|
sbError.AppendLine(temp.ErrorMsg);
|
|
result.TradeId = temp.Trade.id;
|
|
result.LackOfMoney = true;
|
|
break;
|
|
}
|
|
if (temp.RetCode == TradeOpenRetCode.QuotaTrialError || temp.RetCode == TradeOpenRetCode.FundStatus)
|
|
{
|
|
result.LackOfMoney = true;
|
|
result.TrialDataId = temp.TrialDataId;
|
|
result.TradeId = temp.Trade.id;
|
|
sbError.AppendLine(temp.ErrorMsg);
|
|
break;
|
|
}
|
|
|
|
if (!string.IsNullOrEmpty(temp.ErrorMsg))
|
|
{
|
|
sbError.AppendLine(temp.ErrorMsg);
|
|
}
|
|
|
|
Helpers.LockHelper.Release(lockKeyId);
|
|
}
|
|
}
|
|
|
|
DbContext.SaveChanges();
|
|
|
|
result.errorMsg = sbError.ToString();
|
|
|
|
return result;
|
|
}
|
|
|
|
/// <summary>
|
|
/// 确认交易
|
|
/// </summary>
|
|
/// <param name="tid">交易Id</param>
|
|
/// <param name="isBatch"></param>
|
|
/// <param name="hasTradeProcess"></param>
|
|
/// <param name="ignoreMoneyCheck">忽略交易限额/资金和检查</param>
|
|
/// <param name="isSkipApproval"></param>
|
|
/// <param name="confirmedTradeIds"></param>
|
|
/// <param name="changeConfirmPaths"></param>
|
|
/// <param name="continueQuotaCheck"></param>
|
|
/// <returns></returns>
|
|
private TradeOpenResult ConfirmTrade(int tid, bool isBatch, bool hasTradeProcess,
|
|
bool ignoreMoneyCheck, bool isSkipApproval, List<int> confirmedTradeIds, List<string> changeConfirmPaths, bool continueQuotaCheck = false)
|
|
{
|
|
var td = DbContext.trade.FirstOrDefault(t => t.id == tid);
|
|
var result = new TradeOpenResult(td ?? new trade());
|
|
|
|
if (td == null)
|
|
{
|
|
result.ErrorMsg = $"系统编号:{tid},找不到交易数据,不能被确认";
|
|
return result;
|
|
}
|
|
|
|
if (td.TradeType == "结构化交易" && td.IsGroup == 0)
|
|
{
|
|
result.ErrorMsg = $"系统内部错误,不应出现结构化交易类型的确认处理,交易编号:{td.TradeNumber}";
|
|
return result;
|
|
}
|
|
|
|
//判断如果为待确认的则修改状态为确认状态
|
|
if (!ConsTrade.UnConfirmTradeStatusList.Contains(td.TradeStatus) && ((td.TradeStatus == "审批中" && !isSkipApproval) || td.TradeStatus == "确认成交"))
|
|
{
|
|
//result.ErrorMsg = $"客户:{td.ClientName},交易编号:{td.TradeNumber},状态为:{td.TradeStatus},不能被确认";
|
|
result.RetCode = TradeOpenRetCode.Success;
|
|
return result;
|
|
}
|
|
if (ConsTrade.TradeStatusAfterAndWithOutConfirmed.Contains(td.TradeStatus))
|
|
{
|
|
result.ErrorMsg = $"客户:{td.ClientName},交易编号:{td.TradeNumber},状态为:{td.TradeStatus},不能被确认";
|
|
return result;
|
|
}
|
|
// 校验定义文件类型互换
|
|
new SwapTradeService(UserInfo).ExistLongShortTrade(td);
|
|
//判断交易对手方信息是否允许确认
|
|
|
|
var client = DataCacheProvider.GetClientDataSource().GetData(td.ClientId);
|
|
|
|
if (client == null)
|
|
{
|
|
result.ErrorMsg = $"未找到客户信息:{td.ClientName}";
|
|
return result;
|
|
}
|
|
if (!ignoreMoneyCheck && !continueQuotaCheck)
|
|
{
|
|
result = CheckTradeConfirmRule(result, td, isSkipApproval);
|
|
|
|
if (!string.IsNullOrWhiteSpace(result.ErrorMsg))
|
|
{
|
|
return result;
|
|
}
|
|
|
|
result = CheckClientRating(result, client, td);
|
|
|
|
if (!string.IsNullOrWhiteSpace(result.ErrorMsg))
|
|
{
|
|
return result;
|
|
}
|
|
|
|
var trialService = new QuotaMonitorService(this);
|
|
if (!trialService.QuotaCheck(ref result))
|
|
{
|
|
return result;
|
|
}
|
|
}
|
|
var history = "确认交易";
|
|
|
|
if (ignoreMoneyCheck)
|
|
{
|
|
history = "交易特批-" + history;
|
|
|
|
if (isBatch)
|
|
{
|
|
history = "特权账户批量确认自动" + history;
|
|
}
|
|
}
|
|
//进入交易审批流程
|
|
if (hasTradeProcess && !isSkipApproval)
|
|
{
|
|
td.TradeOldStatus = td.TradeStatus;
|
|
td.OptId = UserId;
|
|
td.OptName = UserName;
|
|
td.OptDate = OptDate;
|
|
int passStatus = new ApprovalProcessService(OptUser).CheckTradeApprovalStep(td, OptUser.UserId);
|
|
if (passStatus == 0)
|
|
{
|
|
td.TradeStatus = ConsTrade.确认成交;
|
|
//删掉trade_check相关的复核数据
|
|
new TradeCheckService(this).DeleteTradeCheck(td.id);
|
|
var p = new ProcessTradeLog()
|
|
{
|
|
TradeId = td.id,
|
|
ProcessType = "TradeProcess",
|
|
ProcessStatus = ProcessTradeStatus.通过审批.ToString(),
|
|
Log = "",
|
|
OptId = UserId,
|
|
CreateTime = DateTime.Now
|
|
};
|
|
DbContext.processtradelog.Add(p);
|
|
new SalesCommissionDataService(OptUser).SetCommissionVaild(td.id);
|
|
EditReportStatus(td.id);
|
|
SwapTradeConfirm(td, history,false,optlog:"手工操作");
|
|
}
|
|
else if (passStatus == -3)
|
|
{
|
|
result.ErrorMsg = $"当前存在分支交易审批流程,检测到申请人不满足任意一个分支进入条件,无法提交审批,请更换申请人或调整审批组";
|
|
return result;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
td.TradeOldStatus = td.TradeStatus;
|
|
td.OptId = UserId;
|
|
td.OptName = UserName;
|
|
td.OptDate = OptDate;
|
|
td.TradeStatus = ConsTrade.确认成交;
|
|
//删掉trade_check相关的复核数据
|
|
new TradeCheckService(this).DeleteTradeCheck(td.id);
|
|
td.ProcessOrderId = ProcessTradeLog.审批通过;
|
|
td.CheckTradeUpdate = Convert.ToInt32(TradeCheckEnum.StatusOfNew);
|
|
td.ProcessOptDate = DateTime.Now;
|
|
td.ProcessStatus = ProcessTradeStatus.通过审批.ToString();
|
|
var p = new ProcessTradeLog()
|
|
{
|
|
TradeId = td.id,
|
|
ProcessType = "TradeProcess",
|
|
ProcessStatus = ProcessTradeStatus.通过审批.ToString(),
|
|
Log = "",
|
|
OptId = UserId,
|
|
CreateTime = DateTime.Now
|
|
};
|
|
DbContext.processtradelog.Add(p);
|
|
new SalesCommissionDataService(OptUser).SetCommissionVaild(td.id);
|
|
EditReportStatus(td.id);
|
|
SwapTradeConfirm(td, history, false, optlog: "手工操作");
|
|
}
|
|
|
|
new ClientCashInCashOutService(this).SaveClientCashInCashOut(td);
|
|
|
|
DbContext.SaveChanges();
|
|
|
|
//生成变更确认书(如果走审批流程应该在审批流程走完以后生成才对!!!)
|
|
if (PS.Config.TradeElement.IsGenerateAmendDoc)
|
|
{
|
|
try
|
|
{
|
|
var filepath = new ChangeConfirmBookGenerator(this).GenerateChangeConfirmBook(td.id, out _);
|
|
|
|
if (!string.IsNullOrEmpty(filepath))
|
|
{
|
|
changeConfirmPaths.Add(filepath);
|
|
}
|
|
}
|
|
catch (Exception ex)
|
|
{
|
|
LogFactory.GetLogger("生成变更确认书").Error(ex);
|
|
}
|
|
}
|
|
|
|
if (td.TradeStatus == ConsTrade.确认成交)
|
|
{
|
|
confirmedTradeIds.Add(td.id);
|
|
}
|
|
|
|
|
|
AddTradeOperationHistoryAndSetParentTradeInfo(false, td, history, td.TradeOldStatus);
|
|
result.RetCode = TradeOpenRetCode.Success;
|
|
return result;
|
|
}
|
|
/// <summary>
|
|
/// 新版互换确认
|
|
/// </summary>
|
|
/// <param name="td"></param>
|
|
public void SwapTradeConfirm(trade td,string history,bool addlog,DateTime? openDate=null,string optlog="")
|
|
{
|
|
if (td.TradeType != "收益互换")
|
|
{
|
|
return;
|
|
}
|
|
openDate = openDate == null ? td.TradeDate : openDate;
|
|
td.trade_extend = DbContext.trade_extend.FirstOrDefault(x => x.TradeId == td.id);
|
|
var marginModes = new int[]{ (int)InterestModeEnum.追加预付金, (int)InterestModeEnum.初始预付金 };
|
|
var positions= DbContext.swap_position.Where(x => x.SwapTradeId == td.id && x.IsInitial && !x.Invalid ).ToList();
|
|
td.swap_positions = positions.Where(x =>marginModes.Contains(x.InterestMode)).ToList();
|
|
var posiPositions= positions.Where(x => x.PosiDirection>0).ToList();
|
|
SwapTradeService swapTradeService = new SwapTradeService(this);
|
|
var swapEventService = new SwapEventService(this);
|
|
swapTradeService.InitialPosition(td);
|
|
swapTradeService.AddPositionEvent(td, optlog);
|
|
//new SwapEodPositionService(this).InitSaveEodSwapPosition(td);
|
|
var happenDate = td.TradeDate.Value;
|
|
if (td.trade_extend != null && !td.trade_extend.ExtendObj.NeedOpenFee)
|
|
{
|
|
happenDate = td.ExerciseDate.Value;
|
|
}
|
|
var cashService = new ClientCashInCashOutService(this);
|
|
cashService.SaveSwapTradeClientCash(td, td.TradePrice ?? 0, happenDate,0);
|
|
foreach (var marginPositions in td.swap_positions.GroupBy(g=>g.HappenDate))
|
|
{
|
|
var marginHappenDate = marginPositions.Key;
|
|
foreach (var marginPosition in marginPositions)
|
|
{
|
|
marginPosition.Obervation = DbContext.trade_obervation.FirstOrDefault(x => x.PositionId == marginPosition.id);
|
|
bool generateMargin = true;
|
|
if (marginPosition.Obervation != null)
|
|
{
|
|
if (!marginPosition.Obervation.IsDeductPrincipal)
|
|
{
|
|
generateMargin = false;
|
|
}
|
|
}
|
|
if (generateMargin)
|
|
{
|
|
var marginAmount = marginPosition.InterestPrincipalFix * (marginPosition.InterestDirection == 1 ? -1 : 1);
|
|
cashService.SaveSwapTradeClientCash(td,Convert.ToDouble( marginAmount), marginHappenDate.HasValue ? marginHappenDate.Value : td.TradeDate.Value, marginPosition.id, ClientCashInCashOut.系统操作_应付预付金);
|
|
}
|
|
}
|
|
}
|
|
var swap_event= swapEventService.UpdateSwapEvent();
|
|
swapEventService.AddSwapEventDate(openDate.Value, td.id, (int)SwapEventTypeEnum.确认交易, "", 0, true, history);
|
|
if (addlog)
|
|
{
|
|
var swapInsertEnum = SwapPushDataEnum.收益互换交易新增;
|
|
var posiInsertEnum = SwapPushDataEnum.互换资产交易新增;
|
|
var marginInsertEnum = SwapPushDataEnum.预付金交易新增;
|
|
}
|
|
else
|
|
{
|
|
Task.Run(() =>
|
|
{
|
|
RealtimePnlCalc.RealtimeSwapPosition(new OptUserInfo(0, "互换实时持仓服务", OptUserFrom.Service));
|
|
});
|
|
}
|
|
var interestDirection = (int)SwapDirectionEnum.收取;
|
|
if (td.swap_positions.Any())
|
|
{
|
|
interestDirection = td.swap_positions.FirstOrDefault().InterestDirection;
|
|
}
|
|
InitTradeReport(td, interestDirection);
|
|
}
|
|
/// <summary>
|
|
/// 初始化报送字段填写
|
|
/// </summary>
|
|
/// <param name="td"></param>
|
|
private void InitTradeReport(trade td,int marginDiretion)
|
|
{
|
|
var trade_Report = DbContext.trade_Report.Where(x => x.TradeId == td.id).FirstOrDefault();
|
|
if (trade_Report == null)
|
|
{
|
|
trade_Report = new trade_report();
|
|
trade_Report.TradeId = td.id;
|
|
DbContext.trade_Report.Add(trade_Report);
|
|
}
|
|
trade_Report.FillingPartyRole = td.OpponentRole == "乙方" ? "甲方" : "乙方";
|
|
trade_Report.PerformanceGuarantee = "部分担保";
|
|
trade_Report.PerformanceCollProvider = marginDiretion==(int)SwapDirectionEnum.收取? "乙方" : "甲方";
|
|
trade_Report.IsUsePerformanceColl = "是";
|
|
trade_Report.PerformanceExplain = "以交易确认书约定为准";
|
|
trade_Report.IsPerformanceCollInterest = "否";
|
|
trade_Report.PerformanceCollType = "现金";
|
|
trade_Report.PerformanceCollRange = "仅本笔交易";
|
|
trade_Report.RecoveryPerformanceColl = 2;
|
|
trade_Report.UnwindPerformanceColl = 10;
|
|
trade_Report.EodPerformanceColl = 2;
|
|
trade_Report.SetOpt(OptUser);
|
|
var tradeauditing = new TradeAuditLog
|
|
{
|
|
TradeId = td.id,
|
|
Changes = "",
|
|
DataType = "C02",
|
|
OptId = UserId,
|
|
OptName = UserName,
|
|
OptDate = OptDate,
|
|
OptType = "修改报送相关字段",
|
|
AuditFlag = TradeAuditFlag.operation
|
|
};
|
|
|
|
//记录审核日志
|
|
DbContext.TradeAuditLog.Add(tradeauditing);
|
|
DbContext.SaveChanges();
|
|
}
|
|
private TradeOpenResult CheckClient(Client client, trade td, bool ignoreMoneyCheck, bool isSkipApproval)
|
|
{
|
|
var result = new TradeOpenResult(td);
|
|
|
|
//if (client.PendingMarginCallPayment == 1)
|
|
//{
|
|
// return $"交易'{td.TradeNumber}'确认失败,客户需要追保!";
|
|
//}
|
|
|
|
result = CheckIsMoneyLack(result, client, td, ignoreMoneyCheck);
|
|
|
|
if (result.RetCode == TradeOpenRetCode.LackOfMoney)
|
|
{
|
|
return result;
|
|
}
|
|
|
|
result.RetCode = TradeOpenRetCode.Success;
|
|
return result;
|
|
}
|
|
private TradeOpenResult CheckIsMoneyLack(TradeOpenResult result, Client client, trade td, bool ignoreMoneyCheck)
|
|
{
|
|
|
|
//增加实时资金查询 查看资金资金是否足够支付期权费
|
|
tradeBLL.SetFieldsByTradeType(td);
|
|
|
|
//!!!这个逻辑有问题,结构化交易应该是检查所有总和才对
|
|
if (!(ignoreMoneyCheck || td.IsGroup == 1) && !RealtimePnlCalc.TradeCanBeConfirm(client.id, td, out var errorMsg))
|
|
{
|
|
result.RetCode = TradeOpenRetCode.LackOfMoney;
|
|
result.ErrorMsg = $"客户:{client.Name},交易编号:{td.TradeNumber},{errorMsg}";
|
|
return result;
|
|
}
|
|
return result;
|
|
}
|
|
|
|
private TradeOpenResult CheckTradeConfirmRule(TradeOpenResult result, trade td, bool isSkipApproval)
|
|
{
|
|
if (td.TradeDate == SystemValueDate)
|
|
{
|
|
var invalidTradeConfirmRuleName = new TradeConfirmRuleService(this).checkTradeConfirmRule(td, UserId);
|
|
|
|
if (!string.IsNullOrEmpty(invalidTradeConfirmRuleName) && !isSkipApproval)
|
|
{
|
|
result.ErrorMsg = $"该交易'{td.TradeNumber}'不能满足交易确认规则{invalidTradeConfirmRuleName}";
|
|
return result;
|
|
}
|
|
}
|
|
return result;
|
|
}
|
|
|
|
private TradeOpenResult CheckClientRating(TradeOpenResult result, Client client, trade td)
|
|
{
|
|
var clientRatingQuery = clientDB.Client_Rating.Where(x => x.ClientId == client.id && !x.IsDeleted);
|
|
|
|
//jira OTC-11345
|
|
//只有资信评级在有效期内且资信评级禁止交易时才阻止交易
|
|
|
|
if (clientRatingQuery.Any())
|
|
{
|
|
//if (!clientRatingQuery.Any(cr => cr.ProcessStatus == "已审批"))
|
|
//{
|
|
// return $"客户:{td.ClientName},资信等级未审批!";
|
|
//}
|
|
|
|
var query2 = from clientR in clientRatingQuery
|
|
join creditR in clientDB.credit_rating on clientR.CreditRatingId equals creditR.id into creditR_t
|
|
from creditR in creditR_t.DefaultIfEmpty()
|
|
where clientR.RatingDeadLine >= confirmDate
|
|
&& clientR.RatingStartDate <= confirmDate && clientR.ProcessStatus == "已审批"
|
|
orderby clientR.RatingDeadLine descending, clientR.ProcessOptDate descending
|
|
select new
|
|
{
|
|
clientR.id,
|
|
credit = creditR == null ? null : new
|
|
{
|
|
creditR.IsSuspend,
|
|
creditR.ValidState
|
|
}
|
|
};
|
|
|
|
var rating = query2.FirstOrDefault();
|
|
|
|
if (rating == null)
|
|
{
|
|
//return $"客户:{td.ClientName},资信评级不存在!";
|
|
}
|
|
else if (rating.credit == null)
|
|
{
|
|
//return $"客户:{td.ClientName},资信等级不存在!";
|
|
}
|
|
else if (rating.credit.ValidState == "InValid")
|
|
{
|
|
//return $"客户:{td.ClientName},资信等级无效,请重新设置该客户资信等级!";
|
|
}
|
|
else if (rating.credit.IsSuspend)
|
|
{
|
|
result.ErrorMsg = $"客户:{td.ClientName},资信等级为暂停交易! ";
|
|
return result;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
//没有的话,资信评级不做限制。
|
|
//return $"客户:{td.ClientName},{confirmDate:yyyy-MM-dd}的资信评级未找到!请设置! ";
|
|
}
|
|
result.RetCode = TradeOpenRetCode.Success;
|
|
return result;
|
|
}
|
|
|
|
public void EditReportStatus(int id, bool editConfirmBook = false)
|
|
{
|
|
var tcList = DbContext.trade_cash.Where(O => O.TradeId == id && O.Action == "系统操作-期权费").ToList();
|
|
foreach (var item in tcList)
|
|
{
|
|
item.OptDate = DateTime.Now;
|
|
}
|
|
var contractCodeList = DbContext.trade_contract_r.Where(O => O.TradeId == id && O.Type == "交易确认书").Select(O => O.ContractCode).ToList();
|
|
foreach (var code in contractCodeList)
|
|
{
|
|
//如果查不到,说明是新交易,不用修改报送状态;
|
|
if (string.IsNullOrWhiteSpace(code))
|
|
{ continue; }
|
|
var infoTag = $"_{code.Replace("_", "-")}_成交_";
|
|
if (editConfirmBook)
|
|
{
|
|
infoTag += "确认书";
|
|
}
|
|
var notes = DbContext.sac_report_notes.Where(O => O.InfoTag.Contains(infoTag)).ToArray();
|
|
foreach (var item in notes)
|
|
{
|
|
item.changeStatus = true;
|
|
}
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// from tradecontroller.TerminationBackToConfirmed
|
|
/// </summary>
|
|
public void TerminationBackToConfirmed(int tradeId)
|
|
{
|
|
var td = DbContext.trade.Find(tradeId);
|
|
if (td == null || td.ValidState == ConsGlobal.InValid)
|
|
{
|
|
throw new ServiceException("系统中没有相关的交易");
|
|
}
|
|
|
|
if (td.TradeStatus != ConsTrade.提前终止拒绝)
|
|
{
|
|
throw new ServiceException("只有提前终止拒绝状态的交易可以执行此操作");
|
|
}
|
|
|
|
td.TradeStatus = ConsTrade.确认成交;
|
|
td.OptId = UserId;
|
|
td.OptName = UserName;
|
|
td.OptDate = DateTime.Now;
|
|
AddTradeOperationHistoryAndSetParentTradeInfo(false, td, "提前终止放弃");
|
|
DbContext.SaveChanges();
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// 交易确认结果
|
|
/// </summary>
|
|
public class TradeConfirmResultModel
|
|
{
|
|
public bool LackOfMoney;
|
|
public int TrialDataId;
|
|
public int TradeId;
|
|
public List<int> confirmedTradeIds;
|
|
public List<string> changeConfirmPaths;
|
|
public string errorMsg;
|
|
public string type;
|
|
}
|
|
}
|