1613 lines
		
	
	
		
			76 KiB
		
	
	
	
		
			C#
		
	
	
			
		
		
	
	
			1613 lines
		
	
	
		
			76 KiB
		
	
	
	
		
			C#
		
	
	
| //--------------------------------------------------------------------
 | ||
| //     此代码由T4模板自动生成  byzhouhang 20210918
 | ||
| //	   生成时间 2022-10-20 11:52:17 
 | ||
| //     对此文件的更改可能会导致不正确的行为,并且如果重新生成代码,这些更改将会丢失。
 | ||
| //--------------------------------------------------------------------
 | ||
| 
 | ||
| using IRaCIS.Core.Application.Contracts;
 | ||
| using IRaCIS.Core.Application.Filter;
 | ||
| using IRaCIS.Core.Application.Helper;
 | ||
| using IRaCIS.Core.Application.Interfaces;
 | ||
| using IRaCIS.Core.Application.ViewModel;
 | ||
| using IRaCIS.Core.Domain.Share;
 | ||
| using IRaCIS.Core.Domain.Share.Common;
 | ||
| using IRaCIS.Core.Infra.EFCore.Common;
 | ||
| using IRaCIS.Core.Infrastructure;
 | ||
| using Microsoft.AspNetCore.Hosting;
 | ||
| using Microsoft.AspNetCore.Mvc;
 | ||
| using Microsoft.Extensions.Options;
 | ||
| using Spire.Doc;
 | ||
| using System.Linq.Dynamic.Core;
 | ||
| using System.Runtime.InteropServices;
 | ||
| 
 | ||
| namespace IRaCIS.Core.Application.Service
 | ||
