Merge branch 'Test_IRC_Net8' of https://gitea.frp.extimaging.com/XCKJ/irc-netcore-api into Test_IRC_Net8
continuous-integration/drone/push Build is passing
Details
continuous-integration/drone/push Build is passing
Details
commit
a965ab9336
|
|
@ -96,6 +96,12 @@ builder.Services.AddJsonLocalization(options => options.ResourcesPath = "Resourc
|
||||||
// 异常、参数统一验证过滤器、Json序列化配置、字符串参数绑型统一Trim()
|
// 异常、参数统一验证过滤器、Json序列化配置、字符串参数绑型统一Trim()
|
||||||
builder.Services.AddControllers(options =>
|
builder.Services.AddControllers(options =>
|
||||||
{
|
{
|
||||||
|
// 关键配置:禁用不可空引用类型的自动 Required 验证
|
||||||
|
options.SuppressImplicitRequiredAttributeForNonNullableReferenceTypes = true;
|
||||||
|
|
||||||
|
// 插到最前,抢在默认绑定器之前
|
||||||
|
//options.ModelBinderProviders.Insert(0, new SpecificNullableBinderProvider());
|
||||||
|
|
||||||
options.Filters.Add<ModelActionFilter>();
|
options.Filters.Add<ModelActionFilter>();
|
||||||
options.Filters.Add<ProjectExceptionFilter>();
|
options.Filters.Add<ProjectExceptionFilter>();
|
||||||
options.Filters.Add<UnitOfWorkFilter>();
|
options.Filters.Add<UnitOfWorkFilter>();
|
||||||
|
|
|
||||||
|
|
@ -71,29 +71,27 @@ namespace IRaCIS.Core.API
|
||||||
|
|
||||||
DateTime dateTime;
|
DateTime dateTime;
|
||||||
|
|
||||||
if (reader.ValueType == typeof(DateTime) || reader.ValueType == typeof(DateTime?))
|
// 2. 检查目标类型是否可空
|
||||||
|
bool isNullable = objectType == typeof(DateTime?);
|
||||||
|
|
||||||
|
var canConvert = DateTime.TryParse(reader.Value?.ToString(), out dateTime);
|
||||||
|
|
||||||
|
|
||||||
|
if (isNullable == false && canConvert == false)
|
||||||
{
|
{
|
||||||
DateTime? nullableDateTime = reader.Value as DateTime?;
|
|
||||||
|
|
||||||
|
throw new JsonSerializationException($"Could not convert string to DateTime: {reader.Value} Path {reader.Path}");
|
||||||
if (nullableDateTime != null && nullableDateTime.HasValue)
|
|
||||||
{
|
|
||||||
dateTime = nullableDateTime.Value;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
if (DateTime.TryParse((string)reader.Value, out dateTime) == false)
|
if (canConvert == false)
|
||||||
{
|
{
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
////如果前端传递带时区的,那么转换会报错,需要DateTimeKind.Unspecified
|
||||||
|
//dateTime = DateTime.SpecifyKind(dateTime, DateTimeKind.Unspecified);
|
||||||
|
|
||||||
// 将客户端时间转换为服务器时区的时间
|
// 将客户端时间转换为服务器时区的时间
|
||||||
var serverZoneTime = TimeZoneInfo.ConvertTime(dateTime, _clientTimeZone, TimeZoneInfo.Local);
|
var serverZoneTime = TimeZoneInfo.ConvertTime(dateTime, _clientTimeZone, TimeZoneInfo.Local);
|
||||||
|
|
@ -113,7 +111,10 @@ namespace IRaCIS.Core.API
|
||||||
//第一个参数默认使用系统本地时区 也就是应用服务器的时区
|
//第一个参数默认使用系统本地时区 也就是应用服务器的时区
|
||||||
DateTime clientZoneTime = TimeZoneInfo.ConvertTime(nullableDateTime.Value, _clientTimeZone);
|
DateTime clientZoneTime = TimeZoneInfo.ConvertTime(nullableDateTime.Value, _clientTimeZone);
|
||||||
|
|
||||||
//writer.WriteValue(clientZoneTime);
|
|
||||||
|
//// 最简单的方式:创建 DateTimeOffset
|
||||||
|
//DateTimeOffset dateTimeOffset = new DateTimeOffset(clientZoneTime, _clientTimeZone.GetUtcOffset(clientZoneTime));
|
||||||
|
//writer.WriteValue(dateTimeOffset.ToString("yyyy-MM-dd HH:mm:sszzz"));
|
||||||
|
|
||||||
writer.WriteValue(clientZoneTime.ToString(_dateFormat));
|
writer.WriteValue(clientZoneTime.ToString(_dateFormat));
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -3,8 +3,10 @@ using Newtonsoft.Json;
|
||||||
using Newtonsoft.Json.Serialization;
|
using Newtonsoft.Json.Serialization;
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
using System.Diagnostics.CodeAnalysis;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Reflection;
|
using System.Reflection;
|
||||||
|
using System.Reflection.Metadata;
|
||||||
|
|
||||||
namespace IRaCIS.Core.API
|
namespace IRaCIS.Core.API
|
||||||
{
|
{
|
||||||
|
|
@ -51,34 +53,90 @@ namespace IRaCIS.Core.API
|
||||||
}
|
}
|
||||||
public class NullToEmptyStringValueProvider : IValueProvider
|
public class NullToEmptyStringValueProvider : IValueProvider
|
||||||
{
|
{
|
||||||
PropertyInfo _MemberInfo;
|
PropertyInfo _memberInfo;
|
||||||
|
private readonly bool _isNullable;
|
||||||
public NullToEmptyStringValueProvider(PropertyInfo memberInfo)
|
public NullToEmptyStringValueProvider(PropertyInfo memberInfo)
|
||||||
{
|
{
|
||||||
_MemberInfo = memberInfo;
|
_memberInfo = memberInfo;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
// DTO → JSON 返回前端的时候 处理null 变为"" 方便前端判断
|
||||||
public object GetValue(object target)
|
public object GetValue(object target)
|
||||||
{
|
{
|
||||||
object result = _MemberInfo.GetValue(target);
|
var result = _memberInfo.GetValue(target);
|
||||||
if (_MemberInfo.PropertyType == typeof(string) && result == null) result = "";
|
// 检查类型是否为string或string?
|
||||||
else if (_MemberInfo.PropertyType == typeof(String[]) && result == null) result = new string[] { };
|
if (_memberInfo.PropertyType == typeof(string) && result == null)
|
||||||
//else if (_MemberInfo.PropertyType == typeof(Nullable<Int32>) && result == null) result = 0;
|
{
|
||||||
//else if (_MemberInfo.PropertyType == typeof(Nullable<Decimal>) && result == null) result = 0.00M;
|
|
||||||
|
|
||||||
|
#region 返回的时候处理 string string? null 为"" 不区分处理
|
||||||
|
|
||||||
|
|
||||||
|
//// 如果是string?类型,返回null 可以做到,但是得反射,因为 string string? 是编译层区分的
|
||||||
|
|
||||||
|
//var isNullable1 = _memberInfo.CustomAttributes
|
||||||
|
// .Any(a => a.AttributeType.Name == "NullableAttribute");
|
||||||
|
|
||||||
|
////var isNullable2 = _memberInfo.CustomAttributes
|
||||||
|
//// .Any(a => a.AttributeType.FullName == "System.Runtime.CompilerServices.NullableAttribute");
|
||||||
|
|
||||||
|
//if (isNullable1)
|
||||||
|
//{
|
||||||
|
// return result;
|
||||||
|
//}
|
||||||
|
|
||||||
|
#endregion
|
||||||
|
|
||||||
|
|
||||||
|
// 如果是string类型,返回空字符串
|
||||||
|
return string.Empty;
|
||||||
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//影响 模型绑定时接收前端的值,同时影响 正常 JSON 序列化
|
||||||
public void SetValue(object target, object value)
|
public void SetValue(object target, object value)
|
||||||
{
|
{
|
||||||
|
|
||||||
if (_MemberInfo.PropertyType == typeof(string))
|
_memberInfo.SetValue(target, value);
|
||||||
{
|
|
||||||
//去掉前后空格
|
#region 前端针对 string 类型的变量,如果传递null 会报错必传
|
||||||
_MemberInfo.SetValue(target, value == null ? string.Empty : value.ToString() == string.Empty ? value : value/*.ToString().Trim()*/);
|
|
||||||
|
//if (_memberInfo.PropertyType == typeof(string))
|
||||||
|
//{
|
||||||
|
// _memberInfo.SetValue(target, value == null ? string.Empty : value);
|
||||||
|
//}
|
||||||
|
//else
|
||||||
|
//{
|
||||||
|
// _memberInfo.SetValue(target, value);
|
||||||
|
//}
|
||||||
|
|
||||||
|
#endregion
|
||||||
|
|
||||||
|
#region 处理模型验证区分 string string?
|
||||||
|
|
||||||
|
//////接收模型的时候 定义的明明是string 但是上面也有该属性,判断不准的 比如阅片跟踪列表查询
|
||||||
|
//var isNullable1 = _memberInfo.CustomAttributes.Any(a => a.AttributeType.Name == "NullableAttribute");
|
||||||
|
|
||||||
|
////不影响 string? 传递null 变为""
|
||||||
|
//if (_memberInfo.PropertyType == typeof(string) && isNullable1 == false)
|
||||||
|
//{
|
||||||
|
// //如果不处理 前段传递null string不会接收,说前段没传递会验证报错
|
||||||
|
// _memberInfo.SetValue(target, value == null ? string.Empty : value);
|
||||||
|
//}
|
||||||
|
//else
|
||||||
|
//{
|
||||||
|
|
||||||
|
// _memberInfo.SetValue(target, value);
|
||||||
|
|
||||||
|
//}
|
||||||
|
|
||||||
|
#endregion
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
_MemberInfo.SetValue(target, value);
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,11 @@
|
||||||
using Microsoft.AspNetCore.Mvc;
|
using Microsoft.AspNetCore.Mvc;
|
||||||
using Microsoft.AspNetCore.Mvc.Filters;
|
using Microsoft.AspNetCore.Mvc.Filters;
|
||||||
|
using Microsoft.AspNetCore.Mvc.ModelBinding;
|
||||||
|
using Microsoft.AspNetCore.Mvc.ModelBinding.Binders;
|
||||||
|
using Microsoft.AspNetCore.Mvc.ModelBinding.Metadata;
|
||||||
using Microsoft.Extensions.Localization;
|
using Microsoft.Extensions.Localization;
|
||||||
using Newtonsoft.Json;
|
using Newtonsoft.Json;
|
||||||
|
using System.Reflection;
|
||||||
|
|
||||||
|
|
||||||
namespace IRaCIS.Core.Application.Filter;
|
namespace IRaCIS.Core.Application.Filter;
|
||||||
|
|
@ -28,3 +32,7 @@ public class ModelActionFilter(IStringLocalizer _localizer) : ActionFilterAttrib
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,4 +1,5 @@
|
||||||
using FellowOakDicom;
|
using DocumentFormat.OpenXml.Office.CustomUI;
|
||||||
|
using FellowOakDicom;
|
||||||
using FellowOakDicom.Media;
|
using FellowOakDicom.Media;
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
|
@ -57,6 +58,7 @@ namespace IRaCIS.Core.Application.Helper
|
||||||
var mappings = new List<string>();
|
var mappings = new List<string>();
|
||||||
int index = 1;
|
int index = 1;
|
||||||
|
|
||||||
|
var studyUid=list.FirstOrDefault()?.StudyInstanceUid;
|
||||||
|
|
||||||
var dicomDir = new DicomDirectory();
|
var dicomDir = new DicomDirectory();
|
||||||
|
|
||||||
|
|
@ -130,7 +132,7 @@ namespace IRaCIS.Core.Application.Helper
|
||||||
|
|
||||||
var relativePath= await _oSSService.UploadToOSSAsync(memoryStream, ossFolder, "DICOMDIR", true);
|
var relativePath= await _oSSService.UploadToOSSAsync(memoryStream, ossFolder, "DICOMDIR", true);
|
||||||
|
|
||||||
dic.Add("DICOMDIR" , relativePath.Split('/').Last());
|
dic.Add($"{studyUid}_DICOMDIR" , relativePath.Split('/').Last());
|
||||||
}
|
}
|
||||||
|
|
||||||
//清理临时文件
|
//清理临时文件
|
||||||
|
|
|
||||||
|
|
@ -1173,7 +1173,7 @@ public class VisitTaskService(IRepository<VisitTask> _visitTaskRepository,
|
||||||
var visitQuery = _visitTaskRepository.Where(x => x.TrialId == trialId && x.DoctorUserId == _userInfo.UserRoleId && x.TaskState == TaskState.Effect)
|
var visitQuery = _visitTaskRepository.Where(x => x.TrialId == trialId && x.DoctorUserId == _userInfo.UserRoleId && x.TaskState == TaskState.Effect)
|
||||||
.WhereIf(inQuery.SubjectId != null, x => x.SubjectId == inQuery.SubjectId)
|
.WhereIf(inQuery.SubjectId != null, x => x.SubjectId == inQuery.SubjectId)
|
||||||
.WhereIf(!string.IsNullOrEmpty(subjectCode), t => (t.Subject.Code.Contains(subjectCode!) && t.IsAnalysisCreate == false) || (t.BlindSubjectCode.Contains(subjectCode!) && t.IsAnalysisCreate))
|
.WhereIf(!string.IsNullOrEmpty(subjectCode), t => (t.Subject.Code.Contains(subjectCode!) && t.IsAnalysisCreate == false) || (t.BlindSubjectCode.Contains(subjectCode!) && t.IsAnalysisCreate))
|
||||||
.WhereIf(critrion.CriterionType == CriterionType.OCT, t => t.ReadingCategory == ReadingCategory.Visit ? t.SourceSubjectVisit.NoneDicomStudyList.Where(t=>t.Modality=="OCT").SelectMany(t => t.ImageLabelNoneDicomFileList).Any() : true)
|
.WhereIf(critrion.CriterionType == CriterionType.OCT, t => t.ReadingCategory == ReadingCategory.Visit ? t.SourceSubjectVisit.NoneDicomStudyList.Where(t => t.Modality == "OCT").SelectMany(t => t.ImageLabelNoneDicomFileList).Any() : true)
|
||||||
.WhereIf(critrion.CriterionType == CriterionType.IVUS, t => t.ReadingCategory == ReadingCategory.Visit ? t.SourceSubjectVisit.NoneDicomStudyList.Where(t => t.Modality == "IVUS").SelectMany(t => t.ImageLabelNoneDicomFileList).Any() : true);
|
.WhereIf(critrion.CriterionType == CriterionType.IVUS, t => t.ReadingCategory == ReadingCategory.Visit ? t.SourceSubjectVisit.NoneDicomStudyList.Where(t => t.Modality == "IVUS").SelectMany(t => t.ImageLabelNoneDicomFileList).Any() : true);
|
||||||
|
|
||||||
var visitGroupQuery = visitQuery.GroupBy(x => new { x.SubjectId, x.Subject.Code, x.BlindSubjectCode });
|
var visitGroupQuery = visitQuery.GroupBy(x => new { x.SubjectId, x.Subject.Code, x.BlindSubjectCode });
|
||||||
|
|
@ -2293,12 +2293,12 @@ public class VisitTaskService(IRepository<VisitTask> _visitTaskRepository,
|
||||||
|
|
||||||
foreach (var item in readingTableAnswerRowInfoList)
|
foreach (var item in readingTableAnswerRowInfoList)
|
||||||
{
|
{
|
||||||
if (item.SplitRowId!=null&&lesionRelationship.ContainsKey(item.SplitRowId.Value))
|
if (item.SplitRowId != null && lesionRelationship.ContainsKey(item.SplitRowId.Value))
|
||||||
{
|
{
|
||||||
item.SplitRowId = lesionRelationship[item.SplitRowId.Value];
|
item.SplitRowId = lesionRelationship[item.SplitRowId.Value];
|
||||||
}
|
}
|
||||||
|
|
||||||
if (item.MergeRowId!=null&&lesionRelationship.ContainsKey(item.MergeRowId.Value))
|
if (item.MergeRowId != null && lesionRelationship.ContainsKey(item.MergeRowId.Value))
|
||||||
{
|
{
|
||||||
item.MergeRowId = lesionRelationship[item.MergeRowId.Value];
|
item.MergeRowId = lesionRelationship[item.MergeRowId.Value];
|
||||||
}
|
}
|
||||||
|
|
@ -2403,6 +2403,10 @@ public class VisitTaskService(IRepository<VisitTask> _visitTaskRepository,
|
||||||
//另一个阅片人的任务根据任务进度自动进入PM退回或PM申请重阅
|
//另一个阅片人的任务根据任务进度自动进入PM退回或PM申请重阅
|
||||||
filterExpression = filterExpression.And(t => t.VisitTaskNum >= task.VisitTaskNum);
|
filterExpression = filterExpression.And(t => t.VisitTaskNum >= task.VisitTaskNum);
|
||||||
|
|
||||||
|
//退回只影响有序的后续所有的,无序的当前访视
|
||||||
|
filterExpression = filterExpression.And(t => (t.TrialReadingCriterion.IsReadingTaskViewInOrder == ReadingOrder.InOrder) ||
|
||||||
|
(t.TrialReadingCriterion.IsReadingTaskViewInOrder != ReadingOrder.InOrder && t.SourceSubjectVisitId == task.SourceSubjectVisitId));
|
||||||
|
|
||||||
|
|
||||||
var influenceTaskList = await _visitTaskRepository.Where(filterExpression, true).ToListAsync();
|
var influenceTaskList = await _visitTaskRepository.Where(filterExpression, true).ToListAsync();
|
||||||
|
|
||||||
|
|
@ -2727,6 +2731,13 @@ public class VisitTaskService(IRepository<VisitTask> _visitTaskRepository,
|
||||||
//默认影响的都是该标准的任务
|
//默认影响的都是该标准的任务
|
||||||
filterExpression = filterExpression.And(t => t.TrialReadingCriterionId == filterObj.TrialReadingCriterionId);
|
filterExpression = filterExpression.And(t => t.TrialReadingCriterionId == filterObj.TrialReadingCriterionId);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//退回只影响有序的后续所有的,无序的当前访视
|
||||||
|
if (isReReading == false)
|
||||||
|
{
|
||||||
|
filterExpression = filterExpression.And(t => (t.TrialReadingCriterion.IsReadingTaskViewInOrder == ReadingOrder.InOrder) ||
|
||||||
|
(t.TrialReadingCriterion.IsReadingTaskViewInOrder != ReadingOrder.InOrder && t.SourceSubjectVisitId == filterObj.SourceSubjectVisitId));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -601,9 +601,11 @@ public class Tumor_CDISC_ExportService(IRepository<ReadingQuestionCriterionTrial
|
||||||
|
|
||||||
#region tu 表处理部分
|
#region tu 表处理部分
|
||||||
|
|
||||||
|
var tu = CreatNewTUExport(task, lesion, visitIndexNoDic, translateDataList, isEn_Us);
|
||||||
|
|
||||||
|
|
||||||
if (!tuList.Any(t => t.SubjectCode == task.SubjectCode && t.ARM_TumorNo == $"{task.ArmEnumStr}_{lesion.LessionCode}"))
|
if (!tuList.Any(t => t.SubjectCode == task.SubjectCode && t.ARM_TumorNo == $"{task.ArmEnumStr}_{lesion.LessionCode}"))
|
||||||
{
|
{
|
||||||
var tu = CreatNewTUExport(task, lesion, visitIndexNoDic, translateDataList, isEn_Us);
|
|
||||||
|
|
||||||
if (lesion.OrganInfoId.HasValue)
|
if (lesion.OrganInfoId.HasValue)
|
||||||
{
|
{
|
||||||
|
|
|
||||||
|
|
@ -92,6 +92,10 @@ namespace IRaCIS.Core.Application.Contracts
|
||||||
|
|
||||||
public class UnionDocumentWithConfirmInfoView : UnionDocumentView
|
public class UnionDocumentWithConfirmInfoView : UnionDocumentView
|
||||||
{
|
{
|
||||||
|
public DocUserSignType SysDocUserSignType { get; set; }
|
||||||
|
|
||||||
|
public bool IsConfirmIdentityUserInner { get; set; }
|
||||||
|
|
||||||
public Guid TrialId { get; set; }
|
public Guid TrialId { get; set; }
|
||||||
|
|
||||||
public bool IsNeedSendEmial { get; set; }
|
public bool IsNeedSendEmial { get; set; }
|
||||||
|
|
|
||||||
|
|
@ -19,6 +19,8 @@ namespace IRaCIS.Core.Application.Contracts
|
||||||
Task<IResponseOutput> UserConfirm(UserConfirmCommand userConfirmCommand);
|
Task<IResponseOutput> UserConfirm(UserConfirmCommand userConfirmCommand);
|
||||||
Task<List<TrialUserDto>> GetTrialUserSelect(Guid trialId);
|
Task<List<TrialUserDto>> GetTrialUserSelect(Guid trialId);
|
||||||
|
|
||||||
|
Task<IResponseOutput<PageOutput<UnionDocumentWithConfirmInfoView>>> GetSysDocumentConfirmList(SystemDocQuery inQuery);
|
||||||
|
|
||||||
|
|
||||||
//Task<PageOutput<DocumentUnionWithUserStatView>> GetTrialSystemDocumentList(DocumentTrialUnionQuery querySystemDocument);
|
//Task<PageOutput<DocumentUnionWithUserStatView>> GetTrialSystemDocumentList(DocumentTrialUnionQuery querySystemDocument);
|
||||||
//List<TrialUserUnionDocumentView> GetTrialUserDocumentList(Guid trialId);
|
//List<TrialUserUnionDocumentView> GetTrialUserDocumentList(Guid trialId);
|
||||||
|
|
|
||||||
|
|
@ -302,6 +302,7 @@ namespace IRaCIS.Core.Application.Services
|
||||||
{
|
{
|
||||||
AttachmentCount=sysDoc.SystemDocumentAttachmentList.Where(z=>!z.OffLine).Count(),
|
AttachmentCount=sysDoc.SystemDocumentAttachmentList.Where(z=>!z.OffLine).Count(),
|
||||||
IsSystemDoc = true,
|
IsSystemDoc = true,
|
||||||
|
IsPublish=sysDoc.IsPublish,
|
||||||
CurrentStaffTrainDays=sysDoc.CurrentStaffTrainDays,
|
CurrentStaffTrainDays=sysDoc.CurrentStaffTrainDays,
|
||||||
NewStaffTrainDays = sysDoc.NewStaffTrainDays,
|
NewStaffTrainDays = sysDoc.NewStaffTrainDays,
|
||||||
Id = sysDoc.Id,
|
Id = sysDoc.Id,
|
||||||
|
|
@ -327,6 +328,7 @@ namespace IRaCIS.Core.Application.Services
|
||||||
//UserTypeShortName = user.UserTypeRole.UserTypeShortName
|
//UserTypeShortName = user.UserTypeRole.UserTypeShortName
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
var list = await query
|
var list = await query
|
||||||
//过滤掉删除的,并且没有签名的
|
//过滤掉删除的,并且没有签名的
|
||||||
.Where(t => !(t.IsDeleted == true && t.ConfirmTime == null))
|
.Where(t => !(t.IsDeleted == true && t.ConfirmTime == null))
|
||||||
|
|
|
||||||
|
|
@ -952,10 +952,13 @@ namespace IRaCIS.Core.Application.Services
|
||||||
return ResponseOutput.Ok(new PageOutput<UnionDocumentWithConfirmInfoView>());
|
return ResponseOutput.Ok(new PageOutput<UnionDocumentWithConfirmInfoView>());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
var systemDocQuery =
|
var systemDocQuery =
|
||||||
from sysDoc in _systemDocumentRepository.AsQueryable(false)
|
from sysDoc in _systemDocumentRepository.Where(t => t.IsPublish)
|
||||||
.Where(t => inQuery.UserTypeId != null ? t.NeedConfirmedUserTypeList.Any(t => t.NeedConfirmUserTypeId == inQuery.UserTypeId) : true)
|
.Where(t => inQuery.UserTypeId != null ? t.NeedConfirmedUserTypeList.Any(t => t.NeedConfirmUserTypeId == inQuery.UserTypeId) : true)
|
||||||
from identityUser in _identityUserRepository.AsQueryable(false).Where(t => t.Status == UserStateEnum.Enable && t.UserRoleList.Where(t => t.IsUserRoleDisabled == false).Any(t => sysDoc.NeedConfirmedUserTypeList.AsQueryable().Any(c => c.NeedConfirmUserTypeId == t.UserTypeId)))
|
from identityUser in _identityUserRepository.AsQueryable(false)
|
||||||
|
|
||||||
|
.Where(t => t.Status == UserStateEnum.Enable && t.UserRoleList.Where(t => t.IsUserRoleDisabled == false).Any(t => sysDoc.NeedConfirmedUserTypeList.AsQueryable().Any(c => c.NeedConfirmUserTypeId == t.UserTypeId)))
|
||||||
.Where(t => inQuery.UserId != null ? t.Id == inQuery.UserId : true)
|
.Where(t => inQuery.UserId != null ? t.Id == inQuery.UserId : true)
|
||||||
.Where(t => inQuery.UserTypeId != null ? t.UserRoleList.Any(t => t.UserTypeId == inQuery.UserTypeId && t.IsUserRoleDisabled == false) : true)
|
.Where(t => inQuery.UserTypeId != null ? t.UserRoleList.Any(t => t.UserTypeId == inQuery.UserTypeId && t.IsUserRoleDisabled == false) : true)
|
||||||
.Where(t => isEA ? t.IsZhiZhun == true : true) //EA 只能查看内部人员文档
|
.Where(t => isEA ? t.IsZhiZhun == true : true) //EA 只能查看内部人员文档
|
||||||
|
|
@ -964,6 +967,9 @@ namespace IRaCIS.Core.Application.Services
|
||||||
select new UnionDocumentWithConfirmInfoView()
|
select new UnionDocumentWithConfirmInfoView()
|
||||||
{
|
{
|
||||||
IsSystemDoc = true,
|
IsSystemDoc = true,
|
||||||
|
SysDocUserSignType = sysDoc.DocUserSignType,
|
||||||
|
IsConfirmIdentityUserInner = identityUser.IsZhiZhun,
|
||||||
|
IsPublish=sysDoc.IsPublish,
|
||||||
Id = sysDoc.Id,
|
Id = sysDoc.Id,
|
||||||
CreateTime = sysDoc.CreateTime,
|
CreateTime = sysDoc.CreateTime,
|
||||||
IsDeleted = sysDoc.IsDeleted,
|
IsDeleted = sysDoc.IsDeleted,
|
||||||
|
|
@ -995,14 +1001,16 @@ namespace IRaCIS.Core.Application.Services
|
||||||
};
|
};
|
||||||
|
|
||||||
var unionQuery = systemDocQuery.IgnoreQueryFilters().Where(t => !(t.IsDeleted == true && t.ConfirmTime == null))
|
var unionQuery = systemDocQuery.IgnoreQueryFilters().Where(t => !(t.IsDeleted == true && t.ConfirmTime == null))
|
||||||
|
//外部人员 只签署 外部需要签署的
|
||||||
|
.Where(t => t.IsConfirmIdentityUserInner == false ? t.SysDocUserSignType == DocUserSignType.InnerAndOuter : true)
|
||||||
.WhereIf(!string.IsNullOrEmpty(inQuery.Name), t => t.Name.Contains(inQuery.Name))
|
.WhereIf(!string.IsNullOrEmpty(inQuery.Name), t => t.Name.Contains(inQuery.Name))
|
||||||
.WhereIf(inQuery.FileTypeId != null, t => t.FileTypeId == inQuery.FileTypeId)
|
.WhereIf(inQuery.FileTypeId != null, t => t.FileTypeId == inQuery.FileTypeId)
|
||||||
.WhereIf(inQuery.IsConfirmed == true, t => t.ConfirmTime != null)
|
.WhereIf(inQuery.IsConfirmed == true, t => t.ConfirmTime != null)
|
||||||
.WhereIf(inQuery.IsConfirmed == false, t => t.ConfirmTime == null)
|
.WhereIf(inQuery.IsConfirmed == false, t => t.ConfirmTime == null)
|
||||||
.WhereIf(inQuery.StartConfirmTime != null, t => t.ConfirmTime >= inQuery.StartConfirmTime.Value)
|
.WhereIf(inQuery.StartConfirmTime != null, t => t.ConfirmTime >= inQuery.StartConfirmTime.Value)
|
||||||
.WhereIf(inQuery.EndConfirmTime != null, t => t.ConfirmTime <= inQuery.EndConfirmTime.Value)
|
.WhereIf(inQuery.EndConfirmTime != null, t => t.ConfirmTime <= inQuery.EndConfirmTime.Value)
|
||||||
.WhereIf(inQuery.BeginCreateTime != null, t => t.CreateTime >= inQuery.BeginCreateTime)
|
.WhereIf(inQuery.BeginCreateTime != null, t => t.CreateTime >= inQuery.BeginCreateTime)
|
||||||
.WhereIf(inQuery.EndCreateTime != null, t => t.CreateTime <= inQuery.EndCreateTime)
|
.WhereIf(inQuery.EndCreateTime != null, t => t.CreateTime <= inQuery.EndCreateTime)
|
||||||
.WhereIf(!string.IsNullOrEmpty(inQuery.UserName), t => t.UserName.Contains(inQuery.UserName))
|
.WhereIf(!string.IsNullOrEmpty(inQuery.UserName), t => t.UserName.Contains(inQuery.UserName))
|
||||||
.WhereIf(inQuery.IsDeleted != null, t => t.IsDeleted == inQuery.IsDeleted)
|
.WhereIf(inQuery.IsDeleted != null, t => t.IsDeleted == inQuery.IsDeleted)
|
||||||
.WhereIf(isInternal == false, t => t.ConfirmTime != null); //不是内部的人,看有签名时间的
|
.WhereIf(isInternal == false, t => t.ConfirmTime != null); //不是内部的人,看有签名时间的
|
||||||
|
|
|
||||||
|
|
@ -1185,6 +1185,9 @@ namespace IRaCIS.Core.Application.Service.ImageAndDoc
|
||||||
|
|
||||||
foreach (var item in list.GroupBy(t => new { t.StudyInstanceUid, t.DicomStudyId }))
|
foreach (var item in list.GroupBy(t => new { t.StudyInstanceUid, t.DicomStudyId }))
|
||||||
{
|
{
|
||||||
|
|
||||||
|
var studyUid = item.Key.StudyInstanceUid;
|
||||||
|
|
||||||
var ossFolder = $"{pathInfo.TrialId}/Image/{pathInfo.SubjectId}/{pathInfo.VisitId}/{item.Key.StudyInstanceUid}";
|
var ossFolder = $"{pathInfo.TrialId}/Image/{pathInfo.SubjectId}/{pathInfo.VisitId}/{item.Key.StudyInstanceUid}";
|
||||||
|
|
||||||
var isSucess = await SafeBussinessHelper.RunAsync(async () => await DicomDIRHelper.GenerateStudyDIRAndUploadAsync(item.ToList(), dirDic, ossFolder, _oSSService));
|
var isSucess = await SafeBussinessHelper.RunAsync(async () => await DicomDIRHelper.GenerateStudyDIRAndUploadAsync(item.ToList(), dirDic, ossFolder, _oSSService));
|
||||||
|
|
@ -1192,7 +1195,7 @@ namespace IRaCIS.Core.Application.Service.ImageAndDoc
|
||||||
|
|
||||||
if (isSucess)
|
if (isSucess)
|
||||||
{
|
{
|
||||||
await _dicomStudyRepository.BatchUpdateNoTrackingAsync(t => t.Id == item.Key.DicomStudyId, u => new DicomStudy() { StudyDIRPath = $"/{ossFolder}/{dirDic["DICOMDIR"]}" });
|
await _dicomStudyRepository.BatchUpdateNoTrackingAsync(t => t.Id == item.Key.DicomStudyId, u => new DicomStudy() { StudyDIRPath = $"/{ossFolder}/{dirDic[$"{studyUid}_DICOMDIR"]}" });
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
@ -1625,6 +1628,8 @@ namespace IRaCIS.Core.Application.Service.ImageAndDoc
|
||||||
|
|
||||||
var ossFolder = $"{pathInfo.TrialId}/Image/{pathInfo.SubjectId}/{visitId}/{item.Key.StudyInstanceUid}";
|
var ossFolder = $"{pathInfo.TrialId}/Image/{pathInfo.SubjectId}/{visitId}/{item.Key.StudyInstanceUid}";
|
||||||
|
|
||||||
|
var studyUid = item.Key.StudyInstanceUid;
|
||||||
|
|
||||||
var isSucess = await SafeBussinessHelper.RunAsync(async () => await DicomDIRHelper.GenerateStudyDIRAndUploadAsync(item.ToList(), dirDic, ossFolder, _oSSService));
|
var isSucess = await SafeBussinessHelper.RunAsync(async () => await DicomDIRHelper.GenerateStudyDIRAndUploadAsync(item.ToList(), dirDic, ossFolder, _oSSService));
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -1632,11 +1637,11 @@ namespace IRaCIS.Core.Application.Service.ImageAndDoc
|
||||||
{
|
{
|
||||||
if (isTaskStudy)
|
if (isTaskStudy)
|
||||||
{
|
{
|
||||||
await _taskStudyRepository.BatchUpdateNoTrackingAsync(t => t.Id == item.Key.DicomStudyId, u => new TaskStudy() { StudyDIRPath = $"/{ossFolder}/{dirDic["DICOMDIR"]}" });
|
await _taskStudyRepository.BatchUpdateNoTrackingAsync(t => t.Id == item.Key.DicomStudyId, u => new TaskStudy() { StudyDIRPath = $"/{ossFolder}/{dirDic[$"{studyUid}_DICOMDIR"]}" });
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
await _dicomStudyRepository.BatchUpdateNoTrackingAsync(t => t.Id == item.Key.DicomStudyId, u => new DicomStudy() { StudyDIRPath = $"/{ossFolder}/{dirDic["DICOMDIR"]}" });
|
await _dicomStudyRepository.BatchUpdateNoTrackingAsync(t => t.Id == item.Key.DicomStudyId, u => new DicomStudy() { StudyDIRPath = $"/{ossFolder}/{dirDic[$"{studyUid}_DICOMDIR"]}" });
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
@ -2303,6 +2308,7 @@ namespace IRaCIS.Core.Application.Service.ImageAndDoc
|
||||||
|
|
||||||
var subjectId = item.First().SubjectId;
|
var subjectId = item.First().SubjectId;
|
||||||
|
|
||||||
|
var studyUid = item.Key.StudyInstanceUid;
|
||||||
|
|
||||||
var ossFolder = $"{inCommand.TrialId}/Image/{subjectId}/{visitId}/{item.Key.StudyInstanceUid}";
|
var ossFolder = $"{inCommand.TrialId}/Image/{subjectId}/{visitId}/{item.Key.StudyInstanceUid}";
|
||||||
|
|
||||||
|
|
@ -2310,7 +2316,7 @@ namespace IRaCIS.Core.Application.Service.ImageAndDoc
|
||||||
|
|
||||||
if (isSucess)
|
if (isSucess)
|
||||||
{
|
{
|
||||||
await _dicomStudyRepository.BatchUpdateNoTrackingAsync(t => t.Id == item.Key.DicomStudyId, u => new DicomStudy() { StudyDIRPath = $"/{ossFolder}/{dirDic["DICOMDIR"]}" });
|
await _dicomStudyRepository.BatchUpdateNoTrackingAsync(t => t.Id == item.Key.DicomStudyId, u => new DicomStudy() { StudyDIRPath = $"/{ossFolder}/{dirDic[$"{studyUid}_DICOMDIR"]}" });
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -39,6 +39,7 @@ using SixLabors.ImageSharp;
|
||||||
using SixLabors.ImageSharp.Formats.Jpeg;
|
using SixLabors.ImageSharp.Formats.Jpeg;
|
||||||
using SixLabors.ImageSharp.Processing;
|
using SixLabors.ImageSharp.Processing;
|
||||||
using System.Collections.Concurrent;
|
using System.Collections.Concurrent;
|
||||||
|
using System.ComponentModel.DataAnnotations;
|
||||||
using System.Diagnostics;
|
using System.Diagnostics;
|
||||||
using System.Globalization;
|
using System.Globalization;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
|
|
@ -77,6 +78,46 @@ namespace IRaCIS.Core.Application.Service
|
||||||
public static int IntValue = 100;
|
public static int IntValue = 100;
|
||||||
|
|
||||||
|
|
||||||
|
public class ModelVerifyCommand
|
||||||
|
{
|
||||||
|
public int? IntNUllValue { get; set; }
|
||||||
|
public int IntValue { get; set; }
|
||||||
|
|
||||||
|
public string StringValue { get; set; }
|
||||||
|
|
||||||
|
public string? StringNUllValue { get; set; }
|
||||||
|
|
||||||
|
public string StringBackDefaultValue { get; set; } = string.Empty;
|
||||||
|
|
||||||
|
public Guid GuidValue { get; set; } = NewId.NextSequentialGuid();
|
||||||
|
|
||||||
|
public Guid? GuidNUllValue { get; set; }
|
||||||
|
|
||||||
|
[NotDefault]
|
||||||
|
public Guid GuidValueNotDefault { get; set; }
|
||||||
|
|
||||||
|
|
||||||
|
public bool BoolValue { get; set; }
|
||||||
|
|
||||||
|
public bool? BoolNUllValue { get; set; }
|
||||||
|
|
||||||
|
public DateTime DateTimeValue { get; set; }
|
||||||
|
|
||||||
|
public DateTime? DateTimeNUllValue { get; set; }
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//创建一个模型验证的方法
|
||||||
|
[AllowAnonymous]
|
||||||
|
[HttpPost]
|
||||||
|
public async Task<IResponseOutput> PostModelVerify(ModelVerifyCommand modelVerify)
|
||||||
|
{
|
||||||
|
|
||||||
|
return ResponseOutput.Ok(modelVerify);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
[AllowAnonymous]
|
[AllowAnonymous]
|
||||||
|
|
||||||
public async Task<IResponseOutput> CreatNewDBStruct()
|
public async Task<IResponseOutput> CreatNewDBStruct()
|
||||||
|
|
@ -99,10 +140,10 @@ namespace IRaCIS.Core.Application.Service
|
||||||
|
|
||||||
public async Task<IResponseOutput> DeleteCacheDIR()
|
public async Task<IResponseOutput> DeleteCacheDIR()
|
||||||
{
|
{
|
||||||
var list= _dicomStudyRepository.Where(t => t.StudyDIRPath!="").Select(t => t.StudyDIRPath).ToList();
|
var list = _dicomStudyRepository.Where(t => t.StudyDIRPath != "").Select(t => t.StudyDIRPath).ToList();
|
||||||
|
|
||||||
|
|
||||||
await _IOSSService.DeleteObjects(list.Select(t => t.TrimStart('/')).ToList(),true);
|
await _IOSSService.DeleteObjects(list.Select(t => t.TrimStart('/')).ToList(), true);
|
||||||
|
|
||||||
return ResponseOutput.Ok();
|
return ResponseOutput.Ok();
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -119,7 +119,10 @@ namespace IRaCIS.Core.Infra.EFCore
|
||||||
/// <summary>EntityState.Detached的实体 修改 部分字段</summary>
|
/// <summary>EntityState.Detached的实体 修改 部分字段</summary>
|
||||||
public static void EntityModifyPartialFiled<T>(this IRaCISDBContext _dbContext, T waitModifyEntity, Expression<Func<T, T>> updateFactory) where T : Entity
|
public static void EntityModifyPartialFiled<T>(this IRaCISDBContext _dbContext, T waitModifyEntity, Expression<Func<T, T>> updateFactory) where T : Entity
|
||||||
{
|
{
|
||||||
var entityEntry = _dbContext.Entry(waitModifyEntity);
|
//解决重复跟踪问题
|
||||||
|
var tracked = _dbContext.ChangeTracker.Entries<T>().FirstOrDefault(e => e.Entity.Id.Equals(waitModifyEntity.Id));
|
||||||
|
var entityEntry = tracked?? _dbContext.Entry(waitModifyEntity);
|
||||||
|
|
||||||
//entityEntry.State = EntityState.Detached;
|
//entityEntry.State = EntityState.Detached;
|
||||||
|
|
||||||
var list = ((MemberInitExpression)updateFactory.Body).Bindings.Select(mb => mb.Member.Name)
|
var list = ((MemberInitExpression)updateFactory.Body).Bindings.Select(mb => mb.Member.Name)
|
||||||
|
|
@ -134,7 +137,7 @@ namespace IRaCIS.Core.Infra.EFCore
|
||||||
|
|
||||||
foreach (PropertyInfo prop in list)
|
foreach (PropertyInfo prop in list)
|
||||||
{
|
{
|
||||||
_dbContext.Entry(waitModifyEntity).Property(prop.Name).IsModified = true;
|
entityEntry.Property(prop.Name).IsModified = true;
|
||||||
|
|
||||||
object value = prop.GetValue(applyObj);
|
object value = prop.GetValue(applyObj);
|
||||||
prop.SetValue(waitModifyEntity, value);
|
prop.SetValue(waitModifyEntity, value);
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue