using BaseOUDAL; using NPOI.SS.Formula.Functions; using Qdp.Foundation.Utilities; using YLErp.DBModels; using YLErp.DBModels.Consts; using YLErp.DBModels.Enums; using YLErp.Model; using YLErp.Modules.ApiModule; using YLErp.Modules.TradeDalModule; using YLErp.Modules.UnderlyingModule; using static YLErp.ConsGlobal; namespace YLErp.Modules.TradeModule { /// /// 交易OA服务 /// public class TradeOAService : YLBaseService { private static readonly IYcLogger logger = LogFactory.GetLogger(); public TradeOAService(OptUserInfo userInfo) : base(userInfo) { } public TradeOAService(YLBaseService baseService) : base(baseService) { } /// /// 处理单个交易的OA提交 /// /// 交易ID /// 处理结果 public async Task ProcessSingleOAAsync(int tradeId) { try { // 获取交易信息 var trade = DbContext.trade.FirstOrDefault(x => x.id == tradeId); if (trade == null) { return new TradeOAResult { TradeId = tradeId, Success = false, Message = "未找到交易信息" }; } // 获取交易确认书信息 var tcr = DbContext.trade_contract_r.Where(t => t.Type == ContractTypeEnum.Trade && t.IsValid && t.TradeId == tradeId) .FirstOrDefault(); trade_contract_document tdoc = null; if (tcr != null) { tdoc = DbContext.trade_contract_document.Where(t => t.Code == tcr.ContractCode && t.Type == tcr.Type).FirstOrDefault(); } // 将之前的OA记录设置为无效 var existingOAResults = DbContext.tradeContractOaResult.Where(x => x.trade_id == tradeId && x.is_valid == true).ToList(); foreach (var existingResult in existingOAResults) { existingResult.is_valid = false; existingResult.SetOpt(UserInfo); } // 创建OA结果记录 var oaResult = new trade_contract_oa_result { trade_id = tradeId, contract_code = tcr?.ContractCode, status = "提交中", is_valid = true, }; oaResult.SetOpt(UserInfo); DbContext.tradeContractOaResult.Add(oaResult); await DbContext.SaveChangesAsync(); // 调用OA接口 var oaResp = await CallOAInterfaceAsync(trade, tcr?.ContractCode, tdoc, oaResult.id); if (oaResp != null && oaResp.code == 0) { oaResult.status = "提交成功"; oaResult.oa_fileid = oaResp.data?.requestid; oaResult.oa_msg = oaResp.data?.msg ?? "提交成功"; } else { oaResult.status = "提交失败"; oaResult.oa_msg = oaResp?.data?.msg ?? "OA接口调用失败"; } await DbContext.SaveChangesAsync(); return new TradeOAResult { TradeId = tradeId, Success = oaResult.status == "提交成功", Message = oaResult.oa_msg }; } catch (Exception ex) { logger.Error($"处理交易ID {tradeId} 的OA时发生错误: {ex.Message}", ex); return new TradeOAResult { TradeId = tradeId, Success = false, Message = $"提交OA失败: {ex.Message}" }; } } /// /// 调用OA接口 /// /// 交易信息 /// 合同编号 /// 交易确认书文档 /// OA结果记录ID /// 是否成功 private async Task CallOAInterfaceAsync(trade trade, string contractCode, trade_contract_document tdoc, int oaResultId) { try { // 获取OA配置 var oaConfigSection = AppManager.GetConfiguration().GetSection("oa_confg"); var baseUrl = oaConfigSection["BaseUrl"]; var subUrl = oaConfigSection["SubUrl"]; var systemToken = oaConfigSection["SystemToken"]; var systemName = oaConfigSection["SystemName"]; var isNextFlow = oaConfigSection["IsNextFlow"] ?? "0"; if (string.IsNullOrEmpty(baseUrl)) { logger.Error("OA接口配置中BaseUrl为空"); return new GuoLianOAResponse() { code = -1, data = new GuoLianOAData { msg = "OA接口配置中地址为空" } }; } if (string.IsNullOrEmpty(systemToken)) { logger.Error("OA接口配置中SystemToken为空"); return new GuoLianOAResponse() { code = -1, data = new GuoLianOAData { msg = "OA接口配置中SystemToken为空" } }; } // 处理附件 string attachmentBase64 = null; string attachmentFileName = null; if (tdoc != null && !string.IsNullOrEmpty(tdoc.AbsolutePath)) { try { if (File.Exists(tdoc.AbsolutePath)) { var fileBytes = await File.ReadAllBytesAsync(tdoc.AbsolutePath); attachmentBase64 = Convert.ToBase64String(fileBytes); attachmentFileName = Path.GetFileName(tdoc.AbsolutePath); logger.Info($"成功读取附件文件:{tdoc.AbsolutePath},文件大小:{fileBytes.Length} 字节"); } else { logger.Error($"附件文件不存在:{tdoc.AbsolutePath}"); return new GuoLianOAResponse() { code = -1, data = new GuoLianOAData { msg = "附件文件不存在" } }; } } catch (Exception ex) { logger.Error($"读取附件文件失败:{tdoc.AbsolutePath},错误:{ex.Message}", ex); return new GuoLianOAResponse() { code = -1, data = new GuoLianOAData { msg = "读取附件文件失败" } }; } } // 构建dataMap var dataMap = new { title = $"固定收益部申请【{contractCode}】TRS交易确认书", urgentLevel = "正常", applyDate = DateTime.Now.ToString("yyyyMMdd"), applicant = UserInfo.UserName, applicantComp = "国联民生证券总部", contractType = "业务", businessType = "金融交易类合同(除股票质押式回购业务部分购回、购回协议)", contractSecretLevel = "一般", contractUrgentLevel = "一般", //去除后缀 contractName = Path.GetFileNameWithoutExtension(tdoc.FileName), isRelatedTransaction = "否", partyAType = "企业", partyA = trade.ClientName, partyBType = "企业", partyB = "国联民生证券股份有限公司", partyASmsNotify = "否", partyBSmsNotify = "否", contractAmount = trade.OriginalStockEqvNotional, contractBeginDate = trade.StartDate?.ToString("yyyyMMdd"), contractEndDate = trade.ExerciseDate?.ToString("yyyyMMdd"), currency = "人民币", contractSignDate = DateTime.Now.ToString("yyyyMMdd"), signIntegrityAgreement = "无需签订", contractBackground = $"我司与{trade.ClientName}已完成NAFMII协议签署,并开展TRS交易:{contractCode},参与标的{trade.UnderlyingCode} {trade.UnderlyingName},参与标的数量面额{trade.OriginalStockEqvNotional}元人民币", attachments = string.IsNullOrEmpty(attachmentBase64) ? null : new[] { new { fileName = attachmentFileName, fileBytes = attachmentBase64 } } }; // 构建OA请求参数 var oaRequest = new { isnextflow = isNextFlow, systemToken = systemToken, systemName = systemName, dataMap = JsonHelper.Serialize(dataMap) }; logger.Info($"国联OA接口参数: {JsonHelper.Serialize(oaRequest)}"); // 调用OA接口 (GET请求) var httpClient = new HttpClientWrap(baseUrl); var response = httpClient.PostJson(subUrl, oaRequest,null); logger.Info($"国联OA接口返回: {response}"); // 解析响应 var responseObj = JsonHelper.Deserialize(response); return responseObj; } catch (Exception ex) { logger.Error($"调用OA接口时发生异常,交易ID:{trade.id},异常信息:{ex.Message}", ex); return new GuoLianOAResponse() { code = -2, data = new GuoLianOAData { msg = $"调用OA接口时发生异常: {ex.Message}" } }; } } } }