| {
 | ||
|     /// <summary>
 | ||
|     /// TrialEmailNoticeConfigService
 | ||
|     /// </summary>	
 | ||
|     [ApiExplorerSettings(GroupName = "Trial")]
 | ||
|     public class TrialEmailNoticeConfigService(IRepository<TrialEmailNoticeConfig> _trialEmailNoticeConfigRepository,
 | ||
|             IRepository<TrialEmailBlackUser> _trialEmailBlackUserRepository,
 | ||
|             IRepository<EmailNoticeConfig> _emailNoticeConfigRepository,
 | ||
|             IRepository<Trial> _trialRepository,
 | ||
|             IRepository<TaskMedicalReview> _taskMedicalReviewRepository,
 | ||
|             IRepository<ReadingGlobalTaskInfo> _readingGlobalTaskInfoRepository,
 | ||
|             IRepository<VisitTask> _visitTaskRepository,
 | ||
|             IRepository<TrialUserRole> _trialUserRoleRepository,
 | ||
|             IRepository<TrialEmailNoticeUser> _trialEmailNoticeUserRepository,
 | ||
|             IRepository<Subject> _subjectRepository,
 | ||
|             IRepository<ReadModule> _readModuleRepository,
 | ||
|             IRepository<ReadingTableQuestionAnswer> _readingTableQuestionAnswerRepository,
 | ||
|             IRepository<SubjectVisit> _subjectVisitRepository,
 | ||
|             IRepository<ReadingTaskQuestionAnswer> _readingTaskQuestionAnswerRepository,
 | ||
|             IRepository<ReadingQuestionCriterionTrial> _readingQuestionCriterionTrialRepository,
 | ||
|             IOptionsMonitor<SystemEmailSendConfig> _systemEmailSendConfig,
 | ||
|             IEmailSendService _emailSendService,
 | ||
|             IMapper _mapper, IUserInfo _userInfo, IStringLocalizer _localizer, IWebHostEnvironment _hostEnvironment) : BaseService, ITrialEmailNoticeConfigService
 | ||
|     {
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|         /// <summary>
 | ||
|         /// 获取项目邮箱
 | ||
|         /// </summary>
 | ||
|         /// <param name="inDto"></param>
 | ||
|         /// <returns></returns>
 | ||
|         [HttpPost]
 | ||
|         public async Task<GetTrialEmailSetOutDto> GetTrialEmail(GetTrialEmailSetInDto inDto)
 | ||
|         {
 | ||
|             return await _trialRepository.Where(x => x.Id == inDto.TrialId, ignoreQueryFilters: true).Select(x => new GetTrialEmailSetOutDto()
 | ||
|             {
 | ||
|                 TrialId = inDto.TrialId,
 | ||
|                 EmailAuthorizationCode = x.EmailAuthorizationCode,
 | ||
|                 EmailSMTPServerAddress = x.EmailSMTPServerAddress,
 | ||
|                 EmailFromEmail = x.EmailFromEmail,
 | ||
|                 EmailFromName = x.EmailFromName,
 | ||
|                 IsConfigureEmail = x.IsConfigureEmail,
 | ||
|                 EmailSMTPServerPort = x.EmailSMTPServerPort
 | ||
| 
 | ||
|             }).FirstAsync();
 | ||
|         }
 | ||
| 
 | ||
|         /// <summary>
 | ||
|         /// 设置项目邮箱
 | ||
|         /// </summary>
 | ||
|         /// <param name="inDto"></param>
 | ||
|         /// <returns></returns>
 | ||
|         public async Task<IResponseOutput> SetTrialEmail(SetTrialEmailInDto inDto)
 | ||
|         {
 | ||
| 
 | ||
|             await TestEmailConfigAsync(new TrialEmailNoticeConfigAddOrEdit()
 | ||
|             {
 | ||
| 
 | ||
|                 AuthorizationCode = inDto.EmailAuthorizationCode,
 | ||
|                 FromEmail = inDto.EmailFromEmail,
 | ||
|                 FromName = inDto.EmailFromName,
 | ||
|                 SMTPServerAddress = inDto.EmailSMTPServerAddress,
 | ||
|                 SMTPServerPort = inDto.EmailSMTPServerPort,
 | ||
|                 TrialId = inDto.TrialId,
 | ||
|             });
 | ||
| 
 | ||
|             await _trialRepository.UpdatePartialFromQueryAsync(inDto.TrialId, x => new Trial()
 | ||
|             {
 | ||
| 
 | ||
|                 EmailFromEmail = inDto.EmailFromEmail,
 | ||
|                 EmailFromName = inDto.EmailFromName,
 | ||
|                 EmailAuthorizationCode = inDto.EmailAuthorizationCode,
 | ||
|                 EmailSMTPServerAddress = inDto.EmailSMTPServerAddress,
 | ||
|                 EmailSMTPServerPort = inDto.EmailSMTPServerPort,
 | ||
|                 IsConfigureEmail = true,
 | ||
|             });
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|             await _trialEmailNoticeConfigRepository.BatchUpdateNoTrackingAsync(x => x.TrialId == inDto.TrialId, x => new TrialEmailNoticeConfig()
 | ||
|             {
 | ||
|                 AuthorizationCode = inDto.EmailAuthorizationCode,
 | ||
|                 FromEmail = inDto.EmailFromEmail,
 | ||
|                 FromName = inDto.EmailFromName,
 | ||
|                 SMTPServerAddress = inDto.EmailSMTPServerAddress,
 | ||
|                 SMTPServerPort = inDto.EmailSMTPServerPort,
 | ||
|             });
 | ||
| 
 | ||
|             await _trialRepository.SaveChangesAsync();
 | ||
|             return ResponseOutput.Ok();
 | ||
|         }
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|         private async Task<bool> DealMedicalReviewTasKGenerateAndIsSendAsync(Guid trialId, bool? isHandSend, string pdAnswer, List<Guid> taskIdList, List<Guid> minUserIdList)
 | ||
|         {
 | ||
| 
 | ||
|             var isNeedSend = true;
 | ||
| 
 | ||
|             //手动发送的时候,也有可能答案是是  此时是 这里不发送,发送已经生成的文件
 | ||
|             if (pdAnswer == "是" && isHandSend == null)
 | ||
|             {
 | ||
|                 isNeedSend = true;
 | ||
| 
 | ||
|             }
 | ||
|             else
 | ||
|             {
 | ||
|                 //正常阅片为否的
 | ||
|                 if (isHandSend == null)
 | ||
|                 {
 | ||
|                     isNeedSend = false;
 | ||
| 
 | ||
|                     //生成任务
 | ||
|                     foreach (var taskId in taskIdList)
 | ||
|                     {
 | ||
|                         await _taskMedicalReviewRepository.AddAsync(new TaskMedicalReview()
 | ||
|                         {
 | ||
|                             TrialId = trialId,
 | ||
|                             VisitTaskId = taskId,
 | ||
|                             MedicalManagerUserId = minUserIdList.FirstOrDefault(),
 | ||
|                             AllocateTime = DateTime.Now
 | ||
|                             ,
 | ||
|                             IsAutoGenerate = true,
 | ||
|                             PDRelationTaskIdListStr = string.Join('|', taskIdList.Distinct())
 | ||
|                         }, true);
 | ||
| 
 | ||
|                     }
 | ||
|                 }
 | ||
|                 else if (isHandSend == true)
 | ||
|                 {
 | ||
|                     //手动发送
 | ||
|                     isNeedSend = false;
 | ||
|                 }
 | ||
|                 else
 | ||
|                 {
 | ||
|                     // 医学审核确认未否了 才发
 | ||
|                     isNeedSend = true;
 | ||
|                 }
 | ||
|             }
 | ||
| 
 | ||
|             return isNeedSend;
 | ||
| 
 | ||
|         }
 | ||
| 
 | ||
|         /// <summary>
 | ||
|         /// 测试邮件 带附件 填充word 
 | ||
|         /// </summary>
 | ||
|         /// <param name="visitTaskId"></param>
 | ||
|         /// <param name="isHandSend"> 为空 代表 正常任务自动发送,为true  代表医学审核手动发送  为false 代表医学审核自动发送 </param>
 | ||
|         /// <param name="emailStoreMode"></param>
 | ||
|         /// <param name="sendFileRelativePath"></param>
 | ||
|         /// <returns></returns>
 | ||
|         /// <exception cref="BusinessValidationFailedException"></exception>
 | ||
|         public async Task<string> BaseBusinessScenarioSendEmailAsync(Guid visitTaskId, bool? isHandSend, EmailStoreSendMode emailStoreMode, string sendFileRelativePath)
 | ||
|         {
 | ||
|             var isEn_us = _userInfo.IsEn_Us;
 | ||
|             EmailBusinessScenario businessScenarioEnum = EmailBusinessScenario.None;
 | ||
| 
 | ||
|             #region 任务关联的项目配置  标准信息及配置,subject 信息
 | ||
|             var taskInfo = await _visitTaskRepository.Where(t => t.Id == visitTaskId).Select(t => new
 | ||
|             {
 | ||
| 
 | ||
|                 t.Trial.ResearchProgramNo,
 | ||
|                 t.Subject.TrialSite.TrialSiteCode,
 | ||
|                 SubjectCode = t.Subject.Code,
 | ||
|                 t.Trial.Sponsor.SponsorName,
 | ||
|                 t.Trial.IsEnrollementQualificationConfirm,
 | ||
|                 t.Trial.IsPDProgressView,
 | ||
| 
 | ||
| 
 | ||
|                 VisitEarliestScanDate = t.SourceSubjectVisit.EarliestScanDate,
 | ||
|                 VisitName = (string?)t.SourceSubjectVisit.VisitName,
 | ||
|                 IsFinalVisit = (bool?)t.SourceSubjectVisit.IsFinalVisit,
 | ||
|                 PDState = (PDStateEnum?)t.SourceSubjectVisit.PDState,
 | ||
|                 IsEnrollmentConfirm = (bool?)t.SourceSubjectVisit.IsEnrollmentConfirm,
 | ||
|                 IsBaseline = (bool?)t.SourceSubjectVisit.IsBaseLine,
 | ||
| 
 | ||
| 
 | ||
|                 ModuleEarliestScanDate = t.ReadModule.SubjectVisit.EarliestScanDate,
 | ||
|                 ModuleVisitName = (string?)t.ReadModule.SubjectVisit.VisitName,
 | ||
|                 MoudulePDState = (PDStateEnum?)t.ReadModule.SubjectVisit.PDState,
 | ||
| 
 | ||
|                 t.SourceSubjectVisitId,
 | ||
|                 t.SouceReadModuleId,
 | ||
|                 t.SubjectId,
 | ||
|                 t.Subject.TrialSiteId,
 | ||
| 
 | ||
|                 t.DoctorUserId,
 | ||
|                 t.ReadingTaskState,
 | ||
|                 t.ReadingCategory,
 | ||
|                 t.SignTime,
 | ||
|                 //仲裁规则
 | ||
|                 t.TrialReadingCriterion.ArbitrationRule,
 | ||
|                 //单双中
 | ||
|                 t.TrialReadingCriterion.ReadingType,
 | ||
| 
 | ||
|                 t.TrialReadingCriterion.CriterionType,
 | ||
|                 //有序与否
 | ||
|                 t.TrialReadingCriterion.IsReadingTaskViewInOrder,
 | ||
| 
 | ||
|                 t.TrialId,
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|                 t.IsAnalysisCreate,
 | ||
|                 t.TrialReadingCriterionId,
 | ||
|             }).FirstNotNullAsync();
 | ||
| 
 | ||
| 
 | ||
|             if (taskInfo.IsAnalysisCreate)
 | ||
|             {
 | ||
|                 return string.Empty;
 | ||
|             }
 | ||
| 
 | ||
|             #endregion
 | ||
| 
 | ||
| 
 | ||
|             #region 任务 -邮件场景区分
 | ||
| 
 | ||
|             if (taskInfo.ReadingTaskState == ReadingTaskState.HaveSigned)
 | ||
|             {
 | ||
|                 //入组确认场景
 | ||
|                 if (taskInfo.IsEnrollmentConfirm == true && taskInfo.IsEnrollementQualificationConfirm == true && taskInfo.IsBaseline == true)
 | ||
|                 {
 | ||
|                     businessScenarioEnum = EmailBusinessScenario.EnrollConfirmed;
 | ||
| 
 | ||
| 
 | ||
|                 }
 | ||
|                 //PD确认场景
 | ||
|                 else if (taskInfo.IsPDProgressView &&
 | ||
|                     (taskInfo.PDState == PDStateEnum.PDProgress && taskInfo.SourceSubjectVisitId != null) ||
 | ||
|                     (taskInfo.SouceReadModuleId != null && taskInfo.MoudulePDState == PDStateEnum.PDProgress))
 | ||
|                 {
 | ||
|                     businessScenarioEnum = EmailBusinessScenario.PDConfirmed;
 | ||
|                 }
 | ||
|                 else
 | ||
|                 {
 | ||
|                     return string.Empty;
 | ||
|                 }
 | ||
| 
 | ||
|             }
 | ||
|             else
 | ||
|             {
 | ||
|                 //---进行邮件发送前,该任务必须已签名完成并已经触发完成相应的任务生成
 | ||
|                 throw new BusinessValidationFailedException(_localizer["TrialEmailN_TaskNotSigned"]);
 | ||
|             }
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|             #endregion
 | ||
| 
 | ||
| 
 | ||
|             #region 邮件内容装配
 | ||
| 
 | ||
|             Func<TrialEmailNoticeConfig, (string topicStr, string htmlBodyStr, bool isEn_us, Guid? onlyToUserId)> topicAndHtmlFunc = trialEmailConfig =>
 | ||
|             {
 | ||
|                 var topicStr = string.Format(isEn_us ? trialEmailConfig.EmailTopic : trialEmailConfig.EmailTopicCN, taskInfo.ResearchProgramNo, taskInfo.SubjectCode);
 | ||
| 
 | ||
|                 var htmlBodyStr = string.Format(isEn_us ? trialEmailConfig.EmailHtmlContent : trialEmailConfig.EmailHtmlContentCN,
 | ||
|                    StaticData.EmailSend.EmailNamePlaceholder, taskInfo.ResearchProgramNo, taskInfo.SubjectCode);
 | ||
| 
 | ||
| 
 | ||
|                 return (topicStr, htmlBodyStr, isEn_us, null);
 | ||
|             };
 | ||
| 
 | ||
| 
 | ||
|             var (trialEmailConfig, sendEmailConfig) = await _emailSendService.BuildEmailConfig(taskInfo.TrialId, businessScenarioEnum, topicAndHtmlFunc, taskInfo.TrialSiteId, taskInfo.TrialReadingCriterionId);
 | ||
| 
 | ||
|             #endregion
 | ||
| 
 | ||
| 
 | ||
|             //自动发送
 | ||
|             if (sendEmailConfig != null && trialEmailConfig != null)
 | ||
|             {
 | ||
|                 #region 不同标准 不同项目配置 发送邮件的时机 处理具体逻辑
 | ||
| 
 | ||
|                 var answer = "否";
 | ||
|                 var isNeedSend = true;
 | ||
|                 var minUserIdList = _trialUserRoleRepository.Where(t => t.UserRole.UserTypeEnum == Domain.Share.UserTypeEnum.MIM && t.TrialId == taskInfo.TrialId).Select(t => t.UserId).ToList();
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|                 //入组确认  根据每个标准配置的是否自动发送,发送邮件与否
 | ||
|                 if (businessScenarioEnum == EmailBusinessScenario.EnrollConfirmed)
 | ||
|                 {
 | ||
|                     if (await _readingTableQuestionAnswerRepository.Where().AnyAsync(x => x.VisitTaskId == visitTaskId && x.Answer == TargetState.Exist.GetEnumInt() &&
 | ||
|                  x.ReadingTableQuestionTrial.QuestionMark == QuestionMark.State && x.ReadingQuestionTrial.LesionType == LesionType.TargetLesion))
 | ||
|                     {
 | ||
|                         answer = "是";
 | ||
|                     }
 | ||
| 
 | ||
| 
 | ||
|                     //如果其他阅片人已经做了,说明发送了入组确认报告,第二个人做完就不发送了
 | ||
| 
 | ||
|                     //入组确认一直交给第一个人,如果第一个人重阅 还未做完,第二个人先做完了,此时不发
 | ||
| 
 | ||
|                     var existFirstEnrollTask = await _visitTaskRepository.Where(t => t.SourceSubjectVisitId == taskInfo.SourceSubjectVisitId && t.IsAnalysisCreate == false
 | ||
|                     && t.ReadingTaskState == ReadingTaskState.HaveSigned && t.TrialReadingCriterionId == taskInfo.TrialReadingCriterionId).OrderBy(t => t.SignTime).FirstOrDefaultAsync();
 | ||
| 
 | ||
|                     //入组确认的医生已确定
 | ||
|                     if ((existFirstEnrollTask != null) && (taskInfo.DoctorUserId != existFirstEnrollTask.DoctorUserId))
 | ||
|                     {
 | ||
|                         isNeedSend = false;
 | ||
|                     }
 | ||
|                     else
 | ||
|                     {
 | ||
|                         isNeedSend = await DealMedicalReviewTasKGenerateAndIsSendAsync(taskInfo.TrialId, isHandSend, answer, new List<Guid>() { visitTaskId }, minUserIdList);
 | ||
| 
 | ||
| 
 | ||
|                         if (answer == "是")
 | ||
|                         {
 | ||
|                             //把另外一个人的任务设置为不加急(如果项目加急是否  subject 加急是否)
 | ||
|                             var urgent = _subjectVisitRepository.Where(t => t.Id == taskInfo.SourceSubjectVisitId).Select(t => new { IsSubjectUrgent = t.Subject.IsUrgent, t.Trial.IsUrgent }).FirstOrDefault();
 | ||
| 
 | ||
|                             if (urgent?.IsUrgent == false || urgent?.IsSubjectUrgent == false)
 | ||
|                             {
 | ||
|                                 await _visitTaskRepository.BatchUpdateNoTrackingAsync(t => t.SourceSubjectVisitId == taskInfo.SourceSubjectVisitId && t.TaskState == TaskState.Effect && t.IsAnalysisCreate == false &&
 | ||
|                         t.Id != visitTaskId && t.TrialReadingCriterionId == taskInfo.TrialReadingCriterionId, u => new VisitTask() { IsUrgent = false });
 | ||
|                             }
 | ||
|                         }
 | ||
| 
 | ||
| 
 | ||
|                     }
 | ||
|                 }
 | ||
|                 else if (businessScenarioEnum == EmailBusinessScenario.PDConfirmed)
 | ||
|                 {
 | ||
| 
 | ||
| 
 | ||
|                     //有序
 | ||
| 
 | ||
|                     if (taskInfo.IsReadingTaskViewInOrder == ReadingOrder.InOrder)
 | ||
|                     {
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|                         //双重
 | ||
|                         if (taskInfo.ReadingType == ReadingMethod.Double)
 | ||
|                         {
 | ||
| 
 | ||
| 
 | ||
|                             //仲裁在访视上   就没有全局阅片 没有阅片期
 | ||
|                             if (taskInfo.ArbitrationRule == ArbitrationRule.Visit)
 | ||
|                             {
 | ||
|                                 //找到 访视,裁判 所有有效任务(不可能有全局的)   访视和裁判任务的SourceSubjectVisitId 一样
 | ||
|                                 var taskList = await _visitTaskRepository.Where(t => t.SourceSubjectVisitId == taskInfo.SourceSubjectVisitId && t.TrialReadingCriterionId == taskInfo.TrialReadingCriterionId && t.IsAnalysisCreate == false && t.TaskState == TaskState.Effect &&
 | ||
|                                 (t.ReadingCategory == ReadingCategory.Visit || t.ReadingCategory == ReadingCategory.Judge)).ToListAsync();
 | ||
| 
 | ||
| 
 | ||
|                                 //这里要求 到这里已经如果有裁判  已经生成裁判了保存数据库
 | ||
|                                 //双人阅片,没有产生裁判 第二个人读完发
 | ||
|                                 if (taskList.Count == 2 && taskList.Count(t => t.ReadingTaskState == ReadingTaskState.HaveSigned && t.ReadingCategory == ReadingCategory.Visit) == 2)
 | ||
|                                 {
 | ||
| 
 | ||
|                                     answer = await TranslatePdStateAsync(visitTaskId, taskInfo.ReadingCategory, taskInfo.CriterionType);
 | ||
| 
 | ||
| 
 | ||
|                                     isNeedSend = await DealMedicalReviewTasKGenerateAndIsSendAsync(taskInfo.TrialId, isHandSend, answer, taskList.Select(t => t.Id).ToList(), minUserIdList);
 | ||
| 
 | ||
|                                 }
 | ||
|                                 //双人  产生裁判,并且裁判完成 发
 | ||
|                                 else if (taskList.Count == 3 && taskList.Count(t => t.ReadingTaskState == ReadingTaskState.HaveSigned) == 3 && taskList.Where(t => t.ReadingCategory == ReadingCategory.Judge).Count() == 1)
 | ||
|                                 {
 | ||
|                                     var judgeResultId = taskList.Where(t => t.ReadingCategory == ReadingCategory.Judge).First()!.JudgeResultTaskId!.Value;
 | ||
|                                     answer = await TranslatePdStateAsync(judgeResultId, ReadingCategory.Visit, taskInfo.CriterionType);
 | ||
| 
 | ||
|                                     isNeedSend = await DealMedicalReviewTasKGenerateAndIsSendAsync(taskInfo.TrialId, isHandSend, answer, taskList.Where(t => t.ReadingCategory == ReadingCategory.Judge).Select(t => t.Id).ToList(), minUserIdList);
 | ||
| 
 | ||
|                                 }
 | ||
|                                 else
 | ||
|                                 {
 | ||
|                                     isNeedSend = false;
 | ||
| 
 | ||
|                                 }
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|                             }
 | ||
|                             //仲裁在阅片期   
 | ||
|                             else if (taskInfo.ArbitrationRule == ArbitrationRule.Reading)
 | ||
|                             {
 | ||
|                                 //是访视任务  不可能是裁判任务(访视上不会生成裁判),也不会是全局任务(全局任务 SourceSubjectVisitId=null )
 | ||
|                                 if (taskInfo.SourceSubjectVisitId != null)
 | ||
|                                 {
 | ||
| 
 | ||
|                                     //访视类型的任务  根本就不需要发送邮件
 | ||
| 
 | ||
|                                     isNeedSend = false;
 | ||
| 
 | ||
|                                 }
 | ||
|                                 //是全局任务 或者全局的裁判任务   (如果是全局任务,那么此时裁判任务已经生成)
 | ||
|                                 else if (taskInfo.SouceReadModuleId != null)
 | ||
|                                 {
 | ||
|                                     var taskList = await _visitTaskRepository.Where(t => t.TrialReadingCriterionId == taskInfo.TrialReadingCriterionId && t.IsAnalysisCreate == false && t.TaskState == TaskState.Effect && t.SouceReadModuleId == taskInfo.SouceReadModuleId
 | ||
|                                     && (t.ReadingCategory == ReadingCategory.Global || t.ReadingCategory == ReadingCategory.Judge)).ToListAsync();
 | ||
| 
 | ||
|                                     //两个全局没有裁判
 | ||
|                                     if (taskList.Count == 2 && taskList.Count(t => t.ReadingTaskState == ReadingTaskState.HaveSigned && t.ReadingCategory == ReadingCategory.Global) == 2)
 | ||
|                                     {
 | ||
| 
 | ||
|                                         answer = await TranslatePdStateAsync(visitTaskId, taskInfo.ReadingCategory, taskInfo.CriterionType);
 | ||
| 
 | ||
|                                         isNeedSend = await DealMedicalReviewTasKGenerateAndIsSendAsync(taskInfo.TrialId, isHandSend, answer, taskList.Select(t => t.Id).ToList(), minUserIdList);
 | ||
|                                     }
 | ||
|                                     //双人全局产生裁判
 | ||
|                                     else if (taskList.Count == 3 && taskList.Count(t => t.ReadingTaskState == ReadingTaskState.HaveSigned) == 3 && taskList.Where(t => t.ReadingCategory == ReadingCategory.Judge).Count() == 1 && taskList.Where(t => t.ReadingCategory == ReadingCategory.Global).Count() == 2)
 | ||
|                                     {
 | ||
| 
 | ||
|                                         var judgeResultId = taskList.Where(t => t.ReadingCategory == ReadingCategory.Judge).First().JudgeResultTaskId!.Value;
 | ||
|                                         answer = await TranslatePdStateAsync(judgeResultId, ReadingCategory.Global, taskInfo.CriterionType);
 | ||
| 
 | ||
|                                         isNeedSend = await DealMedicalReviewTasKGenerateAndIsSendAsync(taskInfo.TrialId, isHandSend, answer, taskList.Where(t => t.ReadingCategory == ReadingCategory.Judge).Select(t => t.Id).ToList(), minUserIdList);
 | ||
| 
 | ||
|                                     }
 | ||
|                                     else
 | ||
|                                     {
 | ||
|                                         isNeedSend = false;
 | ||
| 
 | ||
|                                     }
 | ||
|                                 }
 | ||
|                                 else
 | ||
|                                 {
 | ||
|                                     //---发送PD 进展邮件中发现任务数据有问题!
 | ||
|                                     throw new BusinessValidationFailedException(_localizer["TrialEmailN_PDProgressEmailTask"]);
 | ||
|                                 }
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|                             }
 | ||
|                             else
 | ||
|                             {
 | ||
| 
 | ||
|                                 //---双重有序阅片 没有定义该仲裁规则处理逻辑,请联系业务和后台开发核查!
 | ||
|                                 throw new BusinessValidationFailedException(_localizer["TrialEmailN_DoubleBlindedError"]);
 | ||
|                             }
 | ||
| 
 | ||
| 
 | ||
|                         }
 | ||
| 
 | ||
|                         //屏蔽单重阅片添加
 | ||
|                         else
 | ||
|                         {
 | ||
|                             isNeedSend = false;
 | ||
|                             return string.Empty;
 | ||
|                         }
 | ||
| 
 | ||
|                         #region 发邮件屏蔽单重的
 | ||
|                         ////单重
 | ||
|                         //else if (taskInfo.ReadingType == ReadingMethod.Single)
 | ||
|                         //{
 | ||
|                         //    //仲裁在访视上   或者在阅片期
 | ||
|                         //    if (taskInfo.ArbitrationRule != ArbitrationRule.None)
 | ||
|                         //    {
 | ||
| 
 | ||
|                         //---单重有序阅片配置有误(不应该有仲裁对象配置),请核查!
 | ||
|                         //        throw new BusinessValidationFailedException(_localizer["TrialEmailN_SingleBlindedSet"]);
 | ||
|                         //    }
 | ||
| 
 | ||
| 
 | ||
|                         //    //要求PD 确认的访视  是截止访视 还是非截止访视(根据该访视有没有配置阅片期来判断)
 | ||
| 
 | ||
|                         //    if (taskInfo.ReadingCategory == ReadingCategory.Visit)
 | ||
|                         //    {
 | ||
|                         //        //存在阅片期  那么就是截止访视
 | ||
|                         //        if (await _readModuleRepository.Where(t => t.TrialReadingCriterionId == taskInfo.TrialReadingCriterionId && t.SubjectVisitId == taskInfo.SourceSubjectVisitId && t.ReadingSetType == ReadingSetType.ImageReading).AnyAsync())
 | ||
|                         //        {
 | ||
|                         //            isNeedSend = false;
 | ||
|                         //        }
 | ||
|                         //        else//非截止访视 在访视读完后,发送
 | ||
|                         //        {
 | ||
|                         //            answer = await TranslatePdStateAsync(visitTaskId, ReadingCategory.Visit, taskInfo.CriterionType);
 | ||
|                         //        }
 | ||
|                         //    }
 | ||
|                         //    //截止访视  在访视读完,并完成全局阅片后发送全局的结果
 | ||
|                         //    else if (taskInfo.ReadingCategory == ReadingCategory.Global)
 | ||
|                         //    {
 | ||
|                         //        answer = await TranslatePdStateAsync(visitTaskId, ReadingCategory.Global, taskInfo.CriterionType);
 | ||
|                         //    }
 | ||
|                         //    else
 | ||
|                         //    {
 | ||
|                         //---单重有序阅片 该类型的任务不应进入此处逻辑,请联系后台开发核查!
 | ||
|                         //        throw new BusinessValidationFailedException(_localizer["TrialEmailN_SingleBlindedSequenced"]);
 | ||
|                         //    }
 | ||
| 
 | ||
|                         //    isNeedSend = await DealMedicalReviewTasKGenerateAndIsSendAsync(taskInfo.TrialId, isHandSend, answer, new List<Guid>() { visitTaskId }, minUserIdList);
 | ||
| 
 | ||
| 
 | ||
|                         //}
 | ||
|                         //else
 | ||
|                         //{
 | ||
|                         //---有序阅片配置有误(应为单重或者双重阅片),请核查!
 | ||
|                         //    throw new BusinessValidationFailedException(_localizer["TrialEmailN_BlindedSequencedReading"]);
 | ||
|                         //}
 | ||
| 
 | ||
|                         #endregion
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|                     }
 | ||
|                     //屏蔽无序阅片添加
 | ||
|                     else
 | ||
|                     {
 | ||
|                         isNeedSend = false;
 | ||
|                         return string.Empty;
 | ||
|                     }
 | ||
| 
 | ||
|                     #region 发送邮件屏蔽无序的
 | ||
|                     //    //无序
 | ||
|                     //else
 | ||
|                     //{
 | ||
|                     //    //单重
 | ||
| 
 | ||
| 
 | ||
|                     //    if (taskInfo.ReadingType == ReadingMethod.Single && taskInfo.ArbitrationRule == ArbitrationRule.None)
 | ||
|                     //    {
 | ||
|                     //        answer = await TranslatePdStateAsync(visitTaskId, taskInfo.ReadingCategory, taskInfo.CriterionType);
 | ||
| 
 | ||
|                     //        isNeedSend = await DealMedicalReviewTasKGenerateAndIsSendAsync(taskInfo.TrialId, isHandSend, answer, new List<Guid>() { visitTaskId }, minUserIdList);
 | ||
|                     //    }
 | ||
|                     //    //双重  截止访视只在阅片期的时候存在  要求PD确认的访视 肯定是非截止访视
 | ||
|                     //    else if (taskInfo.ReadingType == ReadingMethod.Double && taskInfo.ArbitrationRule == ArbitrationRule.Visit)
 | ||
|                     //    {
 | ||
|                     //        //在两位阅片人读完访视后,如果有裁判者等裁判读完,如果无裁判则等第二个人的读完
 | ||
| 
 | ||
|                     //        var taskList = await _visitTaskRepository.Where(t => t.SourceSubjectVisitId == taskInfo.SourceSubjectVisitId && t.TrialReadingCriterionId == taskInfo.TrialReadingCriterionId && t.IsAnalysisCreate == false && t.TaskState == TaskState.Effect
 | ||
|                     //        && (t.ReadingCategory == ReadingCategory.Visit || t.ReadingCategory == ReadingCategory.Judge)).ToListAsync();
 | ||
| 
 | ||
|                     //        //这里要求 到这里已经如果有裁判  已经生成裁判了保存数据库
 | ||
|                     //        if (taskList.Count == 2 && taskList.Count(t => t.ReadingTaskState == ReadingTaskState.HaveSigned && t.ReadingCategory == ReadingCategory.Visit) == 2)
 | ||
|                     //        {
 | ||
| 
 | ||
|                     //            answer = await TranslatePdStateAsync(visitTaskId, taskInfo.ReadingCategory, taskInfo.CriterionType);
 | ||
| 
 | ||
|                     //            isNeedSend = await DealMedicalReviewTasKGenerateAndIsSendAsync(taskInfo.TrialId, isHandSend, answer, taskList.Select(t => t.Id).ToList(), minUserIdList);
 | ||
|                     //        }
 | ||
|                     //        else if (taskList.Count == 3 && taskList.Count(t => t.ReadingTaskState == ReadingTaskState.HaveSigned) == 3 && taskList.Where(t => t.ReadingCategory == ReadingCategory.Judge).Count() == 1)
 | ||
|                     //        {
 | ||
|                     //            var judgeResultId = taskList.Where(t => t.ReadingCategory == ReadingCategory.Judge).First().JudgeResultTaskId.Value;
 | ||
|                     //            answer = await TranslatePdStateAsync(judgeResultId, ReadingCategory.Visit, taskInfo.CriterionType);
 | ||
| 
 | ||
|                     //            isNeedSend = await DealMedicalReviewTasKGenerateAndIsSendAsync(taskInfo.TrialId, isHandSend, answer, taskList.Where(t => t.ReadingCategory == ReadingCategory.Judge).Select(t => t.Id).ToList(), minUserIdList);
 | ||
| 
 | ||
| 
 | ||
|                     //        }
 | ||
|                     //        else
 | ||
|                     //        {
 | ||
|                     //            isNeedSend = false;
 | ||
|                     //        }
 | ||
| 
 | ||
|                     //    }
 | ||
|                     //    else
 | ||
|                     //    {
 | ||
|                     //---无序阅片配置有误(应为单重无仲裁对象,双重针对访视仲裁),请核查!
 | ||
|                     //        throw new BusinessValidationFailedException(_localizer["TrialEmailN_UnblindedSequencedReading"]);
 | ||
|                     //    }
 | ||
| 
 | ||
|                     //}
 | ||
| 
 | ||
|                     #endregion
 | ||
|                 }
 | ||
|                 else
 | ||
|                 {
 | ||
|                     isNeedSend = false;
 | ||
|                 }
 | ||
| 
 | ||
|                 #endregion
 | ||
| 
 | ||
| 
 | ||
|                 #region MiniWord 组织字典 发送
 | ||
| 
 | ||
| 
 | ||
|                 if (emailStoreMode == EmailStoreSendMode.NotStoreLocalOnlySentEmail)
 | ||
|                 {
 | ||
| 
 | ||
|                     var phyPath = FileStoreHelper.GetPhysicalFilePath(_hostEnvironment, sendFileRelativePath);
 | ||
| 
 | ||
|                     var attachPrefix = $"{taskInfo.SubjectCode}";
 | ||
| 
 | ||
|                     //先预先生成了邮件,发送预先生成的邮件
 | ||
|                     sendEmailConfig.EmailAttachMentConfigList.Add(new EmailAttachMentConfig()
 | ||
|                     {
 | ||
|                         FileName = $"{attachPrefix}_{Path.GetFileNameWithoutExtension(_userInfo.IsEn_Us ? trialEmailConfig.AttachName : trialEmailConfig!.AttachNameCN)}.pdf",
 | ||
| 
 | ||
|                         FileStream = File.OpenRead(phyPath),
 | ||
|                     });
 | ||
| 
 | ||
| 
 | ||
|                     await SendEmailHelper.SendEmailAsync(sendEmailConfig);
 | ||
| 
 | ||
|                     return string.Empty;
 | ||
|                 }
 | ||
| 
 | ||
|                 var value = new Dictionary<string, object>()
 | ||
|                 {
 | ||
|                     ["SponsorName"] = taskInfo.SponsorName,
 | ||
|                     ["ResearchProgramNo"] = taskInfo.ResearchProgramNo,
 | ||
|                     ["TrialSiteCode"] = taskInfo.TrialSiteCode,
 | ||
|                     ["SubjectCode"] = taskInfo.SubjectCode,
 | ||
|                     ["VisitName"] = taskInfo.SourceSubjectVisitId != null ? taskInfo.VisitName : taskInfo.ModuleVisitName,
 | ||
|                     ["EarliestScanDate"] = taskInfo.SourceSubjectVisitId != null ? taskInfo.VisitEarliestScanDate?.ToString("yyyy-MM-dd") : taskInfo.ModuleEarliestScanDate?.ToString("yyyy-MM-dd"),
 | ||
|                     ["SignTime"] = taskInfo.SignTime?.ToString("yyyy-MM-dd"),
 | ||
|                     ["Result"] = answer
 | ||
| 
 | ||
|                 };
 | ||
| 
 | ||
|                 var path = FileStoreHelper.GetPhysicalFilePath(_hostEnvironment, _userInfo.IsEn_Us ? trialEmailConfig.AttachPath : trialEmailConfig.AttachCNPath);
 | ||
| 
 | ||
|                 var (serverFilePath, relativePath, fileRealName) = FileStoreHelper.GetSubjectEnrollConfirmOrPDEmailPath(_hostEnvironment, Path.GetFileName(path), taskInfo.TrialId, taskInfo.TrialSiteId, taskInfo.SubjectId, true);
 | ||
| 
 | ||
|                 if (emailStoreMode == EmailStoreSendMode.StoreLocalSend || emailStoreMode == EmailStoreSendMode.OnlyStoreLocalNotSentEmail)
 | ||
|                 {
 | ||
| 
 | ||
|                     MemoryStream wordMemoryStream = new MemoryStream();
 | ||
| 
 | ||
| 
 | ||
|                     MiniSoftware.MiniWord.SaveAsByTemplate(wordMemoryStream, path, value);
 | ||
| 
 | ||
| 
 | ||
|                     if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows))
 | ||
|                     {
 | ||
|                         Document document = new Document();
 | ||
| 
 | ||
|                         document.LoadFromStream(wordMemoryStream, FileFormat.Docx);
 | ||
| 
 | ||
|                         document.SaveToFile(serverFilePath, FileFormat.PDF);
 | ||
|                     }
 | ||
|                     else
 | ||
|                     {
 | ||
|                         var wordStoreServerPath = Path.Combine(Path.GetDirectoryName(serverFilePath), Path.GetFileNameWithoutExtension(serverFilePath) + ".docx");
 | ||
| 
 | ||
|                         using (FileStream fileStream = new FileStream(wordStoreServerPath, FileMode.Create, FileAccess.Write))
 | ||
|                         {
 | ||
|                             wordMemoryStream.WriteTo(fileStream);
 | ||
|                         }
 | ||
|                         FileConvertHelper.ConvertWordToPdf(wordStoreServerPath, Path.GetDirectoryName(serverFilePath));
 | ||
| 
 | ||
|                         File.Delete(wordStoreServerPath);
 | ||
|                     }
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|                 }
 | ||
|                 //手动生成发送的邮件内容,但是并不发送
 | ||
|                 if (emailStoreMode == EmailStoreSendMode.OnlyStoreLocalNotSentEmail)
 | ||
|                 {
 | ||
|                     isNeedSend = false;
 | ||
| 
 | ||
|                     return relativePath;
 | ||
|                 }
 | ||
| 
 | ||
| 
 | ||
|                 //正常的即时生成邮件  并发送邮件
 | ||
|                 if (isNeedSend)
 | ||
|                 {
 | ||
| 
 | ||
| 
 | ||
|                     MemoryStream wordMemoryStream = new MemoryStream();
 | ||
|                     MemoryStream pdfMemoryStream = new MemoryStream();
 | ||
| 
 | ||
| 
 | ||
|                     MiniSoftware.MiniWord.SaveAsByTemplate(wordMemoryStream, path, value);
 | ||
| 
 | ||
|                     if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows))
 | ||
|                     {
 | ||
|                         Document document = new Document();
 | ||
|                         document.LoadFromStream(wordMemoryStream, FileFormat.Docx);
 | ||
|                         document.SaveToStream(pdfMemoryStream, FileFormat.PDF);
 | ||
| 
 | ||
|                     }
 | ||
|                     else
 | ||
|                     {
 | ||
|                         var wordStoreServerPath = Path.Combine(Path.GetDirectoryName(serverFilePath), Path.GetFileNameWithoutExtension(serverFilePath) + ".docx");
 | ||
| 
 | ||
|                         using (FileStream fileStream = new FileStream(wordStoreServerPath, FileMode.Create, FileAccess.Write))
 | ||
|                         {
 | ||
|                             wordMemoryStream.WriteTo(fileStream);
 | ||
|                         }
 | ||
|                         FileConvertHelper.ConvertWordToPdf(wordStoreServerPath, Path.GetDirectoryName(serverFilePath));
 | ||
| 
 | ||
|                         File.Delete(wordStoreServerPath);
 | ||
| 
 | ||
|                         using (FileStream fileStream = new FileStream(serverFilePath, FileMode.Open, FileAccess.Read))
 | ||
|                         {
 | ||
|                             fileStream.CopyTo(pdfMemoryStream);
 | ||
|                         }
 | ||
| 
 | ||
|                     }
 | ||
| 
 | ||
|                     pdfMemoryStream.Seek(0, SeekOrigin.Begin);
 | ||
|                     sendEmailConfig.EmailAttachMentConfigList.Add(new EmailAttachMentConfig()
 | ||
|                     {
 | ||
|                         FileName = $"{taskInfo.SubjectCode}_{Path.GetFileNameWithoutExtension(_userInfo.IsEn_Us ? trialEmailConfig.AttachName : trialEmailConfig.AttachNameCN)}.pdf",
 | ||
| 
 | ||
|                         FileStream = pdfMemoryStream
 | ||
|                     });
 | ||
| 
 | ||
| 
 | ||
|                     await SendEmailHelper.SendEmailAsync(sendEmailConfig);
 | ||
| 
 | ||
|                 }
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|                 return string.Empty;
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|                 #endregion
 | ||
