diff --git a/IRaCIS.Core.API/Controllers/InspectionController.cs b/IRaCIS.Core.API/Controllers/InspectionController.cs index c7e94417f..0abd96915 100644 --- a/IRaCIS.Core.API/Controllers/InspectionController.cs +++ b/IRaCIS.Core.API/Controllers/InspectionController.cs @@ -139,11 +139,11 @@ namespace IRaCIS.Core.API.Controllers public async Task AddOrUpdateQCChallenge(DataInspectionDto opt) { var fun = await _qCOperationService.AddOrUpdateQCChallenge(opt.OptCommand.qaQuestionCommand, opt.OptCommand.trialId, opt.OptCommand.trialQCProcess, opt.OptCommand.currentQCType); - if (!fun.IsSuccess) - { - return ResponseOutput.NotOk(fun.ErrorMessage); - } - return await _inspectionService.Enforcement(opt.OptCommand, opt.AuditInfo, opt.SignInfo, null, fun); + opt.AuditInfo.GeneralId = fun.Id; + Dictionary keyValuePairs = new Dictionary(); + keyValuePairs.Add("ChallengeCode", fun.ChallengeCode); + opt.AuditInfo.JsonDetail = _inspectionService.AddJsonItem(opt.AuditInfo.JsonDetail, keyValuePairs); + return await _inspectionService.Enforcement(opt.OptCommand, opt.AuditInfo, opt.SignInfo, null, ResponseOutput.Ok()); } @@ -155,6 +155,7 @@ namespace IRaCIS.Core.API.Controllers public async Task AddQCChallengeReply(DataInspectionDto opt) { var fun = _qCOperationService.AddQCChallengeReply; + opt.AuditInfo.GeneralId = opt.OptCommand.QCChallengeId; return await _inspectionService.Enforcement(opt.OptCommand, opt.AuditInfo, opt.SignInfo, fun); } @@ -166,6 +167,8 @@ namespace IRaCIS.Core.API.Controllers public async Task CloseQCChallenge(DataInspectionDto opt) { var fun = await _qCOperationService.CloseQCChallenge(opt.OptCommand.qcChallengeId, opt.OptCommand.subjectVisitId, opt.OptCommand.closeEnum, opt.OptCommand.closeReason); + + opt.AuditInfo.GeneralId = opt.OptCommand.qcChallengeId; if (!fun.IsSuccess) { return ResponseOutput.NotOk(fun.ErrorMessage); @@ -185,7 +188,7 @@ namespace IRaCIS.Core.API.Controllers public async Task DeleteQCChallenge(DataInspectionDto opt) { var fun = _qCOperationService.DeleteQCChallenge; - + opt.AuditInfo.GeneralId = opt.OptCommand.Id; return await _inspectionService.Enforcement(opt.OptCommand.Id, opt.AuditInfo, opt.SignInfo, fun); } @@ -200,6 +203,7 @@ namespace IRaCIS.Core.API.Controllers { var fun = _qCOperationService.AddCheckChallengeReply; + return await _inspectionService.Enforcement(opt.OptCommand, opt.AuditInfo, opt.SignInfo, fun); } @@ -264,6 +268,89 @@ namespace IRaCIS.Core.API.Controllers return await _inspectionService.Enforcement(opt.OptCommand, opt.AuditInfo, opt.SignInfo,null, fun); } + /// + /// 1、设置为不读片,2 设置为读片(取消 先前设置为不读片) 4 设置为删除(数据库记录软删除) 5 恢复为未删除 + /// + [HttpPost, Route("Inspection/QCOperation/SetSeriesState")] + [UnitOfWork] + public async Task SetSeriesState(DataInspectionDto opt) + { + var fun = await _qCOperationService.SetSeriesState(opt.OptCommand.subjectVisitId, opt.OptCommand.studyId, opt.OptCommand.seriesId, opt.OptCommand.state); + return await _inspectionService.Enforcement(opt.OptCommand, opt.AuditInfo, opt.SignInfo, null, fun); + } + + /// + /// 设置QC 通过或者不通过 7:QC failed 8:QC passed + /// + [HttpPost, Route("Inspection/QCOperation/QCPassedOrFailed")] + [UnitOfWork] + public async Task QCPassedOrFailed(DataInspectionDto opt) + { + var fun = await _qCOperationService.QCPassedOrFailed(opt.OptCommand.trialId, opt.OptCommand.subjectVisitId, opt.OptCommand.signId, opt.OptCommand.auditState); + return await _inspectionService.Enforcement(opt.OptCommand, opt.AuditInfo, opt.SignInfo, null, fun); + } + + + /// + /// 设置、取消 访视紧急 + /// + [HttpPost, Route("Inspection/QCOperation/SetVisitUrgent")] + [UnitOfWork] + public async Task SetVisitUrgent(DataInspectionDto opt ) + { + var fun = await _qCOperationService.SetVisitUrgent(opt.OptCommand.trialId, opt.OptCommand.subjectVisitId, opt.OptCommand.setOrCancel); + return await _inspectionService.Enforcement(opt.OptCommand, opt.AuditInfo, opt.SignInfo, null, fun); + } + + + /// + /// QA设置 需要重传 + /// + [HttpPost, Route("Inspection/QCOperation/SetNeedReupload")] + [UnitOfWork] + public async Task SetNeedReupload(DataInspectionDto opt) + { + var fun = await _qCOperationService.SetNeedReupload(opt.OptCommand.trialId, opt.OptCommand.qcChallengeId); + return await _inspectionService.Enforcement(opt.OptCommand, opt.AuditInfo, opt.SignInfo, null, fun); + } + + + /// + /// CRC 设置已经重传完成 + /// + [HttpPost, Route("Inspection/QCOperation/SetReuploadFinished")] + [UnitOfWork] + public async Task SetReuploadFinished(DataInspectionDto opt) + { + var fun = _qCOperationService.SetReuploadFinished; + return await _inspectionService.Enforcement(opt.OptCommand, opt.AuditInfo, opt.SignInfo, fun); + } + + /// + /// CRCRequestReUpload + /// + /// + /// + [HttpPost, Route("Inspection/QCOperation/CRCRequestReUpload")] + [UnitOfWork] + public async Task CRCRequestReUpload(DataInspectionDto opt) + { + var fun = _qCOperationService.CRCRequestReUpload; + return await _inspectionService.Enforcement(opt.OptCommand.Id, opt.AuditInfo, opt.SignInfo, fun); + } + + /// + /// + /// + /// + /// + [HttpPost, Route("Inspection/QCOperation/ForwardSVDicomImage")] + [UnitOfWork] + public async Task ForwardSVDicomImage(DataInspectionDto opt) + { + var fun = _qCOperationService.ForwardSVDicomImage; + return await _inspectionService.Enforcement(opt.OptCommand, opt.AuditInfo, opt.SignInfo, fun); + } #endregion #region 影像上传 diff --git a/IRaCIS.Core.API/IRaCIS.Core.API.xml b/IRaCIS.Core.API/IRaCIS.Core.API.xml index 5f8bdcbb2..b3ecf5c74 100644 --- a/IRaCIS.Core.API/IRaCIS.Core.API.xml +++ b/IRaCIS.Core.API/IRaCIS.Core.API.xml @@ -126,6 +126,45 @@ QC修改检查部位和 拍片类型 + + + 1、设置为不读片,2 设置为读片(取消 先前设置为不读片) 4 设置为删除(数据库记录软删除) 5 恢复为未删除 + + + + + 设置QC 通过或者不通过 7:QC failed 8:QC passed + + + + + 设置、取消 访视紧急 + + + + + QA设置 需要重传 + + + + + CRC 设置已经重传完成 + + + + + CRCRequestReUpload + + + + + + + + + + + 疾病进展确认评估 diff --git a/IRaCIS.Core.Application/IRaCIS.Core.Application.xml b/IRaCIS.Core.Application/IRaCIS.Core.Application.xml index 22cd5d21b..3043c75a0 100644 --- a/IRaCIS.Core.Application/IRaCIS.Core.Application.xml +++ b/IRaCIS.Core.Application/IRaCIS.Core.Application.xml @@ -1527,7 +1527,7 @@ - + QA设置 需要重传 diff --git a/IRaCIS.Core.Application/Service/Inspection/DTO/InspectionModel.cs b/IRaCIS.Core.Application/Service/Inspection/DTO/InspectionModel.cs index 861abed77..5bd79eb20 100644 --- a/IRaCIS.Core.Application/Service/Inspection/DTO/InspectionModel.cs +++ b/IRaCIS.Core.Application/Service/Inspection/DTO/InspectionModel.cs @@ -169,6 +169,36 @@ namespace IRaCIS.Core.Application.Service.Inspection.DTO public string closeReason { get; set; } } + + public class SetNeedReuploadDto + { + public Guid trialId { get; set; } + public Guid qcChallengeId { get; set; } + } + + public class SetVisitUrgentDto + { + public Guid trialId { get; set; } + public Guid subjectVisitId { get; set; } + public bool setOrCancel { get; set; } + } + + public class QCPassedOrFailedDto + { + public Guid trialId { get; set; } + public Guid subjectVisitId { get; set; } + public Guid signId { get; set; } + public AuditStateEnum auditState { get; set; } + } + + public class SetSeriesStateDto + { + public Guid subjectVisitId { get; set; } + public Guid studyId { get; set; } + public Guid seriesId { get; set; } + public int state { get; set; } + } + public class UpdateModalityDto { public Guid id { get; set; } diff --git a/IRaCIS.Core.Application/Service/QC/Interface/IQCOperationService.cs b/IRaCIS.Core.Application/Service/QC/Interface/IQCOperationService.cs index c5784d429..b4e3100be 100644 --- a/IRaCIS.Core.Application/Service/QC/Interface/IQCOperationService.cs +++ b/IRaCIS.Core.Application/Service/QC/Interface/IQCOperationService.cs @@ -11,7 +11,7 @@ namespace IRaCIS.Core.Application.Image.QA public interface IQCOperationService { Task CheckBack(Guid subjectVisitId); - Task SetNeedReupload(Guid trialId, Guid signId, Guid qcChallengeId); + Task SetNeedReupload(Guid trialId, Guid qcChallengeId); Task QCPassedOrFailed(Guid trialId, Guid subjectVisitId, Guid signId, [FromRoute] AuditStateEnum auditState); Task SetCheckPass(Guid subjectVisitId); @@ -19,7 +19,7 @@ namespace IRaCIS.Core.Application.Image.QA Task> AddCheckChallengeReply(CheckChallengeDialogCommand checkDialogCommand); - Task AddOrUpdateQCChallenge(QCChallengeCommand qaQuestionCommand, Guid trialId, [FromRoute] TrialQCProcess trialQCProcess, [FromRoute] CurrentQC currentQCType); + Task AddOrUpdateQCChallenge(QCChallengeCommand qaQuestionCommand, Guid trialId, [FromRoute] TrialQCProcess trialQCProcess, [FromRoute] CurrentQC currentQCType); Task AddOrUpdateQCQuestionAnswerList(QCQuestionAnswerCommand[] qcQuestionAnswerCommands, Guid trialId, Guid subjectVisitId, [FromRoute] TrialQCProcess trialQCProcess, [FromRoute] CurrentQC currentQCType); Task AddQCChallengeReply(QADialogCommand qaDialogCommand); Task CloseCheckChallenge(Guid subjectVisitId); @@ -37,5 +37,7 @@ namespace IRaCIS.Core.Application.Image.QA Task UpdateSubjectAndSVInfo(UploadSubjectAndVisitCommand command); Task UploadVisitCheckExcel(IFormFile file, [FromServices] IMediator _mediator, Guid trialId, [FromServices] IWebHostEnvironment _hostEnvironment); Task VerifyCanQCPassedOrFailed(Guid subjectVisitId); + + Task ForwardSVDicomImage(Guid[] subjectVisitIdList); } } \ No newline at end of file diff --git a/IRaCIS.Core.Application/Service/QC/QCOperationService.cs b/IRaCIS.Core.Application/Service/QC/QCOperationService.cs index c2fef2c4b..c4b37e1e1 100644 --- a/IRaCIS.Core.Application/Service/QC/QCOperationService.cs +++ b/IRaCIS.Core.Application/Service/QC/QCOperationService.cs @@ -21,6 +21,7 @@ using Magicodes.ExporterAndImporter.Excel; using Newtonsoft.Json; using Magicodes.ExporterAndImporter.Csv; using IRaCIS.Core.Application.Service.Inspection.Interface; +using IRaCIS.Core.Infrastructure; namespace IRaCIS.Core.Application.Image.QA { @@ -74,14 +75,15 @@ namespace IRaCIS.Core.Application.Image.QA [HttpPost("{trialId:guid}/{trialQCProcess:int}/{currentQCType:int}")] [TypeFilter(typeof(TrialResourceFilter))] [Authorize(Policy = "ImageQCPolicy")] - public async Task AddOrUpdateQCChallenge(QCChallengeCommand qaQuestionCommand, Guid trialId, [FromRoute] TrialQCProcess trialQCProcess, [FromRoute] CurrentQC currentQCType) + public async Task AddOrUpdateQCChallenge(QCChallengeCommand qaQuestionCommand, Guid trialId, [FromRoute] TrialQCProcess trialQCProcess, [FromRoute] CurrentQC currentQCType) { if (qaQuestionCommand.Id == null) { if (await _repository.AnyAsync(t => t.IsClosed == false && t.SubjectVisitId == qaQuestionCommand.SubjectVisitId && t.ReuploadEnum == QCChanllengeReuploadEnum.QCAgreeUpload)) { - return ResponseOutput.NotOk("当前访视有未关闭的 同意CRC上传的质疑,不允许再次添加质疑"); + throw new BusinessValidationFailedException("当前访视有未关闭的 同意CRC上传的质疑,不允许再次添加质疑"); + } QCChallenge? qcChallenge = null; @@ -90,7 +92,10 @@ namespace IRaCIS.Core.Application.Image.QA { var trialConfig = _repository.Where(t => t.Id == trialId).Select(t => new { TrialId = t.Id, t.QCProcessEnum, t.IsImageConsistencyVerification }).FirstOrDefault(); - if (trialConfig == null) return Null404NotFound(trialConfig); + if (trialConfig == null) + { + throw new BusinessValidationFailedException("项目不存在"); + } #region 处理访视状态变更 //var dbSubjectVisit = _subjectVisitRepository.FirstOrDefault(t => t.Id == qaQuestionCommand.SubjectVisitId); @@ -148,7 +153,7 @@ namespace IRaCIS.Core.Application.Image.QA //分开两个事务 处理访视质疑状态 await DealChallengeState(qcChallenge.SubjectVisitId); - return ResponseOutput.Result(success, qcChallenge.Id); + return qcChallenge; #region 添加的时候把记录给留存 //var templateItems = _mapper.Map>(visitQaCommand.QATrialTemplateItemList); @@ -173,7 +178,10 @@ namespace IRaCIS.Core.Application.Image.QA var qcChallenge = await _repository.FirstOrDefaultAsync(t => t.Id == qaQuestionCommand.Id); - if (qcChallenge == null) return Null404NotFound(qcChallenge); + if (qcChallenge == null) + { + throw new BusinessValidationFailedException("QC问题不存在"); + }; _mapper.Map(qaQuestionCommand, qcChallenge); @@ -182,7 +190,7 @@ namespace IRaCIS.Core.Application.Image.QA await DealChallengeState(qcChallenge.SubjectVisitId); - return ResponseOutput.Result(success); + return qcChallenge; } @@ -1579,7 +1587,7 @@ namespace IRaCIS.Core.Application.Image.QA /// [HttpPut("{trialId:guid}/{qcChallengeId:guid}/{signId:guid}")] [TypeFilter(typeof(TrialResourceFilter))] - public async Task SetNeedReupload(Guid trialId, Guid signId, Guid qcChallengeId) + public async Task SetNeedReupload(Guid trialId, Guid qcChallengeId) { if (_userInfo.UserTypeEnumInt != (int)UserTypeEnum.IQC) { @@ -1654,9 +1662,9 @@ namespace IRaCIS.Core.Application.Image.QA var success = await _repository.SaveChangesAsync(); - var signSuccess = await _repository.UpdateFromQueryAsync(t => t.Id == signId, u => new TrialSign() { IsCompleted = true }); + //var signSuccess = await _repository.UpdateFromQueryAsync(t => t.Id == signId, u => new TrialSign() { IsCompleted = true }); - return ResponseOutput.Result(success && signSuccess); + return ResponseOutput.Result(success); } @@ -1817,7 +1825,8 @@ namespace IRaCIS.Core.Application.Image.QA SiteId = data.SiteId, TrialId = data.TrialId, IsSign = false, - CreateTime=DateTime.Now.AddSeconds(1), + Identification= "Edit|Subject|Info|Subject", + CreateTime =DateTime.Now.AddSeconds(1), JsonDetail = JsonConvert.SerializeObject(new { FirstGiveMedicineTime= command.SubjectFirstGiveMedicineTime.Value.ToString("yyyy-MM-dd") @@ -1863,7 +1872,7 @@ namespace IRaCIS.Core.Application.Image.QA [HttpPost("{trialId:guid}")] - public async Task ForwardSVDicomImage(Guid[] subjectVisitIdList, [FromServices] DicomFileStoreHelper _dicomFileStoreHelper) + public async Task ForwardSVDicomImage(Guid[] subjectVisitIdList) { foreach (var subjectVisitId in subjectVisitIdList) diff --git a/IRaCIS.Core.Application/Service/Visit/DTO/VisitPointViewModel.cs b/IRaCIS.Core.Application/Service/Visit/DTO/VisitPointViewModel.cs index 273de03c8..62dbe26fa 100644 --- a/IRaCIS.Core.Application/Service/Visit/DTO/VisitPointViewModel.cs +++ b/IRaCIS.Core.Application/Service/Visit/DTO/VisitPointViewModel.cs @@ -45,6 +45,7 @@ namespace IRaCIS.Core.Application.Contracts } + public class IDDto { public Guid Id { get; set; } @@ -110,6 +111,11 @@ namespace IRaCIS.Core.Application.Contracts } + + public class ForwardSVDicomImageDto + { + public Guid[] subjectVisitIdList { get; set; } + } public class SubjectVisitSearchDTO : PageInput { public string SubjectInfo { get; set; } = String.Empty; diff --git a/IRaCIS.Core.Application/Service/Visit/SubjectVisitService.cs b/IRaCIS.Core.Application/Service/Visit/SubjectVisitService.cs index 6ebd39541..89f29482b 100644 --- a/IRaCIS.Core.Application/Service/Visit/SubjectVisitService.cs +++ b/IRaCIS.Core.Application/Service/Visit/SubjectVisitService.cs @@ -130,6 +130,7 @@ namespace IRaCIS.Core.Application.Services SiteId = subject.SiteId, TrialId = subject.TrialId, IsSign = false, + Identification= "Edit|Subject|Info|Subject", CreateTime = DateTime.Now.AddSeconds(1), JsonDetail = JsonConvert.SerializeObject(new { diff --git a/IRaCIS.Core.Application/Service/Visit/VisitPlanService.cs b/IRaCIS.Core.Application/Service/Visit/VisitPlanService.cs index 0b752e204..1c929e564 100644 --- a/IRaCIS.Core.Application/Service/Visit/VisitPlanService.cs +++ b/IRaCIS.Core.Application/Service/Visit/VisitPlanService.cs @@ -556,11 +556,12 @@ namespace IRaCIS.Application.Services Identification = "Add|Visit|Info|Visit-Image Upload", JsonDetail = JsonConvert.SerializeObject(new { - IsBaseLine = x.BlindName, + IsBaseLine = x.IsBaseLine, VisitName = x.VisitName, VisitNum = x.VisitNum, VisitDay = x.VisitDay, VisitExecuted=false, + BlindName=x.BlindName, VisitWindowLeft = x.VisitWindowLeft, VisitWindowRight = x.VisitWindowRight, IsEnrollment=y.IsEnrollment, @@ -577,15 +578,18 @@ namespace IRaCIS.Application.Services TrialId = x.TrialId, SubjectCode = y.Code, BlindName = x.BlindName, + SubjectVisitName = x.VisitName, IsSign = false, CreateTime = createtime.AddMilliseconds(500), Identification = "Init|Visit|Status|Visit-Image Upload", JsonDetail = JsonConvert.SerializeObject(new { + BlindName = x.BlindName, VisitName = x.VisitName, SubmitState = "", AuditState = "", + IsBaseLine = x.IsBaseLine, IsEnrollment = y.IsEnrollment, IsUrgent = y.IsUrgent, })