|             }
 | ||
|             else
 | ||
|             {
 | ||
|                 return string.Empty;
 | ||
|             }
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|         }
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|         /// <summary>
 | ||
|         /// 手动生成入组确认 或者PD 进展的邮件   如果能发送,会返回文件的路径,否则会给出提示
 | ||
|         /// </summary>
 | ||
|         /// <param name="generateEmailCommand"></param>
 | ||
| 
 | ||
|         /// <returns></returns>
 | ||
|         [HttpPost]
 | ||
|         public async Task<IResponseOutput> ManualGenerateEmailFile(GenerateEmailCommand generateEmailCommand)
 | ||
|         {
 | ||
|             var subjectId = generateEmailCommand.SubjectId;
 | ||
|             var businessScenarioEnum = generateEmailCommand.BusinessScenarioEnum;
 | ||
|             var trialReadingCriterionId = generateEmailCommand.TrialReadingCriterionId;
 | ||
| 
 | ||
| 
 | ||
|             var trialConfig = await _subjectRepository.Where(t => t.Id == subjectId).Select(t => new { t.Trial.IsEnrollementQualificationConfirm, t.Trial.IsPDProgressView }).FirstNotNullAsync();
 | ||
| 
 | ||
|             //找到入组确认 或者Pd 进展   已生成任务的  访视
 | ||
|             var subjectVisitList = await _subjectVisitRepository.Where(t => t.SubjectId == subjectId & t.CheckState == CheckStateEnum.CVPassed && (t.IsEnrollmentConfirm == true || t.PDState == PDStateEnum.PDProgress)).ToListAsync();
 | ||
| 
 | ||
|             if (businessScenarioEnum == EmailBusinessScenario.EnrollConfirmed)
 | ||
|             {
 | ||
| 
 | ||
|                 if (trialConfig.IsEnrollementQualificationConfirm == false)
 | ||
|                 {
 | ||
|                     //---项目未配置入组确认!
 | ||
|                     return ResponseOutput.NotOk(_localizer["TrialEmailN_InCons"]);
 | ||
| 
 | ||
|                 }
 | ||
|                 var exisitBaseline = subjectVisitList.FirstOrDefault(t => t.IsEnrollmentConfirm);
 | ||
|                 if (exisitBaseline == null)
 | ||
|                 {
 | ||
|                     //---不存在配置了入组确认的并且生成任务的基线访视
 | ||
|                     return ResponseOutput.NotOk(_localizer["TrialEmailN_NoBaseLine"]);
 | ||
|                 }
 | ||
|                 else
 | ||
|                 {
 | ||
|                     //入组确认不用管项目的 有序 无序  单重  双重  阅片
 | ||
| 
 | ||
|                     //找到最早签名的
 | ||
|                     var firstSignTask = await _visitTaskRepository.Where(t => t.SourceSubjectVisitId == exisitBaseline.Id /*&& t.TaskState == TaskState.Effect*/ && t.IsAnalysisCreate == false
 | ||
|                                                            && t.ReadingTaskState == ReadingTaskState.HaveSigned && t.TrialReadingCriterionId == trialReadingCriterionId).OrderBy(t => t.SignTime).FirstOrDefaultAsync();
 | ||
| 
 | ||
| 
 | ||
|                     if (firstSignTask != null)
 | ||
|                     {
 | ||
|                         var task = await _visitTaskRepository.Where(t => t.SourceSubjectVisitId == exisitBaseline.Id && t.TaskState == TaskState.Effect && t.DoctorUserId == firstSignTask.DoctorUserId && t.IsAnalysisCreate == false
 | ||
|                                                          && t.ReadingTaskState == ReadingTaskState.HaveSigned && t.TrialReadingCriterionId == trialReadingCriterionId).OrderBy(t => t.SignTime).FirstOrDefaultAsync();
 | ||
| 
 | ||
|                         //如果存在做完的该任务
 | ||
| 
 | ||
|                         if (task == null)
 | ||
|                         {
 | ||
|                             //---做入组确认的阅片人基线任务没有阅片完!
 | ||
|                             return ResponseOutput.NotOk(_localizer["TrialEmailN_IncompBase"]);
 | ||
|                         }
 | ||
|                         else
 | ||
|                         {
 | ||
|                             var filePath = await BaseBusinessScenarioSendEmailAsync(task.Id, true, EmailStoreSendMode.OnlyStoreLocalNotSentEmail, string.Empty);
 | ||
| 
 | ||
|                             if (string.IsNullOrEmpty(filePath))
 | ||
|                             {
 | ||
|                                 //---邮件手动生成失败,请联系开发核实该场景失败原因
 | ||
|                                 return ResponseOutput.NotOk(_localizer["TrialEmailN_EmailFail"]);
 | ||
|                             }
 | ||
|                             else
 | ||
|                             {
 | ||
|                                 return ResponseOutput.Ok(new { RelativePath = filePath, TaskName = task.TaskName, VisitTaskId = task.Id });
 | ||
| 
 | ||
|                             }
 | ||
| 
 | ||
| 
 | ||
|                         }
 | ||
|                     }
 | ||
|                     else
 | ||
|                     {
 | ||
|                         //---当前未有阅片人读完基线任务!
 | ||
|                         return ResponseOutput.NotOk(_localizer["TrialEmailN_NoReader"]);
 | ||
|                     }
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|                 }
 | ||
|             }
 | ||
| 
 | ||
|             else if (businessScenarioEnum == EmailBusinessScenario.PDConfirmed)
 | ||
|             {
 | ||
| 
 | ||
|                 if (trialConfig.IsPDProgressView == false)
 | ||
|                 {
 | ||
|                     //---项目未配置PD进展!
 | ||
|                     return ResponseOutput.NotOk(_localizer["TrialEmailN_NoPDConfig"]);
 | ||
|                 }
 | ||
| 
 | ||
|                 //是否是截止访视 截止访视在全局发  否则就在当前访视发
 | ||
| 
 | ||
|                 var pdSubjectVisitIdList = subjectVisitList.Where(t => t.PDState == PDStateEnum.PDProgress).OrderBy(t => t.VisitNum).Select(t => (Guid?)t.Id).ToList();
 | ||
| 
 | ||
|                 if (pdSubjectVisitIdList.Count == 0)
 | ||
|                 {
 | ||
|                     //---不存在配置了PD进展的并且生成任务的访视
 | ||
|                     return ResponseOutput.NotOk(_localizer["TrialEmailN_NoPDTasks"]);
 | ||
|                 }
 | ||
| 
 | ||
| 
 | ||
|                 var currentLatestPdVisitId = pdSubjectVisitIdList.Last();
 | ||
|                 //标准配置
 | ||
|                 var trialReadingCriterionConfig = await _readingQuestionCriterionTrialRepository.Where(t => t.Id == trialReadingCriterionId).Select(t => new
 | ||
|                 { TrialReadingCriterionId = t.Id, t.ReadingType, t.IsReadingTaskViewInOrder, t.CriterionType, t.ArbitrationRule }).FirstNotNullAsync();
 | ||
| 
 | ||
|                 // 项目双重
 | ||
|                 if (trialReadingCriterionConfig.ReadingType == ReadingMethod.Double && trialReadingCriterionConfig.IsReadingTaskViewInOrder == ReadingOrder.InOrder)
 | ||
|                 {
 | ||
|                     //仲裁在访视上面
 | ||
|                     if (trialReadingCriterionConfig.ArbitrationRule == ArbitrationRule.Visit)
 | ||
|                     {
 | ||
|                         //在两位阅片人读完访视后,如果有裁判者等裁判读完,如果无裁判则等第二个人的读完
 | ||
| 
 | ||
|                         var taskList = await _visitTaskRepository.Where(t => t.SourceSubjectVisitId == currentLatestPdVisitId && t.TrialReadingCriterionId == trialReadingCriterionId && t.IsAnalysisCreate == false
 | ||
|                         && t.TaskState == TaskState.Effect && (t.ReadingCategory == ReadingCategory.Visit || t.ReadingCategory == ReadingCategory.Judge)).ToListAsync();
 | ||
| 
 | ||
|                         var totalTaskCount = taskList.Count;
 | ||
|                         var finishedCount = taskList.Where(t => t.ReadingTaskState == ReadingTaskState.HaveSigned).Count();
 | ||
| 
 | ||
| 
 | ||
|                         //发送随访的
 | ||
|                         if (totalTaskCount == 2 && totalTaskCount == finishedCount)
 | ||
|                         {
 | ||
|                             var task = taskList.FirstOrDefault(t => t.ReadingCategory == ReadingCategory.Visit);
 | ||
| 
 | ||
|                             var filePath = await BaseBusinessScenarioSendEmailAsync(task!.Id, true, EmailStoreSendMode.OnlyStoreLocalNotSentEmail, string.Empty);
 | ||
| 
 | ||
|                             return ResponseOutput.Ok(new { RelativePath = filePath, TaskName = task.TaskName, VisitTaskId = task.Id });
 | ||
|                         }
 | ||
|                         //发送全局
 | ||
|                         else if (totalTaskCount == 3 && totalTaskCount == finishedCount)
 | ||
|                         {
 | ||
|                             var task = taskList.FirstOrDefault(t => t.ReadingCategory == ReadingCategory.Judge);
 | ||
| 
 | ||
|                             var filePath = await BaseBusinessScenarioSendEmailAsync(task!.Id, true, EmailStoreSendMode.OnlyStoreLocalNotSentEmail, string.Empty);
 | ||
| 
 | ||
|                             return ResponseOutput.Ok(new { RelativePath = filePath, TaskName = task.TaskName, VisitTaskId = task.Id });
 | ||
|                         }
 | ||
|                         else
 | ||
|                         {
 | ||
|                             //---当前受试者最新PD访视阅片任务完成状态不符合发送条件
 | ||
|                             return ResponseOutput.NotOk(_localizer["TrialEmailN_PDNotFinished"]);
 | ||
|                         }
 | ||
| 
 | ||
|                     }
 | ||
|                     //仲裁在阅片期上
 | ||
|                     else if (trialReadingCriterionConfig.ArbitrationRule == ArbitrationRule.Reading)
 | ||
|                     {
 | ||
|                         var existReadModule = await _readModuleRepository.Where(t => t.TrialReadingCriterionId == trialReadingCriterionId && t.SubjectVisitId == currentLatestPdVisitId && t.ReadingSetType == ReadingSetType.ImageReading)
 | ||
|                         .FirstOrDefaultAsync();
 | ||
| 
 | ||
|                         if (existReadModule == null)
 | ||
|                         {
 | ||
|                             //---项目配置了阅片期仲裁,但是当前受试者最新PD访视没有影像学阅片期
 | ||
|                             return ResponseOutput.NotOk(_localizer["TrialEmailN_PDNoImaging"]);
 | ||
|                         }
 | ||
|                         else
 | ||
|                         {
 | ||
|                             var taskList = await _visitTaskRepository.Where(t => t.TrialReadingCriterionId == trialReadingCriterionId && t.IsAnalysisCreate == false && t.TaskState == TaskState.Effect && t.SouceReadModuleId == existReadModule.Id
 | ||
|                              && (t.ReadingCategory == ReadingCategory.Global || t.ReadingCategory == ReadingCategory.Judge)).ToListAsync();
 | ||
| 
 | ||
|                             var totalTaskCount = taskList.Count;
 | ||
|                             var finishedCount = taskList.Where(t => t.ReadingTaskState == ReadingTaskState.HaveSigned).Count();
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|                             //发送全局的
 | ||
|                             if (totalTaskCount == 2 && totalTaskCount == finishedCount)
 | ||
|                             {
 | ||
|                                 var task = taskList.FirstOrDefault(t => t.ReadingCategory == ReadingCategory.Global);
 | ||
| 
 | ||
|                                 var filePath = await BaseBusinessScenarioSendEmailAsync(task!.Id, true, EmailStoreSendMode.OnlyStoreLocalNotSentEmail, string.Empty);
 | ||
| 
 | ||
|                                 return ResponseOutput.Ok(new { RelativePath = filePath, TaskName = task.TaskName, VisitTaskId = task.Id });
 | ||
|                             }
 | ||
|                             //发送全局裁判的
 | ||
|                             else if (totalTaskCount == 3 && totalTaskCount == finishedCount)
 | ||
|                             {
 | ||
|                                 var task = taskList.FirstOrDefault(t => t.ReadingCategory == ReadingCategory.Judge);
 | ||
| 
 | ||
|                                 var filePath = await BaseBusinessScenarioSendEmailAsync(task!.Id, true, EmailStoreSendMode.OnlyStoreLocalNotSentEmail, string.Empty);
 | ||
| 
 | ||
|                                 return ResponseOutput.Ok(new { RelativePath = filePath, TaskName = task.TaskName, VisitTaskId = task.Id });
 | ||
|                             }
 | ||
| 
 | ||
| 
 | ||
|                             else
 | ||
|                             {
 | ||
|                                 //---当前受试者最新PD访视阅片期任务完成状态不符合发送条件
 | ||
|                                 return ResponseOutput.NotOk(_localizer["TrialEmailN_PDPhaseNotFinished"]);
 | ||
|                             }
 | ||
|                         }
 | ||
| 
 | ||
| 
 | ||
|                     }
 | ||
|                     else
 | ||
|                     {
 | ||
|                         //---未定义该仲裁规则发送业务逻辑!
 | ||
|                         return ResponseOutput.NotOk(_localizer["TrialEmailN_NoRuleDefined"]);
 | ||
|                     }
 | ||
|                 }
 | ||
| 
 | ||
|                 #region 发送邮件屏蔽单重阅片情况
 | ||
|                 //// 项目单重   判断最新的Pd 访视是否完成 是否有阅片期即可  
 | ||
|                 //else if (trialReadingCriterionConfig.ReadingType == ReadingMethod.Single)
 | ||
|                 //{
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|                 //    var task = await _visitTaskRepository.Where(t => t.SourceSubjectVisitId == currentLatestPdVisitId && t.TaskState == TaskState.Effect && t.IsAnalysisCreate == false
 | ||
|                 //                                         && t.ReadingTaskState == ReadingTaskState.HaveSigned && t.TrialReadingCriterionId == trialReadingCriterionId).FirstOrDefaultAsync();
 | ||
| 
 | ||
| 
 | ||
|                 //    if (task == null)
 | ||
|                 //    {
 | ||
|                 //        return ResponseOutput.NotOk("当前受试者最新PD访视任务未阅片完成");
 | ||
|                 //    }
 | ||
|                 //    else
 | ||
|                 //    {
 | ||
|                 //        //存在阅片期  那么就是截止访视
 | ||
| 
 | ||
|                 //        var existReadModule = await _readModuleRepository.Where(t => t.TrialReadingCriterionId == trialReadingCriterionId && t.SubjectVisitId == currentLatestPdVisitId && t.ReadingSetType == ReadingSetType.ImageReading)
 | ||
|                 //            .FirstOrDefaultAsync();
 | ||
|                 //        if (existReadModule != null)
 | ||
|                 //        {
 | ||
| 
 | ||
|                 //            var global = await _visitTaskRepository.Where(t => t.SouceReadModuleId == currentLatestPdVisitId && t.TaskState == TaskState.Effect && t.IsAnalysisCreate == false
 | ||
|                 //                                                && t.ReadingTaskState == ReadingTaskState.HaveSigned && t.TrialReadingCriterionId == trialReadingCriterionId).FirstOrDefaultAsync();
 | ||
| 
 | ||
| 
 | ||
|                 //            if (global != null)
 | ||
|                 //            {
 | ||
|                 //                var filePath = await BaseBusinessScenarioSendEmailAsync(global.Id, true, EmailStoreSendMode.OnlyStoreLocalNotSentEmail, string.Empty);
 | ||
| 
 | ||
|                 //                return ResponseOutput.Ok(new { RelativePath = filePath, TaskName = task.TaskName, VisitTaskId = task.Id });
 | ||
|                 //            }
 | ||
|                 //            else
 | ||
|                 //            {
 | ||
|                 //                return ResponseOutput.NotOk("当前受试者阅片期任务未阅片完成");
 | ||
|                 //            }
 | ||
| 
 | ||
|                 //        }
 | ||
|                 //        else//非截止访视 在访视读完后,发送
 | ||
|                 //        {
 | ||
|                 //            var filePath = await BaseBusinessScenarioSendEmailAsync(task.Id, true, EmailStoreSendMode.OnlyStoreLocalNotSentEmail, string.Empty);
 | ||
| 
 | ||
|                 //            return ResponseOutput.Ok(new { RelativePath = filePath, TaskName = task.TaskName, VisitTaskId = task.Id });
 | ||
|                 //        }
 | ||
|                 //    }
 | ||
| 
 | ||
| 
 | ||
|                 //}
 | ||
|                 #endregion
 | ||
| 
 | ||
|                 else
 | ||
|                 {
 | ||
|                     //---当前项目配置,不满足双重有序阅片,不满足发送条件!
 | ||
|                     return ResponseOutput.NotOk(_localizer["TrialEmailN_NoDoubleOrder"]);
 | ||
|                 }
 | ||
| 
 | ||
|             }
 | ||
| 
 | ||
|             else
 | ||
|             {
 | ||
|                 //---当前项目配置,未定义发送业务逻辑!
 | ||
|                 return ResponseOutput.NotOk(_localizer["TrialEmailN_NoSendLogicDefined"]);
 | ||
|             }
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|         }
 | ||
| 
 | ||
|         /// <summary>
 | ||
|         /// 手动发送邮件
 | ||
|         /// </summary>
 | ||
|         /// <param name="visitTaskId"></param>
 | ||
|         /// <param name="sendFileRelativePath"></param>
 | ||
|         /// <returns></returns>
 | ||
|         [HttpPut]
 | ||
|         public async Task<IResponseOutput> ManualSendEmail(Guid visitTaskId, string sendFileRelativePath)
 | ||
|         {
 | ||
|             var filePath = await BaseBusinessScenarioSendEmailAsync(visitTaskId, true, EmailStoreSendMode.NotStoreLocalOnlySentEmail, sendFileRelativePath);
 | ||
| 
 | ||
|             return ResponseOutput.Ok();
 | ||
| 
 | ||
|         }
 | ||
| 
 | ||
|         /// <summary>
 | ||
|         /// 
 | ||
|         /// </summary>
 | ||
|         /// <param name="visitTaskId"> 任务Id</param>
 | ||
|         /// <param name="readingCategory"> 任务类型</param>
 | ||
|         /// <param name="criterionType">标准类型</param>
 | ||
|         /// <param name="IsGlobalGenerate">  是否是全局产生(区分裁判任务)</param>
 | ||
|         /// <returns></returns>
 | ||
|         /// <exception cref="BusinessValidationFailedException"></exception>
 | ||
|         private async Task<string> TranslatePdStateAsync(Guid visitTaskId, ReadingCategory readingCategory, CriterionType criterionType, bool? IsGlobalGenerate = null)
 | ||
|         {
 | ||
| 
 | ||
|             var answer = string.Empty;
 | ||
| 
 | ||
|             ReadingTaskQuestionAnswer visitQuestionAnswer = null;
 | ||
| 
 | ||
|             ReadingTaskQuestionAnswer globalQuestionAnswer = null;
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|             switch (criterionType)
 | ||
|             {
 | ||
| 
 | ||
| 
 | ||
|                 case CriterionType.RECIST1Point1:
 | ||
| 
 | ||
|                     if (readingCategory == ReadingCategory.Visit)
 | ||
|                     {
 | ||
| 
 | ||
|                         visitQuestionAnswer = await _readingTaskQuestionAnswerRepository.Where(t => t.VisitTaskId == visitTaskId && t.ReadingQuestionTrial.QuestionType == QuestionType.Tumor).FirstNotNullAsync();
 | ||
| 
 | ||
| 
 | ||
|                         answer = visitQuestionAnswer.Answer;
 | ||
|                     }
 | ||
|                     else if (readingCategory == ReadingCategory.Global)
 | ||
|                     {
 | ||
|                         var questionAnsewer = await _readingGlobalTaskInfoRepository.Where(t => t.GlobalTaskId == visitTaskId && t.TrialReadingQuestion.QuestionType == QuestionType.Tumor).OrderByDescending(c => c.VisitTask.VisitTaskNum).FirstNotNullAsync();
 | ||
| 
 | ||
| 
 | ||
|                         answer = questionAnsewer.Answer;
 | ||
|                         if (string.IsNullOrEmpty(questionAnsewer.Answer))
 | ||
|                         {
 | ||
|                             answer = await _readingTaskQuestionAnswerRepository.Where(t => questionAnsewer.TaskId == t.VisitTaskId && t.ReadingQuestionTrial.QuestionType == QuestionType.Tumor)
 | ||
|                          .Select(t => t.Answer).FirstOrDefaultAsync();
 | ||
|                         }
 | ||
| 
 | ||
|                     }
 | ||
|                     //else if (readingCategory == ReadingCategory.Judge)
 | ||
|                     //{
 | ||
|                     //    var judgeResultTaskId = await _visitTaskRepository.Where(t => t.Id == visitTaskId).Select(t => t.JudgeResultTaskId).FirstNotNullAsync();
 | ||
| 
 | ||
|                     //    var questionAnsewer = await _readingTaskQuestionAnswerRepository.Where(t => t.VisitTaskId == judgeResultTaskId && t.ReadingQuestionTrial.QuestionType == QuestionType.Tumor).FirstNotNullAsync();
 | ||
| 
 | ||
| 
 | ||
|                     //    answer = questionAnsewer.Answer;
 | ||
|                     //}
 | ||
|                     else
 | ||
|                     {
 | ||
|                         //---不应有 除访视、裁判、全局其他类型的任务进行发送邮件,请核查业务逻辑
 | ||
|                         throw new BusinessValidationFailedException(_localizer["TrialEmailN_InvalidTaskTypeForEmailSending"]);
 | ||
|                     }
 | ||
| 
 | ||
|                     if (answer == OverallAssessment.PD.GetEnumInt())
 | ||
|                     {
 | ||
|                         answer = "是";
 | ||
|                     }
 | ||
|                     else
 | ||
|                     {
 | ||
|                         answer = "否";
 | ||
|                     }
 | ||
| 
 | ||
|                     break;
 | ||
| 
 | ||
|                 case CriterionType.PCWG3:
 | ||
|                     if (readingCategory == ReadingCategory.Visit)
 | ||
|                     {
 | ||
| 
 | ||
|                         visitQuestionAnswer = await _readingTaskQuestionAnswerRepository.Where(t => t.VisitTaskId == visitTaskId && t.ReadingQuestionTrial.QuestionType == QuestionType.SiteVisitForTumorEvaluation).FirstNotNullAsync();
 | ||
| 
 | ||
| 
 | ||
|                         answer = visitQuestionAnswer.Answer;
 | ||
|                     }
 | ||
|                     else if (readingCategory == ReadingCategory.Global)
 | ||
|                     {
 | ||
|                         var questionAnsewer = await _readingGlobalTaskInfoRepository.Where(t => t.TaskId == visitTaskId && t.TrialReadingQuestion.QuestionType == QuestionType.SiteVisitForTumorEvaluation).FirstNotNullAsync();
 | ||
| 
 | ||
|                         answer = questionAnsewer.Answer;
 | ||
|                     }
 | ||
|                     //else if (readingCategory == ReadingCategory.Judge)
 | ||
|                     //{
 | ||
|                     //    //var judgeResultTaskId = await _visitTaskRepository.Where(t => t.Id == visitTaskId).Select(t => t.JudgeResultTaskId).FirstNotNullAsync();
 | ||
| 
 | ||
|                     //    var questionAnsewer = await _readingTaskQuestionAnswerRepository.Where(t => t.VisitTaskId == visitTaskId && t.ReadingQuestionTrial.QuestionType == QuestionType.SiteVisitForTumorEvaluation).FirstNotNullAsync();
 | ||
| 
 | ||
|                     //    answer = questionAnsewer.Answer;
 | ||
|                     //}
 | ||
|                     else
 | ||
|                     {
 | ||
|                         //---不应有 除访视、裁判、全局其他类型的任务进行发送邮件,请核查业务逻辑
 | ||
|                         throw new BusinessValidationFailedException(_localizer["TrialEmailN_InvalidTaskTypeForEmailSending"]);
 | ||
|                     }
 | ||
| 
 | ||
|                     if (answer == VisitTumorEvaluation.PD.GetEnumInt())
 | ||
|                     {
 | ||
|                         answer = "是";
 | ||
|                     }
 | ||
|                     if (answer == VisitTumorEvaluation.ND.GetEnumInt())
 | ||
|                     {
 | ||
|                         answer = "ND";
 | ||
|                     }
 | ||
|                     if (answer == VisitTumorEvaluation.NE.GetEnumInt())
 | ||
|                     {
 | ||
|                         answer = "NE";
 | ||
|                     }
 | ||
|                     else
 | ||
|                     {
 | ||
|                         answer = "否";
 | ||
|                     }
 | ||
|                     break;
 | ||
|                 case CriterionType.SelfDefine:
 | ||
|                 case CriterionType.mRECISTMesothelioma:
 | ||
|                 case CriterionType.RECIL:
 | ||
|                 case CriterionType.RECIST1Point0:
 | ||
|                 case CriterionType.WHO:
 | ||
|                 case CriterionType.PERCIST:
 | ||
|                 case CriterionType.Forrest:
 | ||
|                 case CriterionType.Lugano2014:
 | ||
|                 case CriterionType.IRECIST1Point1:
 | ||
|                 case CriterionType.RANO_BM:
 | ||
|                 case CriterionType.RANO:
 | ||
|                 case CriterionType.IWCLL2018:
 | ||
|                 case CriterionType.mRECISTHCC:
 | ||
|                 case CriterionType.Cheson2007:
 | ||
|                 case CriterionType.IMWG2016:
 | ||
|                 default:
 | ||
| 
 | ||
|                     //---该标准任务还未定义PD获取逻辑,联系业务和后台开发协商后补充
 | ||
|                     throw new BusinessValidationFailedException(_localizer["TrialEmailN_PDLogicNotDefined"]);
 | ||
|             }
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|             return answer;
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|         }
 | ||
| 
 | ||
| 
 | ||
|         /// <summary>
 | ||
|         /// 选择人员下拉
 | ||
|         /// </summary>
 | ||
|         /// <param name="trialId"></param>
 | ||
|         /// <returns></returns>
 | ||
|         public async Task<List<TrialUserType>> GetTrialUserTypeSelectList(Guid trialId)
 | ||
|         {
 | ||
| 
 | ||
|             var query = _trialUserRoleRepository.Where(t => t.TrialId == trialId, false, true).IgnoreQueryFilters().Select(t => t.UserRole.UserTypeRole).Distinct()
 | ||
| 
 | ||
|               .ProjectTo<TrialUserType>(_mapper.ConfigurationProvider);
 | ||
| 
 | ||
|             return await query.ToListAsync();
 | ||
| 
 | ||
|         }
 | ||
| 
 | ||
|         /// <summary>
 | ||
|         /// 黑名单用户Id  列表
 | ||
|         /// </summary>
 | ||
|         /// <param name="trialEmailNoticeConfigId"></param>
 | ||
|         /// <returns></returns>
 | ||
|         public async Task<List<TrialSelectUser>> GetTrialUserIdSelectList(Guid trialEmailNoticeConfigId)
 | ||
|         {
 | ||
| 
 | ||
|             var trialEmailNoticeConfig = await _trialEmailNoticeConfigRepository.Where(t => t.Id == trialEmailNoticeConfigId).Include(t => t.TrialEmailNoticeUserList).FirstNotNullAsync();
 | ||
| 
 | ||
|             var trialId = trialEmailNoticeConfig.TrialId;
 | ||
| 
 | ||
|             var userTypeList = trialEmailNoticeConfig.TrialEmailNoticeUserList.Select(t => t.UserType).ToList();
 | ||
| 
 | ||
| 
 | ||
|             var query = _trialUserRoleRepository.Where(t => t.TrialId == trialId && userTypeList.Contains(t.UserRole.UserTypeEnum), false, true).IgnoreQueryFilters()
 | ||
|                 .Select(t => new TrialSelectUser()
 | ||
|                 {
 | ||
|                     UserId = t.UserId,
 | ||
|                     UserName = t.UserRole.UserName,
 | ||
|                     RealName = t.UserRole.FullName,
 | ||
|                     UserTypeEnum = t.UserRole.UserTypeEnum
 | ||
|                 }).Distinct();
 | ||
| 
 | ||
|             return await query.ToListAsync();
 | ||
|         }
 | ||
| 
 | ||
|         /// <summary>
 | ||
|         /// 获取系统 邮件配置 勾选列表
 | ||
|         /// </summary>
 | ||
|         /// <param name="inQuery"></param>
 | ||
|         /// <returns></returns>
 | ||
|         [HttpPost]
 | ||
|         public async Task<PageOutput<TrialSelectEmailNoticeConfigView>> GetSysEmailNoticeConfigList(EmailNoticeConfigQuery inQuery)
 | ||
|         {
 | ||
|             var trialConfig = _trialRepository.Where(t => t.Id == inQuery.TrialId).Select(t => new { t.IsEnrollementQualificationConfirm, t.IsPDProgressView }).First();
 | ||
| 
 | ||
|             var emailNoticeConfigQueryable = _emailNoticeConfigRepository.Where(t => t.BusinessLevelEnum == BusinessLevel.Trial)
 | ||
|            .WhereIf(inQuery.BusinessScenarioEnum != null, t => t.BusinessScenarioEnum == inQuery.BusinessScenarioEnum)
 | ||
|            .WhereIf(inQuery.IsReturnRequired != null, t => t.IsReturnRequired == inQuery.IsReturnRequired)
 | ||
|            .WhereIf(inQuery.IsEnable != null, t => t.IsEnable == inQuery.IsEnable)
 | ||
|            .WhereIf(inQuery.IsDistinguishCriteria != null, t => t.IsDistinguishCriteria == inQuery.IsDistinguishCriteria)
 | ||
|            .WhereIf(inQuery.BusinessModuleEnum != null, t => t.BusinessModuleEnum == inQuery.BusinessModuleEnum)
 | ||
|            .WhereIf(inQuery.EmailUrgentEnum != null, t => t.EmailUrgentEnum == inQuery.EmailUrgentEnum)
 | ||
|            .WhereIf(inQuery.ToUserType != null, t => t.EmailNoticeUserTypeList.Any(t => t.UserType == inQuery.ToUserType && t.EmailUserType == EmailUserType.To))
 | ||
|            .WhereIf(inQuery.CopyUserType != null, t => t.EmailNoticeUserTypeList.Any(t => t.UserType == inQuery.CopyUserType && t.EmailUserType == EmailUserType.Copy))
 | ||
|            .WhereIf(trialConfig.IsEnrollementQualificationConfirm == false, t => t.BusinessModuleEnum != BusinessModule.EligibilityVerification)
 | ||
|            .WhereIf(trialConfig.IsPDProgressView == false, t => t.BusinessModuleEnum != BusinessModule.PDVerification)
 | ||
|            .WhereIf(trialConfig.IsPDProgressView == false && trialConfig.IsEnrollementQualificationConfirm == false, t => t.BusinessModuleEnum != BusinessModule.PDVerification
 | ||
|                && t.BusinessModuleEnum != BusinessModule.EligibilityVerification)
 | ||
|            .ProjectTo<TrialSelectEmailNoticeConfigView>(_mapper.ConfigurationProvider, new { trialId = inQuery.TrialId });
 | ||
| 
 | ||
|             return await emailNoticeConfigQueryable.ToPagedListAsync(inQuery);
 | ||
|         }
 | ||
| 
 | ||
|         public async Task<IResponseOutput> BatchAddEnrollOrPdEmailConfig(Guid trialId)
 | ||
|         {
 | ||
|             var trialConfig = _trialRepository.Where(t => t.Id == trialId).Select(t => new { t.IsEnrollementQualificationConfirm, t.IsPDProgressView }).First();
 | ||
| 
 | ||
|             var emailNoticeConfigQueryable = _emailNoticeConfigRepository
 | ||
| 
 | ||
|               .WhereIf(trialConfig.IsEnrollementQualificationConfirm == true && trialConfig.IsPDProgressView == false, t => t.BusinessModuleEnum == BusinessModule.EligibilityVerification || t.BusinessModuleEnum == BusinessModule.Eligibility_PDVerification)
 | ||
|               .WhereIf(trialConfig.IsEnrollementQualificationConfirm == false && trialConfig.IsPDProgressView == true, t => t.BusinessModuleEnum == BusinessModule.PDVerification || t.BusinessModuleEnum == BusinessModule.Eligibility_PDVerification)
 | ||
|                .WhereIf(trialConfig.IsPDProgressView == true && trialConfig.IsEnrollementQualificationConfirm == true, t => t.BusinessModuleEnum == BusinessModule.PDVerification
 | ||
|                || t.BusinessModuleEnum == BusinessModule.EligibilityVerification || t.BusinessModuleEnum == BusinessModule.Eligibility_PDVerification)
 | ||
|               .ProjectTo<TrialSelectEmailNoticeConfigView>(_mapper.ConfigurationProvider, new { trialId = trialId });
 | ||
| 
 | ||
| 
 | ||
|             var list = await emailNoticeConfigQueryable.ToListAsync();
 | ||
| 
 | ||
|             var addList = _mapper.Map<List<BatchAddTrialEmailNoticeConfig>>(list.Where(t => t.IsHaveSelected == false).ToList());
 | ||
| 
 | ||
|             foreach (var item in addList)
 | ||
|             {
 | ||
|                 item.TrialId = trialId;
 | ||
|             }
 | ||
| 
 | ||
|             return await BatchAddSysEmailConfig(addList);
 | ||
| 
 | ||
|         }
 | ||
|         /// <summary>
 | ||
|         ///  批量勾选  传递列表每行数据,后台进行处理转换,建立关联关系
 | ||
|         /// </summary>
 | ||
|         /// <param name="batchAddList"></param>
 | ||
|         /// <returns></returns>
 | ||
|         public async Task<IResponseOutput> BatchAddSysEmailConfig(List<BatchAddTrialEmailNoticeConfig> batchAddList)
 | ||
|         {
 | ||
|             if (!batchAddList.Any())
 | ||
|             {
 | ||
|                 return ResponseOutput.Ok();
 | ||
|             }
 | ||
| 
 | ||
|             var first = batchAddList.First();
 | ||
|             var trialId = first.TrialId;
 | ||
| 
 | ||
|             var emailConfig = await _trialRepository.Where(t => t.Id == trialId).Select(x => new
 | ||
|             {
 | ||
|                 TrialId = x.Id,
 | ||
|                 EmailAuthorizationCode = x.EmailAuthorizationCode,
 | ||
|                 EmailSMTPServerAddress = x.EmailSMTPServerAddress,
 | ||
|                 EmailFromEmail = x.EmailFromEmail,
 | ||
|                 EmailFromName = x.EmailFromName,
 | ||
|                 IsConfigureEmail = x.IsConfigureEmail,
 | ||
|                 EmailSMTPServerPort = x.EmailSMTPServerPort
 | ||
| 
 | ||
|             }).FirstNotNullAsync();
 | ||
| 
 | ||
|             var list = await _readingQuestionCriterionTrialRepository.Where(t => t.TrialId == trialId && t.IsConfirm).Select(t => new { t.CriterionType, TrialReadingCriterionId = t.Id }).ToListAsync();
 | ||
| 
 | ||
| 
 | ||
|             var addList = _mapper.Map<List<TrialEmailNoticeConfig>>(batchAddList);
 | ||
| 
 | ||
| 
 | ||
|             foreach (var item in addList)
 | ||
|             {
 | ||
|                 item.SysEmailNoticeConfigId = item.Id;
 | ||
|                 item.Id = Guid.Empty;
 | ||
| 
 | ||
|                 item.AuthorizationCode = emailConfig.EmailAuthorizationCode;
 | ||
|                 item.FromEmail = emailConfig.EmailFromEmail;
 | ||
|                 item.SMTPServerAddress = emailConfig.EmailSMTPServerAddress;
 | ||
|                 item.FromName = emailConfig.EmailFromName;
 | ||
|                 item.SMTPServerPort = emailConfig.EmailSMTPServerPort;
 | ||
|                 item.IsAutoSend = true;
 | ||
|                 item.IsEnable = true;
 | ||
| 
 | ||
|                 item.TrialReadingCriterionId = list.FirstOrDefault(t => t.CriterionType == item.CriterionTypeEnum)?.TrialReadingCriterionId;
 | ||
| 
 | ||
|                 item.TrialEmailNoticeUserList.AddRange(batchAddList.Where(t => t.Id == item.SysEmailNoticeConfigId)
 | ||
|                     .SelectMany(t => t.ToUserTypeList).Select(t => new TrialEmailNoticeUser() { EmailUserType = EmailUserType.To, UserType = t }));
 | ||
| 
 | ||
|                 item.TrialEmailNoticeUserList.AddRange(batchAddList.Where(t => t.Id == item.SysEmailNoticeConfigId)
 | ||
|                    .SelectMany(t => t.CopyUserTypeList).Select(t => new TrialEmailNoticeUser() { EmailUserType = EmailUserType.Copy, UserType = t }));
 | ||
| 
 | ||
| 
 | ||
|                 await _trialEmailNoticeConfigRepository.AddAsync(item);
 | ||
| 
 | ||
|             }
 | ||
| 
 | ||
|             await _trialEmailNoticeConfigRepository.SaveChangesAsync();
 | ||
| 
 | ||
|             //处理定时任务
 | ||
|             var taskInfoList = await _trialEmailNoticeConfigRepository.Where(t => t.TrialId== trialId && t.EmailCron != string.Empty && t.IsAutoSend)
 | ||
|              .Select(t => new { t.Id, t.Code, TrialCode = t.Trial.TrialCode, t.EmailCron, t.BusinessScenarioEnum, t.TrialId })
 | ||
|              .ToListAsync();
 | ||
| 
 | ||
|             foreach (var task in taskInfoList)
 | ||
|             {
 | ||
|                 //利用主键作为任务Id
 | ||
|                 var jobId = $"{task.TrialId}({task.TrialCode})_({task.BusinessScenarioEnum})";
 | ||
| 
 | ||
|                 HangfireJobHelper.AddOrUpdateTrialCronJob(jobId, trialId, task.BusinessScenarioEnum, task.EmailCron);
 | ||
|             }
 | ||
| 
 | ||
|             return ResponseOutput.Ok();
 | ||
| 
 | ||
| 
 | ||
|         }
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|         [HttpPost]
 | ||
|         public async Task<IResponseOutput<List<TrialEmailNoticeConfigView>>> GetTrialEmailNoticeConfigList(TrialEmailNoticeConfigQuery inQuery)
 | ||
|         {
 | ||
|             //await SyncSystemEmainCofigDocListAsync(inQuery.TrialId);
 | ||
| 
 | ||
|             var trialConfig = _trialRepository.Where(t => t.Id == inQuery.TrialId).Select(t => new { t.IsEnrollementQualificationConfirm, t.IsPDProgressView }).First();
 | ||
| 
 | ||
|             var trialEmailNoticeConfigQueryable = _trialEmailNoticeConfigRepository.Where(t => t.TrialId == inQuery.TrialId)
 | ||
|               .WhereIf(inQuery.IsDistinguishCriteria == false, t => t.TrialReadingCriterionId == null)
 | ||
|               .WhereIf(inQuery.IsDistinguishCriteria == true, t => t.CriterionTypeEnum != null)
 | ||
|               .WhereIf(inQuery.TrialReadingCriterionId != null, t => t.TrialReadingCriterionId == inQuery.TrialReadingCriterionId)
 | ||
|               .WhereIf(inQuery.BusinessScenarioEnum != null, t => t.BusinessScenarioEnum == inQuery.BusinessScenarioEnum)
 | ||
|               .WhereIf(inQuery.EmailUrgentEnum != null, t => t.EmailUrgentEnum == inQuery.EmailUrgentEnum)
 | ||
|               .WhereIf(inQuery.IsEnable != null, t => t.IsEnable == inQuery.IsEnable)
 | ||
|               .WhereIf(inQuery.ToUserType != null, t => t.TrialEmailNoticeUserList.Any(t => t.UserType == inQuery.ToUserType && t.EmailUserType == EmailUserType.To))
 | ||
|               .WhereIf(inQuery.CopyUserType != null, t => t.TrialEmailNoticeUserList.Any(t => t.UserType == inQuery.CopyUserType && t.EmailUserType == EmailUserType.Copy))
 | ||
| 
 | ||
|               .WhereIf(inQuery.BusinessModuleEnum != null, t => t.BusinessModuleEnum == inQuery.BusinessModuleEnum)
 | ||
| 
 | ||
|               .ProjectTo<TrialEmailNoticeConfigView>(_mapper.ConfigurationProvider);
 | ||
| 
 | ||
|             var sortField = string.IsNullOrWhiteSpace(inQuery.SortField) ? nameof(TrialEmailNoticeConfigView.Code) : inQuery.SortField;
 | ||
|             var orderQuery = inQuery.Asc ? trialEmailNoticeConfigQueryable.OrderBy(sortField) : trialEmailNoticeConfigQueryable.OrderBy(sortField + " desc");
 | ||
|             var list = await orderQuery.ToListAsync();
 | ||
| 
 | ||
|             return ResponseOutput.Ok(list, trialConfig);
 | ||
|         }
 | ||
| 
 | ||
| 
 | ||
|         [TrialGlobalLimit("AfterStopCannNotOpt")]
 | ||
|         public async Task<IResponseOutput> AddOrUpdateTrialEmailNoticeConfig(TrialEmailNoticeConfigAddOrEdit addOrEditTrialEmailNoticeConfig)
 | ||
|         {
 | ||
|             await TestEmailConfigAsync(addOrEditTrialEmailNoticeConfig);
 | ||
| 
 | ||
| 
 | ||
|             if (addOrEditTrialEmailNoticeConfig.Id == null)
 | ||
|             {
 | ||
| 
 | ||
|                 var entity = _mapper.Map<TrialEmailNoticeConfig>(addOrEditTrialEmailNoticeConfig);
 | ||
| 
 | ||
| 
 | ||
|                 foreach (var item in addOrEditTrialEmailNoticeConfig.ToUserTypeList)
 | ||
|                 {
 | ||
|                     entity.TrialEmailNoticeUserList.Add(new TrialEmailNoticeUser() { EmailUserType = EmailUserType.To, UserType = item });
 | ||
| 
 | ||
|                 }
 | ||
| 
 | ||
|                 foreach (var item in addOrEditTrialEmailNoticeConfig.CopyUserTypeList)
 | ||
|                 {
 | ||
|                     entity.TrialEmailNoticeUserList.Add(new TrialEmailNoticeUser() { EmailUserType = EmailUserType.Copy, UserType = item });
 | ||
| 
 | ||
|                 }
 | ||
| 
 | ||
|                 foreach (var userid in addOrEditTrialEmailNoticeConfig.BlackUserIdList)
 | ||
|                 {
 | ||
|                     entity.TrialEmailBlackUserList.Add(new TrialEmailBlackUser() { UserId = userid });
 | ||
|                 }
 | ||
| 
 | ||
|                 await _trialEmailNoticeConfigRepository.AddAsync(entity, true);
 | ||
| 
 | ||
|                 return ResponseOutput.Ok(entity.Id.ToString());
 | ||
| 
 | ||
|             }
 | ||
|             else
 | ||
|             {
 | ||
|                 var id = (Guid)addOrEditTrialEmailNoticeConfig.Id;
 | ||
| 
 | ||
|                 await _trialEmailNoticeUserRepository.BatchDeleteNoTrackingAsync(t => t.TrialEmailNoticeConfigId == addOrEditTrialEmailNoticeConfig.Id);
 | ||
|                 await _trialEmailBlackUserRepository.BatchDeleteNoTrackingAsync(t => t.TrialEmailNoticeConfigId == addOrEditTrialEmailNoticeConfig.Id);
 | ||
| 
 | ||
| 
 | ||
|                 List<TrialEmailNoticeUser> trialEmailNoticeUsers = new List<TrialEmailNoticeUser>();
 | ||
| 
 | ||
| 
 | ||
|                 foreach (var item in addOrEditTrialEmailNoticeConfig.ToUserTypeList)
 | ||
|                 {
 | ||
|                     trialEmailNoticeUsers.Add(new TrialEmailNoticeUser() { EmailUserType = EmailUserType.To, UserType = item, TrialEmailNoticeConfigId = id });
 | ||
| 
 | ||
|                 }
 | ||
| 
 | ||
|                 foreach (var item in addOrEditTrialEmailNoticeConfig.CopyUserTypeList)
 | ||
|                 {
 | ||
|                     trialEmailNoticeUsers.Add(new TrialEmailNoticeUser() { EmailUserType = EmailUserType.Copy, UserType = item, TrialEmailNoticeConfigId = id });
 | ||
| 
 | ||
|                 }
 | ||
|                 await _trialEmailNoticeUserRepository.AddRangeAsync(trialEmailNoticeUsers);
 | ||
| 
 | ||
|                 foreach (var userid in addOrEditTrialEmailNoticeConfig.BlackUserIdList)
 | ||
|                 {
 | ||
|                     await _trialEmailBlackUserRepository.AddAsync(new TrialEmailBlackUser() { UserId = userid, TrialEmailNoticeConfigId = id });
 | ||
| 
 | ||
|                 }
 | ||
| 
 | ||
|                 await _trialEmailNoticeConfigRepository.UpdateFromDTOAsync(addOrEditTrialEmailNoticeConfig);
 | ||
| 
 | ||
| 
 | ||
|                 await _trialEmailNoticeConfigRepository.SaveChangesAsync();
 | ||
| 
 | ||
|                 var cronInfo = await _trialEmailNoticeConfigRepository.Where(t => t.Id == addOrEditTrialEmailNoticeConfig.Id)
 | ||
|             .Select(t => new { t.Id, t.Code, TrialCode = t.Trial.TrialCode, t.EmailCron, t.BusinessScenarioEnum, t.TrialId })
 | ||
|             .FirstAsync();
 | ||
| 
 | ||
|                 var jobId = $"{cronInfo.TrialId}({cronInfo.TrialCode})_({cronInfo.BusinessScenarioEnum})";
 | ||
| 
 | ||
| 
 | ||
|                 if (addOrEditTrialEmailNoticeConfig.IsAutoSend)
 | ||
|                 {
 | ||
|                     HangfireJobHelper.AddOrUpdateTrialCronJob(jobId, addOrEditTrialEmailNoticeConfig.TrialId, addOrEditTrialEmailNoticeConfig.BusinessScenarioEnum, addOrEditTrialEmailNoticeConfig.EmailCron);
 | ||
| 
 | ||
|                 }
 | ||
|                 else
 | ||
|                 {
 | ||
|                     HangfireJobHelper.RemoveCronJob(jobId);
 | ||
|                 }
 | ||
| 
 | ||
|                 return ResponseOutput.Ok();
 | ||
|             }
 | ||
| 
 | ||
| 
 | ||
|         }
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|         private async Task TestEmailConfigAsync(TrialEmailNoticeConfigAddOrEdit config)
 | ||
|         {
 | ||
| 
 | ||
| 
 | ||
|             if (!config.FromEmail.Contains("@") || string.IsNullOrEmpty(config.FromEmail))
 | ||
|             {
 | ||
|                 //---项目发件邮箱配置有误,请核实
 | ||
|                 throw new BusinessValidationFailedException(_localizer["TrialEmailN_InvalidEmailConfig"]);
 | ||
|             }
 | ||
| 
 | ||
|             try
 | ||
|             {
 | ||
|                 await SendEmailHelper.TestEmailConfigAsync(new SystemEmailSendConfig()
 | ||
|                 {
 | ||
|                     AuthorizationCode = config.AuthorizationCode,
 | ||
|                     FromEmail = config.FromEmail,
 | ||
|                     FromName = config.FromName,
 | ||
|                     Host = config.SMTPServerAddress,
 | ||
|                     Port = config.SMTPServerPort
 | ||
|                 });
 | ||
| 
 | ||
|             }
 | ||
|             catch (Exception ex)
 | ||
|             {
 | ||
| 
 | ||
|                 //---发件人配置错误,请核对服务器地址或者授权码是否填写有误
 | ||
|                 throw new BusinessValidationFailedException(_localizer["TrialEmailN_InvalidSenderEmailConfig"]);
 | ||
|             }
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
| 
 | ||
|             #region 人员还未加入,可以先配置邮件  历史废弃
 | ||
| 
 | ||
|             //var toUserList = await _trialUserRoleRepository.Where(t => t.TrialId == config.TrialId)
 | ||
|             //   .WhereIf(config.ToUserTypeList != null, t => config.ToUserTypeList.Contains(t.User.UserTypeEnum))
 | ||
|             //   .Select(t => new { t.User.EMail, t.User.FullName }).ToListAsync();
 | ||
| 
 | ||
| 
 | ||
|             //if (toUserList.Count() == 0 || toUserList.Where(t => t.EMail.Contains("@")).Count() == 0)
 | ||
|             //{
 | ||
|             //    //---项目没有有效的收件人,无法发送邮件
 | ||
|             //    throw new BusinessValidationFailedException(_localizer["TrialEmailN_InvalidRecipient"]);
 | ||
|             //}
 | ||
| 
 | ||
|             //var sendEmailConfig = new SMTPEmailConfig();
 | ||
| 
 | ||
|             //sendEmailConfig.FromEmailAddress = new MimeKit.MailboxAddress(config.FromName, config.FromEmail);
 | ||
|             //sendEmailConfig.AuthorizationCode = config.AuthorizationCode;
 | ||
|             //sendEmailConfig.UserName = config.FromEmail;
 | ||
| 
 | ||
|             //sendEmailConfig.Host = config.SMTPServerAddress;
 | ||
|             //sendEmailConfig.Port = config.SMTPServerPort;
 | ||
| 
 | ||
| 
 | ||
|             //sendEmailConfig.ToMailAddressList.Add(new MimeKit.MailboxAddress(config.FromName, config.FromEmail));
 | ||
| 
 | ||
| 
 | ||
|             //var pathToFile = _hostEnvironment.WebRootPath
 | ||
|             //          + Path.DirectorySeparatorChar.ToString()
 | ||
|             //          + "EmailTemplate"
 | ||
|             //          + Path.DirectorySeparatorChar.ToString()
 | ||
|             //         //+ "EmailConfigTest.html";
 | ||
| 
 | ||
|             //         + (_userInfo.IsEn_Us ? "EmailConfigTest_US.html" : "EmailConfigTest.html");
 | ||
| 
 | ||
| 
 | ||
|             ////---项目邮件测试
 | ||
|             //sendEmailConfig.TopicDescription = _localizer["TrialEmailN_EmailTestMessage"];
 | ||
| 
 | ||
|             //using (StreamReader SourceReader = System.IO.File.OpenText(pathToFile))
 | ||
|             //{
 | ||
|             //    var templateInfo = SourceReader.ReadToEnd();
 | ||
| 
 | ||
| 
 | ||
|             //    sendEmailConfig.HtmlBodyStr = string.Format(templateInfo,
 | ||
|             //    //--- 收到此邮件,代表邮件配置正确
 | ||
|             //        _localizer["TrialEmailN_ConfigurationCorrect"]
 | ||
|             //        );
 | ||
|             //}
 | ||
| 
 | ||
|             //try
 | ||
|             //{
 | ||
|             //    await SendEmailHelper.SendEmailAsync(sendEmailConfig);
 | ||
| 
 | ||
|             //}
 | ||
|             //catch (Exception ex)
 | ||
|             //{
 | ||
| 
 | ||
|             //    //---发件人配置错误,请核对服务器地址或者授权码是否填写有误
 | ||
|             //    throw new BusinessValidationFailedException(_localizer["TrialEmailN_InvalidSenderEmailConfig"] + ex.Message);
 | ||
|             //}
 | ||
| 
 | ||
|             #endregion
 | ||
| 
 | ||
| 
 | ||
|         }
 | ||
| 
 | ||
|         [TrialGlobalLimit("AfterStopCannNotOpt")]
 | ||
|         [HttpDelete("{trialEmailNoticeConfigId:guid}")]
 | ||
|         public async Task<IResponseOutput> DeleteTrialEmailNoticeConfig(Guid trialEmailNoticeConfigId)
 | ||
|         {
 | ||
| 
 | ||
|             var cronInfo = await _trialEmailNoticeConfigRepository.Where(t => t.Id == trialEmailNoticeConfigId)
 | ||
|            .Select(t => new { t.Id, t.Code, TrialCode = t.Trial.TrialCode, t.EmailCron, t.BusinessScenarioEnum, t.TrialId })
 | ||
|            .FirstAsync();
 | ||
| 
 | ||
|             var jobId = $"{cronInfo.TrialId}({cronInfo.TrialCode})_({cronInfo.BusinessScenarioEnum})";
 | ||
| 
 | ||
|             HangfireJobHelper.RemoveCronJob(jobId);
 | ||
| 
 | ||
|             var success = await _trialEmailNoticeConfigRepository.DeleteFromQueryAsync(t => t.Id == trialEmailNoticeConfigId, true);
 | ||
| 
 | ||
|             return ResponseOutput.Ok();
 | ||
|         }
 | ||
| 
 | ||
| 
 | ||
|     }
 | ||
| }
 |