Merge branch 'Test.Study' of http://192.168.3.69:2000/XCKJ/irc-netcore-api into Test.Study
commit
4b65f1e922
|
@ -25,6 +25,7 @@ using Aliyun.Acs.Core;
|
|||
using Aliyun.Acs.Core.Profile;
|
||||
using Aliyun.Acs.Sts.Model.V20150401;
|
||||
using Microsoft.AspNetCore.Hosting;
|
||||
using MassTransit;
|
||||
|
||||
namespace IRaCIS.Api.Controllers
|
||||
{
|
||||
|
@ -144,16 +145,16 @@ namespace IRaCIS.Api.Controllers
|
|||
.Build();
|
||||
|
||||
|
||||
|
||||
IClientProfile profile = DefaultProfile.GetProfile("cn-shanghai", configuration["AliyunOSS:accessKeyId"], configuration["AliyunOSS:accessKeySecret"]);
|
||||
DefaultAcsClient client = new DefaultAcsClient(profile);
|
||||
|
||||
|
||||
// 创建一个STS请求
|
||||
AssumeRoleRequest request = new AssumeRoleRequest
|
||||
{
|
||||
RoleArn = "acs:ram::1899121822495495:role/oss-upload", // 角色ARN,需要替换为你的角色ARN
|
||||
RoleSessionName = "session-name", // 角色会话名称,可自定义
|
||||
DurationSeconds = 3600, // 令牌有效期(单位:秒),这里设置为1小时
|
||||
RoleSessionName = $"session-name-{NewId.NextGuid()}", // 角色会话名称,可自定义
|
||||
DurationSeconds = 900, // 令牌有效期(单位:秒),这里设置为1小时
|
||||
};
|
||||
|
||||
|
||||
|
|
|
@ -66,28 +66,27 @@
|
|||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="aliyun-net-sdk-sts" Version="3.1.1" />
|
||||
<PackageReference Include="AspNetCoreRateLimit" Version="4.0.2" />
|
||||
<PackageReference Include="aliyun-net-sdk-sts" Version="3.1.2" />
|
||||
<PackageReference Include="AspNetCoreRateLimit" Version="5.0.0" />
|
||||
<PackageReference Include="Autofac.Extensions.DependencyInjection" Version="8.0.0" />
|
||||
<PackageReference Include="AutoMapper.Extensions.Microsoft.DependencyInjection" Version="12.0.0" />
|
||||
<PackageReference Include="EasyCaching.InMemory" Version="1.7.0" />
|
||||
<PackageReference Include="EasyCaching.Interceptor.Castle" Version="1.7.0" />
|
||||
<PackageReference Include="EntityFrameworkCore.Triggered.Extensions" Version="3.2.1" />
|
||||
<PackageReference Include="EasyCaching.Interceptor.Castle" Version="1.9.1" />
|
||||
<PackageReference Include="EasyCaching.Serialization.MessagePack" Version="1.9.1" />
|
||||
<PackageReference Include="AutoMapper.Extensions.Microsoft.DependencyInjection" Version="12.0.1" />
|
||||
<PackageReference Include="EasyCaching.InMemory" Version="1.9.1" />
|
||||
<PackageReference Include="Hangfire.AspNetCore" Version="1.8.5" />
|
||||
<PackageReference Include="Hangfire.Dashboard.BasicAuthorization" Version="1.0.2" />
|
||||
<PackageReference Include="Hangfire.SqlServer" Version="1.8.5" />
|
||||
<PackageReference Include="Invio.Extensions.Authentication.JwtBearer" Version="2.0.1" />
|
||||
<PackageReference Include="LogDashboard" Version="1.4.8" />
|
||||
<PackageReference Include="MediatR.Extensions.Microsoft.DependencyInjection" Version="11.0.0" />
|
||||
<PackageReference Include="Microsoft.AspNetCore.Mvc.NewtonsoftJson" Version="6.0.10" />
|
||||
<PackageReference Include="Microsoft.Extensions.Hosting.WindowsServices" Version="6.0.1" />
|
||||
<PackageReference Include="Quartz.Extensions.DependencyInjection" Version="3.6.2" />
|
||||
<PackageReference Include="Quartz.Extensions.Hosting" Version="3.6.2" />
|
||||
<PackageReference Include="Serilog.AspNetCore" Version="6.0.1" />
|
||||
<PackageReference Include="Serilog.Enrichers.ClientInfo" Version="1.2.0" />
|
||||
<PackageReference Include="Microsoft.AspNetCore.Mvc.NewtonsoftJson" Version="6.0.23" />
|
||||
<PackageReference Include="Microsoft.Extensions.Hosting.WindowsServices" Version="7.0.1" />
|
||||
<PackageReference Include="Quartz.Extensions.DependencyInjection" Version="3.7.0" />
|
||||
<PackageReference Include="Quartz.Extensions.Hosting" Version="3.7.0" />
|
||||
<PackageReference Include="Serilog.AspNetCore" Version="7.0.0" />
|
||||
<PackageReference Include="Serilog.Enrichers.ClientInfo" Version="2.0.1" />
|
||||
<PackageReference Include="Serilog.Sinks.Email" Version="2.4.0" />
|
||||
<PackageReference Include="Serilog.Sinks.File" Version="5.0.0" />
|
||||
<PackageReference Include="Swashbuckle.AspNetCore.SwaggerUI" Version="6.4.0" />
|
||||
<PackageReference Include="Swashbuckle.AspNetCore.SwaggerUI" Version="6.5.0" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
|
|
|
@ -29,6 +29,7 @@ using IRaCIS.Core.Application.Helper;
|
|||
using Microsoft.AspNetCore.Http;
|
||||
using Autofac.Core;
|
||||
using DocumentFormat.OpenXml.InkML;
|
||||
using EasyCaching.Core;
|
||||
|
||||
namespace IRaCIS.Core.API
|
||||
{
|
||||
|
@ -112,9 +113,9 @@ namespace IRaCIS.Core.API
|
|||
//JWT Token 验证
|
||||
services.AddJWTAuthSetup(_configuration);
|
||||
// MediatR 进程内消息 事件解耦 从程序集中 注册命令和handler对应关系
|
||||
services.AddMediatR(typeof(ConsistencyVerificationHandler).Assembly);
|
||||
services.AddMediatR(cfg => cfg.RegisterServicesFromAssemblyContaining<ConsistencyVerificationHandler>());
|
||||
// EasyCaching 缓存
|
||||
services.AddEasyCachingSetup();
|
||||
services.AddEasyCachingSetup(_configuration);
|
||||
|
||||
//services.AddDistributedMemoryCache();
|
||||
|
||||
|
|
|
@ -1,8 +1,12 @@
|
|||
using IRaCIS.Core.Application.Triggers;
|
||||
using Hangfire.SqlServer;
|
||||
using IRaCIS.Core.Application.Triggers;
|
||||
using IRaCIS.Core.Infra.EFCore;
|
||||
using Medallion.Threading;
|
||||
using Medallion.Threading.SqlServer;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
using Microsoft.Extensions.Configuration;
|
||||
using Microsoft.Extensions.DependencyInjection;
|
||||
using StackExchange.Redis;
|
||||
|
||||
namespace IRaCIS.Core.API
|
||||
{
|
||||
|
@ -52,6 +56,13 @@ namespace IRaCIS.Core.API
|
|||
|
||||
});
|
||||
|
||||
//注意区分 easy caching 也有 IDistributedLockProvider
|
||||
services.AddSingleton<IDistributedLockProvider>(sp =>
|
||||
{
|
||||
//var connection = ConnectionMultiplexer.Connect(configuration["Redis:Configuration"]!);
|
||||
|
||||
return new SqlDistributedSynchronizationProvider(configuration.GetSection("ConnectionStrings:RemoteNew").Value);
|
||||
});
|
||||
|
||||
//services.AddAssemblyTriggers(typeof(SubjectVisitImageDateTrigger).Assembly);
|
||||
}
|
||||
|
|
|
@ -1,17 +1,26 @@
|
|||
using EasyCaching.Core;
|
||||
using EasyCaching.Core.Configurations;
|
||||
using EasyCaching.Interceptor.Castle;
|
||||
using Microsoft.Extensions.Configuration;
|
||||
using Microsoft.Extensions.DependencyInjection;
|
||||
|
||||
namespace IRaCIS.Core.API
|
||||
{
|
||||
public static class EasyCachingSetup
|
||||
{
|
||||
public static void AddEasyCachingSetup(this IServiceCollection services)
|
||||
public static void AddEasyCachingSetup(this IServiceCollection services, IConfiguration configuration)
|
||||
{
|
||||
services.AddEasyCaching(options =>
|
||||
{
|
||||
options.UseInMemory();
|
||||
|
||||
//options.UseRedis(configuration, EasyCachingConstValue.DefaultRedisName).WithMessagePack(EasyCachingConstValue.DefaultRedisName);
|
||||
|
||||
|
||||
});
|
||||
|
||||
//services.ConfigureCastleInterceptor(options => options.CacheProviderName = EasyCachingConstValue.DefaultRedisName);
|
||||
|
||||
services.ConfigureCastleInterceptor(options => options.CacheProviderName = EasyCachingConstValue.DefaultInMemoryName);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -21,7 +21,7 @@ namespace IRaCIS.Core.API
|
|||
.MinimumLevel.Override("Hangfire", LogEventLevel.Warning)
|
||||
.MinimumLevel.Override("System.Net.Http.HttpClient.HttpReports", LogEventLevel.Warning)
|
||||
.Enrich.WithClientIp()
|
||||
.Enrich.WithClientAgent()
|
||||
|
||||
.Enrich.FromLogContext()
|
||||
|
||||
//控制台 方便调试 问题 我们显示记录日志 时 获取上下文的ip 和用户名 用户类型
|
||||
|
|
|
@ -1,55 +0,0 @@
|
|||
using Microsoft.OpenApi.Models;
|
||||
using Swashbuckle.AspNetCore.SwaggerGen;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
|
||||
namespace IRaCIS.Core.API
|
||||
{
|
||||
public class JsonPatchDocumentFilter : IDocumentFilter
|
||||
{
|
||||
public void Apply(OpenApiDocument swaggerDoc, DocumentFilterContext context)
|
||||
{
|
||||
var schemas = swaggerDoc.Components.Schemas.ToList();
|
||||
foreach (var item in schemas)
|
||||
{
|
||||
if (item.Key.StartsWith("Operation") || item.Key.StartsWith("JsonPatchDocument"))
|
||||
swaggerDoc.Components.Schemas.Remove(item.Key);
|
||||
}
|
||||
|
||||
swaggerDoc.Components.Schemas.Add("Operation", new OpenApiSchema
|
||||
{
|
||||
Type = "object",
|
||||
Properties = new Dictionary<string, OpenApiSchema>
|
||||
{
|
||||
{ "op", new OpenApiSchema { Type = "string" } },
|
||||
{"value", new OpenApiSchema{ Type = "object", Nullable = true } },
|
||||
{ "path", new OpenApiSchema { Type = "string" } }
|
||||
}
|
||||
});
|
||||
|
||||
swaggerDoc.Components.Schemas.Add("JsonPatchDocument", new OpenApiSchema
|
||||
{
|
||||
Type = "array",
|
||||
Items = new OpenApiSchema
|
||||
{
|
||||
Reference = new OpenApiReference { Type = ReferenceType.Schema, Id = "Operation" }
|
||||
},
|
||||
Description = "Array of operations to perform"
|
||||
});
|
||||
|
||||
foreach (var path in swaggerDoc.Paths.SelectMany(p => p.Value.Operations)
|
||||
.Where(p => p.Key == Microsoft.OpenApi.Models.OperationType.Patch))
|
||||
{
|
||||
foreach (var item in path.Value.RequestBody.Content.Where(c => c.Key != "application/json-patch+json"))
|
||||
path.Value.RequestBody.Content.Remove(item.Key);
|
||||
|
||||
var response = path.Value.RequestBody.Content.SingleOrDefault(c => c.Key == "application/json-patch+json");
|
||||
|
||||
response.Value.Schema = new OpenApiSchema
|
||||
{
|
||||
Reference = new OpenApiReference { Type = ReferenceType.Schema, Id = "JsonPatchDocument" }
|
||||
};
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -18,7 +18,6 @@ namespace IRaCIS.Core.API
|
|||
{
|
||||
public static void AddSwaggerSetup(this IServiceCollection services)
|
||||
{
|
||||
services.AddSwaggerExamplesFromAssemblyOf<JsonPatchUserRequestExample>();
|
||||
|
||||
services.AddSwaggerGen(options =>
|
||||
{
|
||||
|
@ -63,7 +62,6 @@ namespace IRaCIS.Core.API
|
|||
// 在header中添加token,传递到后台
|
||||
options.OperationFilter<SecurityRequirementsOperationFilter>();
|
||||
|
||||
options.DocumentFilter<JsonPatchDocumentFilter>();
|
||||
|
||||
// 添加登录按钮
|
||||
options.AddSecurityDefinition("bearerAuth", new OpenApiSecurityScheme()
|
||||
|
|
|
@ -0,0 +1,48 @@
|
|||
{
|
||||
"Logging": {
|
||||
"LogLevel": {
|
||||
"Default": "Information",
|
||||
"Microsoft": "Warning",
|
||||
"Microsoft.Hosting.Lifetime": "Information"
|
||||
}
|
||||
},
|
||||
"AliyunOSS": {
|
||||
"regionId": "cn-shanghai",
|
||||
"region": "oss-cn-shanghai",
|
||||
"endpoint": "https://oss-cn-shanghai.aliyuncs.com",
|
||||
"accessKeyId": "LTAI5tKvzs7ed3UfSpNk3xwQ",
|
||||
"accessKeySecret": "zTIceGEShlZDGnLrCFfIGFE7TXVRio",
|
||||
"bucketName": "zy-sir-store",
|
||||
"viewEndpoint": "https://zy-sir-cache.oss-cn-shanghai.aliyuncs.com"
|
||||
},
|
||||
|
||||
"ConnectionStrings": {
|
||||
"RemoteNew": "Server=47.117.165.18,1434;Database=Prod_Study;User ID=sa;Password=WHxckj@2019;TrustServerCertificate=true",
|
||||
"Hangfire": "Server=47.117.165.18,1434;Database=Prod_Study.hangfire;User ID=sa;Password=WHxckj@2019;TrustServerCertificate=true"
|
||||
},
|
||||
|
||||
"BasicSystemConfig": {
|
||||
|
||||
"OpenUserComplexPassword": false,
|
||||
|
||||
"OpenSignDocumentBeforeWork": false,
|
||||
|
||||
"OpenTrialRelationDelete": true,
|
||||
|
||||
"OpenLoginLimit": false,
|
||||
"LoginMaxFailCount": 5,
|
||||
|
||||
"LoginFailLockMinutes": 30
|
||||
|
||||
},
|
||||
|
||||
"SystemEmailSendConfig": {
|
||||
"Port": 465,
|
||||
"Host": "smtp.qiye.aliyun.com",
|
||||
"FromEmail": "study@extimaging.com",
|
||||
"FromName": "研究单位阅片系统",
|
||||
"AuthorizationCode": "zhanying123",
|
||||
"SiteUrl": "https://study.extimaging.com/login"
|
||||
}
|
||||
|
||||
}
|
|
@ -5,6 +5,7 @@
|
|||
"Audience": "ZhiZhun",
|
||||
"TokenExpireDays": "7"
|
||||
},
|
||||
//ip
|
||||
"IpRateLimiting": {
|
||||
"EnableEndpointRateLimiting": true,
|
||||
"StackBlockedRequests": false,
|
||||
|
@ -56,6 +57,26 @@
|
|||
"EnableReadDeepClone": true,
|
||||
"EnableWriteDeepClone": false
|
||||
}
|
||||
},
|
||||
"redis": {
|
||||
"MaxRdSecond": 120,
|
||||
"EnableLogging": false,
|
||||
"LockMs": 5000,
|
||||
"SleepMs": 300,
|
||||
"dbconfig": {
|
||||
"Password": "xc@123456",
|
||||
"IsSsl": false,
|
||||
"SslHost": null,
|
||||
"ConnectionTimeout": 5000,
|
||||
"AllowAdmin": true,
|
||||
"Endpoints": [
|
||||
{
|
||||
"Host": "47.117.164.182",
|
||||
"Port": 6379
|
||||
}
|
||||
],
|
||||
"Database": 0
|
||||
}
|
||||
}
|
||||
},
|
||||
"IRaCISImageStore": {
|
||||
|
|
|
@ -58,10 +58,14 @@ namespace IRaCIS.Core.Application.Filter
|
|||
// 后期列举出具体的类型,其他任何用户类型,都不允许操作
|
||||
if (_userInfo.UserTypeEnumInt == (int)UserTypeEnum.CRA)
|
||||
{
|
||||
//---对不起,您的账户没有操作权限。
|
||||
context.Result = new JsonResult(ResponseOutput.NotOk(_localizer["TrialResource_NoAccessPermission"]));
|
||||
if (!_userInfo.RequestUrl.Contains("TrialDocument/userConfirm"))
|
||||
{
|
||||
//---对不起,您的账户没有操作权限。
|
||||
context.Result = new JsonResult(ResponseOutput.NotOk(_localizer["TrialResource_NoAccessPermission"]));
|
||||
|
||||
return;
|
||||
return;
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
|
|
@ -15,14 +15,14 @@
|
|||
</PropertyGroup>
|
||||
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|AnyCPU'">
|
||||
<NoWarn>1701;1702;1591;1587</NoWarn>
|
||||
<NoWarn>1701;1702;1591;1587</NoWarn>
|
||||
</PropertyGroup>
|
||||
|
||||
|
||||
|
||||
<ItemGroup>
|
||||
|
||||
<Using Include="IRaCIS.Core.Application;" />
|
||||
<Using Include="IRaCIS.Core.Application;" />
|
||||
<Using Include="AutoMapper.QueryableExtensions;" />
|
||||
<Using Include="Microsoft.EntityFrameworkCore;" />
|
||||
<Using Include="IRaCIS.Core.Domain.Models;" />
|
||||
|
@ -50,60 +50,56 @@
|
|||
|
||||
|
||||
<ItemGroup>
|
||||
<Content Include="Resources\zh-CN.json">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
<ExcludeFromSingleFile>true</ExcludeFromSingleFile>
|
||||
<CopyToPublishDirectory>PreserveNewest</CopyToPublishDirectory>
|
||||
</Content>
|
||||
<Content Include="Resources\en-US.json">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
<ExcludeFromSingleFile>true</ExcludeFromSingleFile>
|
||||
<CopyToPublishDirectory>PreserveNewest</CopyToPublishDirectory>
|
||||
</Content>
|
||||
<Content Include="Resources\zh-CN.json">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
<ExcludeFromSingleFile>true</ExcludeFromSingleFile>
|
||||
<CopyToPublishDirectory>PreserveNewest</CopyToPublishDirectory>
|
||||
</Content>
|
||||
<Content Include="Resources\en-US.json">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
<ExcludeFromSingleFile>true</ExcludeFromSingleFile>
|
||||
<CopyToPublishDirectory>PreserveNewest</CopyToPublishDirectory>
|
||||
</Content>
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Aliyun.OSS.SDK.NetCore" Version="2.13.0" />
|
||||
<PackageReference Include="AutoMapper.Collection.EntityFrameworkCore" Version="9.0.0" />
|
||||
<PackageReference Include="EntityFrameworkCore.Triggered" Version="3.2.1" />
|
||||
<PackageReference Include="DistributedLock.Redis" Version="1.0.2" />
|
||||
<PackageReference Include="DistributedLock.SqlServer" Version="1.0.3" />
|
||||
<PackageReference Include="EasyCaching.InMemory" Version="1.9.1" />
|
||||
<PackageReference Include="EasyCaching.Redis" Version="1.9.1" />
|
||||
<PackageReference Include="Castle.Core.AsyncInterceptor" Version="2.1.0" />
|
||||
<PackageReference Include="EasyCaching.Interceptor.AspectCore" Version="1.7.0" />
|
||||
<PackageReference Include="EasyCaching.Interceptor.AspectCore" Version="1.9.1" />
|
||||
<PackageReference Include="ExcelDataReader" Version="3.6.0" />
|
||||
<PackageReference Include="ExcelDataReader.DataSet" Version="3.6.0" />
|
||||
<PackageReference Include="fo-dicom.Codecs" Version="5.1.0">
|
||||
<TreatAsUsed>true</TreatAsUsed>
|
||||
</PackageReference>
|
||||
<PackageReference Include="fo-dicom.Drawing" Version="4.0.8" />
|
||||
<PackageReference Include="fo-dicom.Imaging.ImageSharp" Version="5.0.3" />
|
||||
<PackageReference Include="FreeSpire.Doc" Version="10.8.0" />
|
||||
<PackageReference Include="fo-dicom" Version="5.1.1" />
|
||||
<PackageReference Include="fo-dicom.Imaging.ImageSharp" Version="5.1.0" />
|
||||
<PackageReference Include="fo-dicom.Codecs" Version="5.10.8" />
|
||||
<PackageReference Include="FreeSpire.Doc" Version="11.6.0" />
|
||||
<PackageReference Include="Hangfire.Core" Version="1.8.5" />
|
||||
<PackageReference Include="Magicodes.IE.Core" Version="2.7.4.2" />
|
||||
<PackageReference Include="Magicodes.IE.Csv" Version="2.7.4.2">
|
||||
<TreatAsUsed>true</TreatAsUsed>
|
||||
<PackageReference Include="Magicodes.IE.Core" Version="2.7.4.5" />
|
||||
<PackageReference Include="Magicodes.IE.Csv" Version="2.7.4.5">
|
||||
<TreatAsUsed>true</TreatAsUsed>
|
||||
</PackageReference>
|
||||
<PackageReference Include="Magicodes.IE.Excel" Version="2.7.4.2">
|
||||
<TreatAsUsed>true</TreatAsUsed>
|
||||
<PackageReference Include="Magicodes.IE.Excel" Version="2.7.4.5">
|
||||
<TreatAsUsed>true</TreatAsUsed>
|
||||
</PackageReference>
|
||||
<PackageReference Include="Magicodes.IE.Excel.AspNetCore" Version="2.7.4.2" />
|
||||
<PackageReference Include="MailKit" Version="3.4.2" />
|
||||
<PackageReference Include="MediatR" Version="11.0.0" />
|
||||
<PackageReference Include="Microsoft.AspNetCore.JsonPatch" Version="6.0.10" />
|
||||
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="6.0.10">
|
||||
<TreatAsUsed>true</TreatAsUsed>
|
||||
</PackageReference>
|
||||
<PackageReference Include="MimeKit" Version="3.4.2" />
|
||||
<PackageReference Include="MiniExcel" Version="1.30.1" />
|
||||
<PackageReference Include="MiniWord" Version="0.6.1" />
|
||||
<PackageReference Include="Magicodes.IE.Excel.AspNetCore" Version="2.7.4.5" />
|
||||
<PackageReference Include="MailKit" Version="4.2.0" />
|
||||
<PackageReference Include="MediatR" Version="12.1.1" />
|
||||
<PackageReference Include="MimeKit" Version="4.2.0" />
|
||||
<PackageReference Include="MiniExcel" Version="1.31.2" />
|
||||
<PackageReference Include="MiniWord" Version="0.7.0" />
|
||||
<PackageReference Include="My.Extensions.Localization.Json" Version="3.0.0">
|
||||
<TreatAsUsed>true</TreatAsUsed>
|
||||
<TreatAsUsed>true</TreatAsUsed>
|
||||
</PackageReference>
|
||||
<PackageReference Include="Nito.AsyncEx" Version="5.1.2" />
|
||||
<PackageReference Include="NPOI" Version="2.6.0" />
|
||||
<PackageReference Include="Panda.DynamicWebApi" Version="1.2.0" />
|
||||
<PackageReference Include="Quartz" Version="3.5.0" />
|
||||
<PackageReference Include="SixLabors.ImageSharp" Version="2.1.3" />
|
||||
<PackageReference Include="Swashbuckle.AspNetCore.Filters" Version="7.0.5" />
|
||||
<PackageReference Include="WinSCP" Version="5.21.5" />
|
||||
<PackageReference Include="NPOI" Version="2.6.2" />
|
||||
<PackageReference Include="Panda.DynamicWebApi" Version="1.2.1" />
|
||||
<PackageReference Include="Quartz" Version="3.7.0" />
|
||||
<PackageReference Include="SixLabors.ImageSharp" Version="3.0.2" />
|
||||
<PackageReference Include="Swashbuckle.AspNetCore.Filters" Version="7.0.11" />
|
||||
<PackageReference Include="WinSCP" Version="6.1.2" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
|
|
|
@ -9509,11 +9509,6 @@
|
|||
<member name="T:IRaCIS.Core.Application.Contracts.TrialSiteUserSurveyAddOrEdit">
|
||||
<summary> TrialSiteUserSurveyAddOrEdit 列表查询参数模型</summary>
|
||||
</member>
|
||||
<member name="T:IRaCIS.Core.Application.Contracts.JsonPatchUserRequestExample">
|
||||
<summary>
|
||||
实测 标注在服务方法上 没用
|
||||
</summary>
|
||||
</member>
|
||||
<member name="T:IRaCIS.Core.Application.Contracts.TrialSiteEquipmentSurveyService">
|
||||
<summary>
|
||||
TrialSiteEquipmentSurveyService
|
||||
|
@ -10884,20 +10879,6 @@
|
|||
<param name="inDto"></param>
|
||||
<returns></returns>
|
||||
</member>
|
||||
<member name="M:IRaCIS.Core.Application.TrialConfigService.GetTrialCriterionAdditionalAssessmentOptionList(System.Guid)">
|
||||
<summary>
|
||||
获取附加评估选项列表
|
||||
</summary>
|
||||
<param name="trialReadingCriterionId"></param>
|
||||
<returns></returns>
|
||||
</member>
|
||||
<member name="M:IRaCIS.Core.Application.TrialConfigService.SetTrialCriterionAdditionalAssessment(System.Collections.Generic.List{IRaCIS.Core.Application.Contracts.AddOrUpdateTrialCriterionAdditional})">
|
||||
<summary>
|
||||
保存附加评估设置 (自动添加 或者删除附加评估问题)
|
||||
</summary>
|
||||
<param name="updateList"></param>
|
||||
<returns></returns>
|
||||
</member>
|
||||
<member name="M:IRaCIS.Core.Application.TrialConfigService.GetSignText(System.String)">
|
||||
<summary>
|
||||
获取签名文本
|
||||
|
|
|
@ -479,9 +479,17 @@ namespace IRaCIS.Core.Application.ViewModel
|
|||
}
|
||||
|
||||
|
||||
public class PIAuditDialogListView : PIAuditTaskCommand
|
||||
public class PIAuditDialogListView
|
||||
{
|
||||
|
||||
public Guid VisitTaskId { get; set; }
|
||||
public string NotAgreeReason { get; set; }
|
||||
public string PIAuditNote { get; set; } = string.Empty;
|
||||
|
||||
public List<string> PIAuditImagePathList { get; set; }
|
||||
|
||||
public PIAuditState? PIAuditState { get; set; }
|
||||
|
||||
public string ReplyContent { get; set; } = string.Empty;
|
||||
|
||||
public bool? IsEnrollment { get; set; }
|
||||
|
|
|
@ -25,6 +25,7 @@ using Quartz;
|
|||
using IRaCIS.Application.Services.BackGroundJob;
|
||||
using Magicodes.ExporterAndImporter.Core.Extension;
|
||||
using Hangfire;
|
||||
using MassTransit;
|
||||
|
||||
namespace IRaCIS.Core.Application.Service.Allocation
|
||||
{
|
||||
|
@ -275,6 +276,8 @@ namespace IRaCIS.Core.Application.Service.Allocation
|
|||
//发送对话
|
||||
var addDialig = _mapper.Map<PIAudit>(incommand);
|
||||
|
||||
addDialig.PIAuditState = incommand.PIAuditState;
|
||||
|
||||
addDialig.PIAuditImagePath = visitTask.PIAuditImagePath;
|
||||
|
||||
await _PIAuditRepository.AddAsync(addDialig);
|
||||
|
@ -1227,18 +1230,9 @@ namespace IRaCIS.Core.Application.Service.Allocation
|
|||
{
|
||||
if (origenalTask.ReadingCategory == ReadingCategory.Visit)
|
||||
{
|
||||
var list = _readingTaskQuestionAnswerRepository.Where(t => t.VisitTaskId == origenalTask.Id).ToList();
|
||||
|
||||
foreach (var item in list)
|
||||
{
|
||||
item.Id = Guid.Empty;
|
||||
item.VisitTaskId = newTask.Id;
|
||||
}
|
||||
|
||||
_ = _readingTaskQuestionAnswerRepository.AddRangeAsync(list).Result;
|
||||
CopyForms(newTask, origenalTask);
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
//拷贝后续表单
|
||||
|
@ -1246,15 +1240,7 @@ namespace IRaCIS.Core.Application.Service.Allocation
|
|||
{
|
||||
if (origenalTask.ReadingCategory == ReadingCategory.Visit)
|
||||
{
|
||||
var list = _readingTaskQuestionAnswerRepository.Where(t => t.VisitTaskId == origenalTask.Id).ToList();
|
||||
|
||||
foreach (var item in list)
|
||||
{
|
||||
item.Id = Guid.Empty;
|
||||
item.VisitTaskId = newTask.Id;
|
||||
}
|
||||
|
||||
_ = _readingTaskQuestionAnswerRepository.AddRangeAsync(list).Result;
|
||||
CopyForms(newTask, origenalTask);
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -1350,15 +1336,7 @@ namespace IRaCIS.Core.Application.Service.Allocation
|
|||
{
|
||||
if (origenalTask.ReadingCategory == ReadingCategory.Visit)
|
||||
{
|
||||
var list = _readingTaskQuestionAnswerRepository.Where(t => t.VisitTaskId == origenalTask.Id).ToList();
|
||||
|
||||
foreach (var item in list)
|
||||
{
|
||||
item.Id = Guid.Empty;
|
||||
item.VisitTaskId = newTask.Id;
|
||||
}
|
||||
|
||||
_ = _readingTaskQuestionAnswerRepository.AddRangeAsync(list).Result;
|
||||
CopyForms(newTask, origenalTask);
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -1368,15 +1346,7 @@ namespace IRaCIS.Core.Application.Service.Allocation
|
|||
{
|
||||
if (origenalTask.ReadingCategory == ReadingCategory.Visit)
|
||||
{
|
||||
var list = _readingTaskQuestionAnswerRepository.Where(t => t.VisitTaskId == origenalTask.Id).ToList();
|
||||
|
||||
foreach (var item in list)
|
||||
{
|
||||
item.Id = Guid.Empty;
|
||||
item.VisitTaskId = newTask.Id;
|
||||
}
|
||||
|
||||
_ = _readingTaskQuestionAnswerRepository.AddRangeAsync(list).Result;
|
||||
CopyForms(newTask, origenalTask);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1435,7 +1405,69 @@ namespace IRaCIS.Core.Application.Service.Allocation
|
|||
return ResponseOutput.Ok();
|
||||
}
|
||||
|
||||
private void CopyForms(VisitTask newTask, VisitTask origenalTask)
|
||||
{
|
||||
|
||||
//自定义
|
||||
var readingCustomTagList = _repository.Where<ReadingCustomTag>(t => t.VisitTaskId == origenalTask.Id).ToList();
|
||||
|
||||
foreach (var item in readingCustomTagList)
|
||||
{
|
||||
item.Id = Guid.Empty;
|
||||
item.VisitTaskId = newTask.Id;
|
||||
}
|
||||
|
||||
_ = _repository.AddRangeAsync(readingCustomTagList).Result;
|
||||
|
||||
|
||||
//var readingTaskQuestionMarkList = _repository.Where<ReadingTaskQuestionMark>(t => t.VisitTaskId == origenalTask.Id).ToList();
|
||||
|
||||
//foreach (var item in readingTaskQuestionMarkList)
|
||||
//{
|
||||
// item.Id = Guid.Empty;
|
||||
// item.VisitTaskId = newTask.Id;
|
||||
//}
|
||||
|
||||
//_ = _repository.AddRangeAsync(readingTaskQuestionMarkList).Result;
|
||||
|
||||
var readingTaskQuestionAnswerList = _repository.Where<ReadingTaskQuestionAnswer>(t => t.VisitTaskId == origenalTask.Id).ToList();
|
||||
|
||||
foreach (var item in readingTaskQuestionAnswerList)
|
||||
{
|
||||
item.Id = Guid.Empty;
|
||||
item.VisitTaskId = newTask.Id;
|
||||
}
|
||||
_ = _repository.AddRangeAsync(readingTaskQuestionAnswerList).Result;
|
||||
|
||||
|
||||
|
||||
//ReadingTableAnswerRowInfo ReadingTableQuestionAnswer 一起加
|
||||
var readingTableAnswerRowInfoList = _repository.Where<ReadingTableAnswerRowInfo>(t => t.VisitTaskId == origenalTask.Id).Include(t => t.LesionAnswerList).ToList();
|
||||
|
||||
foreach (var item in readingTableAnswerRowInfoList)
|
||||
{
|
||||
var originalVisitTaskId = item.VisitTaskId;
|
||||
var originalFristAddTaskId = item.FristAddTaskId;
|
||||
|
||||
item.Id = NewId.NextSequentialGuid();
|
||||
item.VisitTaskId = newTask.Id;
|
||||
item.FristAddTaskId = originalVisitTaskId == originalFristAddTaskId ? newTask.Id : item.FristAddTaskId;
|
||||
|
||||
foreach (var item2 in item.LesionAnswerList)
|
||||
{
|
||||
item2.Id = Guid.Empty;
|
||||
item2.RowId = item.Id;
|
||||
item2.VisitTaskId = newTask.Id;
|
||||
}
|
||||
}
|
||||
|
||||
_ = _repository.AddRangeAsync(readingTableAnswerRowInfoList).Result;
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
}
|
||||
/// <summary>
|
||||
/// PM 设置任务 退回
|
||||
/// </summary>
|
||||
|
|
|
@ -251,7 +251,7 @@ namespace IRaCIS.Core.Application.Service
|
|||
CreateMap<PIAudit, PIAuditDialogListView>()
|
||||
.ForMember(o => o.CreateUserName, t => t.MapFrom(u => u.CreateUser.UserName))
|
||||
.ForMember(o => o.UserTypeEnum, t => t.MapFrom(u => u.CreateUser.UserTypeEnum))
|
||||
.ForMember(o => o.PIAuditState, t => t.MapFrom(u => u.VisitTask.PIAuditState))
|
||||
//.ForMember(o => o.PIAuditState, t => t.MapFrom(u => u.VisitTask.PIAuditState))
|
||||
;
|
||||
|
||||
|
||||
|
|
|
@ -249,7 +249,7 @@ namespace IRaCIS.Application.Services
|
|||
public async Task<Dictionary<string, List<BasicDicSelectCopy>>> GetBasicDataSelect(string[] searchArray)
|
||||
{
|
||||
|
||||
var searchList = await _dicRepository.Where(t => searchArray.Contains(t.Parent.Code) && t.ParentId != null && t.IsEnable).ProjectTo<BasicDicSelectCopy>(_mapper.ConfigurationProvider).ToListAsync();
|
||||
var searchList = await _dicRepository.Where(t => searchArray.Contains(t.Parent.Code) && t.ParentId != null && t.IsEnable).ProjectTo<BasicDicSelectCopy>(_mapper.ConfigurationProvider,new { isEn_Us = _userInfo.IsEn_Us}).ToListAsync();
|
||||
|
||||
return searchList.GroupBy(t => t.ParentCode).ToDictionary(g => g.Key, g => g.OrderBy(t => t.ShowOrder).ToList());
|
||||
|
||||
|
|
|
@ -6,7 +6,6 @@ using Microsoft.AspNetCore.Hosting;
|
|||
using IRaCIS.Core.Application.Auth;
|
||||
using AutoMapper;
|
||||
using IRaCIS.Application.Contracts;
|
||||
using Nito.AsyncEx;
|
||||
using Microsoft.Extensions.Options;
|
||||
|
||||
namespace IRaCIS.Application.Services
|
||||
|
@ -55,7 +54,6 @@ namespace IRaCIS.Application.Services
|
|||
|
||||
|
||||
|
||||
private readonly AsyncLock _mutex = new AsyncLock();
|
||||
|
||||
private readonly SystemEmailSendConfig _systemEmailConfig;
|
||||
|
||||
|
|
|
@ -58,7 +58,7 @@ namespace IRaCIS.Core.Application.Service
|
|||
|
||||
CreateMap<Dictionary, BasicDicSelectCopy>()
|
||||
.ForMember(o => o.ParentChildCodeEnum, t => t.MapFrom(u => u.Parent.ChildCodeEnum))
|
||||
.ForMember(o => o.Value, t => t.MapFrom(u => u.MappedValue))
|
||||
.ForMember(o => o.Value, t => t.MapFrom(u => isEn_Us? u.Value : u.ValueCN ))
|
||||
.ForMember(o => o.ParentCode, t => t.MapFrom(u => u.Parent.Code));
|
||||
|
||||
CreateMap<Dictionary, BasicDicSelect>()
|
||||
|
|
|
@ -103,7 +103,7 @@ namespace IRaCIS.Core.Application.Service
|
|||
return (topicStr, htmlBodyStr, isEn_us, null);
|
||||
};
|
||||
|
||||
await SendTrialEmailAsync(taskInfo.TrialId, businessScenarioEnum, topicAndHtmlFunc);
|
||||
await SendTrialEmailAsync(taskInfo.TrialId, businessScenarioEnum, topicAndHtmlFunc, taskInfo.SiteId);
|
||||
}
|
||||
else
|
||||
{
|
||||
|
|
|
@ -170,7 +170,7 @@ namespace IRaCIS.Core.Application.Services
|
|||
SignViewMinimumMinutes = sysDoc.SignViewMinimumMinutes,
|
||||
Name = sysDoc.Name,
|
||||
Path = sysDoc.Path,
|
||||
FileType = sysDoc.FileType.MappedValue,
|
||||
FileType = _userInfo.IsEn_Us? sysDoc.FileType.Value: sysDoc.FileType.ValueCN,
|
||||
UpdateTime = sysDoc.UpdateTime,
|
||||
|
||||
FullFilePath = sysDoc.Path ,
|
||||
|
|
|
@ -27,7 +27,6 @@ namespace IRaCIS.Core.Application.Services
|
|||
private readonly IRepository<Trial> _trialRepository;
|
||||
private readonly IRepository<SystemDocConfirmedUser> _systemDocConfirmedUserRepository;
|
||||
private readonly IRepository<SystemDocument> _systemDocumentRepository;
|
||||
private readonly IRepository<TrialCriterionAdditionalAssessmentType> _trialCriterionAdditionalAssessmentTypeRepository;
|
||||
private readonly IRepository<ReadingQuestionCriterionTrial> _readingQuestionCriterionTrialRepository;
|
||||
|
||||
|
||||
|
@ -35,7 +34,6 @@ namespace IRaCIS.Core.Application.Services
|
|||
IRepository<TrialDocConfirmedUser> trialDocUserTypeConfirmedUserRepository,
|
||||
IRepository<Trial> trialRepository,
|
||||
IRepository<SystemDocConfirmedUser> systemDocConfirmedUserRepository,
|
||||
IRepository<TrialCriterionAdditionalAssessmentType> trialCriterionAdditionalAssessmentTypeRepository,
|
||||
IRepository<ReadingQuestionCriterionTrial> readingQuestionCriterionTrialRepository
|
||||
, IRepository<SystemDocument> systemDocumentRepository)
|
||||
{
|
||||
|
@ -45,7 +43,6 @@ namespace IRaCIS.Core.Application.Services
|
|||
this._systemDocConfirmedUserRepository = systemDocConfirmedUserRepository;
|
||||
_systemDocumentRepository = systemDocumentRepository;
|
||||
_readingQuestionCriterionTrialRepository = readingQuestionCriterionTrialRepository;
|
||||
_trialCriterionAdditionalAssessmentTypeRepository = trialCriterionAdditionalAssessmentTypeRepository;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -60,7 +57,7 @@ namespace IRaCIS.Core.Application.Services
|
|||
var trialDocumentQueryable = _trialDocumentRepository.AsQueryable(true).Where(t => t.TrialId == queryTrialDocument.TrialId)
|
||||
.WhereIf(!string.IsNullOrEmpty(queryTrialDocument.Name), t => t.Name.Contains(queryTrialDocument.Name))
|
||||
.WhereIf(queryTrialDocument.FileTypeId != null, t => t.FileTypeId == queryTrialDocument.FileTypeId)
|
||||
.ProjectTo<TrialDocumentView>(_mapper.ConfigurationProvider, new { token = _userInfo.UserToken });
|
||||
.ProjectTo<TrialDocumentView>(_mapper.ConfigurationProvider, new { token = _userInfo.UserToken, isEn_Us=_userInfo.IsEn_Us });
|
||||
|
||||
return await trialDocumentQueryable.ToPagedListAsync(queryTrialDocument.PageIndex, queryTrialDocument.PageSize, queryTrialDocument.SortField, queryTrialDocument.Asc);
|
||||
}
|
||||
|
@ -160,7 +157,7 @@ namespace IRaCIS.Core.Application.Services
|
|||
Name = needConfirmedUserType.SystemDocument.Name,
|
||||
Path = needConfirmedUserType.SystemDocument.Path,
|
||||
FileTypeId = needConfirmedUserType.SystemDocument.FileTypeId,
|
||||
FileType = needConfirmedUserType.SystemDocument.FileType.MappedValue,
|
||||
FileType = _userInfo.IsEn_Us? needConfirmedUserType.SystemDocument.FileType.Value: needConfirmedUserType.SystemDocument.FileType.ValueCN,
|
||||
UpdateTime = needConfirmedUserType.SystemDocument.UpdateTime,
|
||||
|
||||
FullFilePath = needConfirmedUserType.SystemDocument.Path ,
|
||||
|
@ -192,7 +189,7 @@ namespace IRaCIS.Core.Application.Services
|
|||
Name = trialDoc.Name,
|
||||
Path = trialDoc.Path,
|
||||
FileTypeId = trialDoc.FileTypeId,
|
||||
FileType = trialDoc.FileType.MappedValue,
|
||||
FileType = _userInfo.IsEn_Us ? trialDoc.FileType.Value: trialDoc.FileType.ValueCN,
|
||||
UpdateTime = trialDoc.UpdateTime,
|
||||
SignViewMinimumMinutes = trialDoc.SignViewMinimumMinutes,
|
||||
|
||||
|
@ -206,13 +203,35 @@ namespace IRaCIS.Core.Application.Services
|
|||
};
|
||||
|
||||
|
||||
#region 报错 奇怪的bug
|
||||
var unionQuery = systemDocumentQueryable.Union(trialDocQueryable)
|
||||
.WhereIf(!string.IsNullOrEmpty(querySystemDocument.Name), t => t.Name.Contains(querySystemDocument.Name))
|
||||
.WhereIf(querySystemDocument.FileTypeId != null, t => t.FileTypeId == querySystemDocument.FileTypeId)
|
||||
.WhereIf(querySystemDocument.IsSign == true, t => t.ConfirmTime != null)
|
||||
.WhereIf(querySystemDocument.IsSign == false, t => t.ConfirmTime == null);
|
||||
.WhereIf(!string.IsNullOrEmpty(querySystemDocument.Name), t => t.Name.Contains(querySystemDocument.Name))
|
||||
.WhereIf(querySystemDocument.FileTypeId != null, t => t.FileTypeId == querySystemDocument.FileTypeId)
|
||||
.WhereIf(querySystemDocument.IsSign == true, t => t.ConfirmTime != null)
|
||||
.WhereIf(querySystemDocument.IsSign == false, t => t.ConfirmTime == null);
|
||||
|
||||
var result = await unionQuery.ToPagedListAsync(querySystemDocument.PageIndex, querySystemDocument.PageSize, querySystemDocument.SortField, querySystemDocument.Asc);
|
||||
#endregion
|
||||
|
||||
#region 临时方案
|
||||
|
||||
//var list1 = systemDocumentQueryable
|
||||
// .WhereIf(!string.IsNullOrEmpty(querySystemDocument.Name), t => t.Name.Contains(querySystemDocument.Name))
|
||||
// .WhereIf(querySystemDocument.FileTypeId != null, t => t.FileTypeId == querySystemDocument.FileTypeId)
|
||||
// .WhereIf(querySystemDocument.IsSign == true, t => t.ConfirmTime != null)
|
||||
// .WhereIf(querySystemDocument.IsSign == false, t => t.ConfirmTime == null).ToList();
|
||||
|
||||
//var list2 = trialDocQueryable
|
||||
// .WhereIf(!string.IsNullOrEmpty(querySystemDocument.Name), t => t.Name.Contains(querySystemDocument.Name))
|
||||
//.WhereIf(querySystemDocument.FileTypeId != null, t => t.FileTypeId == querySystemDocument.FileTypeId)
|
||||
//.WhereIf(querySystemDocument.IsSign == true, t => t.ConfirmTime != null)
|
||||
//.WhereIf(querySystemDocument.IsSign == false, t => t.ConfirmTime == null).ToList();
|
||||
|
||||
//var list3 = list1.Union(list2).ToList();
|
||||
|
||||
//var result = list3.ToPagedList(querySystemDocument.PageIndex, querySystemDocument.PageSize, querySystemDocument.SortField, querySystemDocument.Asc);
|
||||
|
||||
#endregion
|
||||
|
||||
var needSignTrialDocCount = await _trialDocumentRepository.AsQueryable(true).Where(t => t.TrialId== querySystemDocument.TrialId && t.Trial.TrialStatusStr != StaticData.TrialState.TrialStopped)
|
||||
.Where(t => t.Trial.TrialUserList.Any(t => t.UserId == _userInfo.Id))
|
||||
|
@ -227,13 +246,11 @@ namespace IRaCIS.Core.Application.Services
|
|||
var trialTaskConfig = _trialRepository.Where(t => t.Id == querySystemDocument.TrialId).ProjectTo<TrialConfigTabDto>(_mapper.ConfigurationProvider).FirstOrDefault();
|
||||
|
||||
|
||||
//var trialCriterionAdditionalAssessmentTypeList = _trialCriterionAdditionalAssessmentTypeRepository
|
||||
// .Where(t => t.TrialReadingCriterion.TrialId == trialId && t.IsSelected == true && t.TrialReadingCriterion.IsSigned).Select(t=>new { t.CriterionType,t.AdditionalAssessmentType}).ToList();
|
||||
|
||||
|
||||
var isManualGenerateTask= _readingQuestionCriterionTrialRepository.Where(t=>t.TrialId==trialId && t.IsSigned && t.IsAutoCreate==false).Any();
|
||||
var isAdditionalAssessment = _readingQuestionCriterionTrialRepository.Where(t => t.TrialId == trialId && t.IsSigned && t.IsAdditionalAssessment == true
|
||||
&&t.TrialCriterionAdditionalAssessmentTypeList.Any(c=>/*c.AdditionalAssessmentType==Domain.Share.Reading.AdditionalAssessmentType.BrainMetastasis &&*/ c.IsSelected==true)).Any();
|
||||
|
||||
var isAdditionalAssessment =false;
|
||||
|
||||
|
||||
var isAllOnlySRReading = _readingQuestionCriterionTrialRepository.Where(t => t.TrialId == trialId && t.IsSigned).All(t => t.ReadingDivisionEnum == ReadingDivisionEnum.OnlySR);
|
||||
|
@ -316,7 +333,7 @@ namespace IRaCIS.Core.Application.Services
|
|||
Name = trialDocumentNeedConfirmedUserType.TrialDocument.Name,
|
||||
Path = trialDocumentNeedConfirmedUserType.TrialDocument.Path,
|
||||
FileTypeId = trialDocumentNeedConfirmedUserType.TrialDocument.FileTypeId,
|
||||
FileType = trialDocumentNeedConfirmedUserType.TrialDocument.FileType.MappedValue,
|
||||
FileType = _userInfo.IsEn_Us ? trialDocumentNeedConfirmedUserType.TrialDocument.FileType.Value : trialDocumentNeedConfirmedUserType.TrialDocument.FileType.ValueCN,
|
||||
UpdateTime = trialDocumentNeedConfirmedUserType.TrialDocument.UpdateTime,
|
||||
|
||||
|
||||
|
@ -350,7 +367,7 @@ namespace IRaCIS.Core.Application.Services
|
|||
SignViewMinimumMinutes = needConfirmEdUserType.SystemDocument.SignViewMinimumMinutes,
|
||||
Name = needConfirmEdUserType.SystemDocument.Name,
|
||||
Path = needConfirmEdUserType.SystemDocument.Path,
|
||||
FileType = needConfirmEdUserType.SystemDocument.FileType.MappedValue,
|
||||
FileType = _userInfo.IsEn_Us ? needConfirmEdUserType.SystemDocument.FileType.Value : needConfirmEdUserType.SystemDocument.FileType.ValueCN,
|
||||
FileTypeId = needConfirmEdUserType.SystemDocument.FileTypeId,
|
||||
UpdateTime = needConfirmEdUserType.SystemDocument.UpdateTime,
|
||||
|
||||
|
|
|
@ -14,12 +14,13 @@ namespace IRaCIS.Core.Application.Service
|
|||
|
||||
var userId = Guid.Empty;
|
||||
var token = string.Empty;
|
||||
var isEn_Us = false;
|
||||
CreateMap<SystemDocument, SystemDocumentView>()
|
||||
.ForMember(d => d.FileType, u => u.MapFrom(s => s.FileType.Value))
|
||||
.ForMember(d => d.FullFilePath, u => u.MapFrom(s => s.Path));
|
||||
|
||||
CreateMap<TrialDocument, TrialDocumentView>()
|
||||
.ForMember(d => d.FileType, u => u.MapFrom(s => s.FileType.MappedValue))
|
||||
.ForMember(d => d.FileType, u => u.MapFrom(s => isEn_Us ? s.FileType.Value : s.FileType.ValueCN ))
|
||||
.ForMember(d => d.IsSomeUserSigned, u => u.MapFrom(s => s.TrialDocConfirmedUserList.Any(t=>t.ConfirmTime!=null)))
|
||||
.ForMember(d => d.FullFilePath, u => u.MapFrom(s => s.Path ));
|
||||
|
||||
|
|
|
@ -1,5 +1,4 @@
|
|||
using Dicom;
|
||||
using Dicom.Imaging.Codec;
|
||||
|
||||
using EasyCaching.Core;
|
||||
using IRaCIS.Core.Application.Contracts.Dicom;
|
||||
using IRaCIS.Core.Domain.Share;
|
||||
|
@ -8,10 +7,13 @@ using IRaCIS.Core.Application.Contracts;
|
|||
using IRaCIS.Core.Application.Helper;
|
||||
using Microsoft.AspNetCore.Hosting;
|
||||
using IRaCIS.Core.Infrastructure;
|
||||
using FellowOakDicom;
|
||||
using FellowOakDicom.Imaging.Codec;
|
||||
using Medallion.Threading;
|
||||
|
||||
namespace IRaCIS.Core.Application.Services
|
||||
{
|
||||
public class DicomArchiveService :BaseService, IDicomArchiveService
|
||||
public class DicomArchiveService : BaseService, IDicomArchiveService
|
||||
{
|
||||
private readonly IRepository<DicomStudy> _studyRepository;
|
||||
private readonly IRepository<DicomSeries> _seriesRepository;
|
||||
|
@ -21,7 +23,7 @@ namespace IRaCIS.Core.Application.Services
|
|||
|
||||
private readonly IWebHostEnvironment _hostEnvironment;
|
||||
|
||||
private static object lockCodeGenerate = new object();
|
||||
private readonly IDistributedLockProvider _distributedLockProvider;
|
||||
|
||||
|
||||
private List<Guid> _instanceIdList = new List<Guid>();
|
||||
|
@ -31,8 +33,9 @@ namespace IRaCIS.Core.Application.Services
|
|||
IRepository<DicomInstance> instanceRepository,
|
||||
IWebHostEnvironment hostEnvironment,
|
||||
IRepository<Dictionary> dictionaryRepository,
|
||||
IEasyCachingProvider provider)
|
||||
IEasyCachingProvider provider, IDistributedLockProvider distributedLockProvider)
|
||||
{
|
||||
_distributedLockProvider = distributedLockProvider;
|
||||
_hostEnvironment = hostEnvironment;
|
||||
_studyRepository = studyRepository;
|
||||
|
||||
|
@ -50,7 +53,7 @@ namespace IRaCIS.Core.Application.Services
|
|||
return success;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
public async Task<(Guid StudyId, string StudyCode)> ArchiveDicomStreamAsync(Stream dicomStream,
|
||||
|
@ -129,7 +132,7 @@ namespace IRaCIS.Core.Application.Services
|
|||
|
||||
DicomStudy dicomStudy = CreateDicomStudy(dataset, addtionalInfo, out bool isStudyNeedAdd);
|
||||
DicomSeries dicomSeries = CreateDicomSeries(dataset, dicomStudy, out bool isSeriesNeedAdd);
|
||||
DicomInstance dicomInstance = CreateDicomInstance(dataset, dicomStudy, dicomSeries,out bool isInstanceNeedAdd);
|
||||
DicomInstance dicomInstance = CreateDicomInstance(dataset, dicomStudy, dicomSeries, out bool isInstanceNeedAdd);
|
||||
|
||||
dicomSeries.DicomStudy = dicomStudy;
|
||||
|
||||
|
@ -183,7 +186,7 @@ namespace IRaCIS.Core.Application.Services
|
|||
//正常保存 不做处理
|
||||
await dicomFile.SaveAsync(physicalPath);
|
||||
}
|
||||
else
|
||||
else
|
||||
{
|
||||
//RLELossless 保存
|
||||
await dicomFile.Clone(DicomTransferSyntax.RLELossless).SaveAsync(physicalPath); //RLELossless
|
||||
|
@ -235,7 +238,7 @@ namespace IRaCIS.Core.Application.Services
|
|||
{
|
||||
modalityForEdit = "PET";
|
||||
}
|
||||
if(modality== "PT、CT")
|
||||
if (modality == "PT、CT")
|
||||
{
|
||||
modalityForEdit = "PET-CT";
|
||||
}
|
||||
|
@ -282,9 +285,10 @@ namespace IRaCIS.Core.Application.Services
|
|||
dicomStudy.PatientBirthDate = $"{dicomStudy.PatientBirthDate[0]}{dicomStudy.PatientBirthDate[1]}{dicomStudy.PatientBirthDate[2]}{dicomStudy.PatientBirthDate[3]}-{dicomStudy.PatientBirthDate[4]}{dicomStudy.PatientBirthDate[5]}-{dicomStudy.PatientBirthDate[6]}{dicomStudy.PatientBirthDate[7]}";
|
||||
}
|
||||
|
||||
lock (lockCodeGenerate)
|
||||
{
|
||||
var @lock = _distributedLockProvider.CreateLock($"StudyCode");
|
||||
|
||||
using (@lock.Acquire())
|
||||
{
|
||||
//查询数据库获取最大的Code 没有记录则为0
|
||||
var dbStudyCodeIntMax = _studyRepository.Where(s => s.TrialId == addtionalInfo.TrialId).Select(t => t.Code).DefaultIfEmpty().Max();
|
||||
|
||||
|
@ -298,9 +302,9 @@ namespace IRaCIS.Core.Application.Services
|
|||
dicomStudy.StudyCode = AppSettings.GetCodeStr(currentNextCodeInt, nameof(DicomStudy));
|
||||
|
||||
_provider.Set<int>($"{addtionalInfo.TrialId}_{StaticData.CacheKey.StudyMaxCode}", dicomStudy.Code, TimeSpan.FromMinutes(30));
|
||||
|
||||
}
|
||||
|
||||
|
||||
#region Setting Code old
|
||||
|
||||
//var studyCode = _studyRepository.Where(s => s.TrialId == addtionalInfo.TrialId).Select(t => t.StudyCode).OrderByDescending(c => c).FirstOrDefault();
|
||||
|
@ -468,7 +472,7 @@ namespace IRaCIS.Core.Application.Services
|
|||
|
||||
_instanceIdList.Add(instanceId);
|
||||
}
|
||||
|
||||
|
||||
return dicomInstance;
|
||||
|
||||
}
|
||||
|
|
|
@ -5,25 +5,27 @@ using Microsoft.AspNetCore.Authorization;
|
|||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.Extensions.Configuration;
|
||||
using IRaCIS.Core.Application.Auth;
|
||||
using EasyCaching.Core;
|
||||
|
||||
namespace IRaCIS.Core.Application.Services
|
||||
{
|
||||
[AllowAnonymous, ApiExplorerSettings(GroupName = "Image")]
|
||||
public class ImageShareService : BaseService, IImageShareService
|
||||
{
|
||||
|
||||
private readonly IEasyCachingProvider _provider;
|
||||
private readonly IRepository<ImageShare> _imageShareRepository;
|
||||
private readonly IRepository<DicomStudy> _studyRepository;
|
||||
private readonly IConfiguration _configuration;
|
||||
private readonly ITokenService _tokenService;
|
||||
|
||||
public ImageShareService(IRepository<ImageShare> imageShareRepository, IRepository<DicomStudy> studyRepository, IConfiguration configuration, ITokenService tokenService)
|
||||
public ImageShareService(IRepository<ImageShare> imageShareRepository, IRepository<DicomStudy> studyRepository, IConfiguration configuration, ITokenService tokenService, IEasyCachingProvider provider)
|
||||
{
|
||||
|
||||
_imageShareRepository = imageShareRepository;
|
||||
_studyRepository = studyRepository;
|
||||
_configuration = configuration;
|
||||
_tokenService = tokenService;
|
||||
_provider = provider;
|
||||
}
|
||||
|
||||
[HttpPost]
|
||||
|
@ -110,6 +112,7 @@ namespace IRaCIS.Core.Application.Services
|
|||
return ResponseOutput.NotOk(_localizer["ISS_ShareExpiration"]);
|
||||
}
|
||||
|
||||
var vitrualUserId = Guid.NewGuid();
|
||||
var resource = new ResourceInfo()
|
||||
{
|
||||
StudyId = imageShare.StudyId,
|
||||
|
@ -127,7 +130,7 @@ namespace IRaCIS.Core.Application.Services
|
|||
}))
|
||||
};
|
||||
|
||||
|
||||
await _provider.SetAsync(vitrualUserId.ToString(), resource.Token, TimeSpan.FromDays(7));
|
||||
return ResponseOutput.Ok(resource);
|
||||
|
||||
}
|
||||
|
|
|
@ -14,16 +14,13 @@ using IRaCIS.Core.Application.MediatR.Handlers;
|
|||
using Microsoft.AspNetCore.Http;
|
||||
using Newtonsoft.Json;
|
||||
using System.Threading;
|
||||
using Nito.AsyncEx;
|
||||
using Medallion.Threading;
|
||||
|
||||
namespace IRaCIS.Core.Application.Service.ImageAndDoc
|
||||
{
|
||||
[ApiExplorerSettings(GroupName = "Image")]
|
||||
public class StudyService : BaseService, IStudyService
|
||||
{
|
||||
private static object lockObj = new object();
|
||||
private static readonly AsyncLock _mutex = new AsyncLock();
|
||||
private static readonly AsyncLock _mutex2 = new AsyncLock();
|
||||
|
||||
private readonly IEasyCachingProvider _provider;
|
||||
|
||||
|
@ -35,12 +32,12 @@ namespace IRaCIS.Core.Application.Service.ImageAndDoc
|
|||
private readonly IRepository<Dictionary> _dictionaryRepository;
|
||||
|
||||
private readonly IRepository<StudyMonitor> _studyMonitorRepository;
|
||||
|
||||
private readonly IDistributedLockProvider _distributedLockProvider;
|
||||
|
||||
public StudyService(IEasyCachingProvider provider
|
||||
, IRepository<SubjectVisit> subjectVisitRepository,
|
||||
IRepository<DicomInstance> dicomInstanceRepository,
|
||||
IRepository<DicomSeries> dicomSeriesRepository, IRepository<DicomStudy> dicomstudyRepository, IRepository<Dictionary> dictionaryRepository, IRepository<StudyMonitor> studyMonitorRepository)
|
||||
IRepository<DicomSeries> dicomSeriesRepository, IRepository<DicomStudy> dicomstudyRepository, IRepository<Dictionary> dictionaryRepository, IRepository<StudyMonitor> studyMonitorRepository, IDistributedLockProvider distributedLockProvider)
|
||||
{
|
||||
_provider = provider;
|
||||
_subjectVisitRepository = subjectVisitRepository;
|
||||
|
@ -49,6 +46,7 @@ namespace IRaCIS.Core.Application.Service.ImageAndDoc
|
|||
_dicomstudyRepository = dicomstudyRepository;
|
||||
_dictionaryRepository = dictionaryRepository;
|
||||
_studyMonitorRepository = studyMonitorRepository;
|
||||
_distributedLockProvider = distributedLockProvider;
|
||||
}
|
||||
|
||||
|
||||
|
@ -160,7 +158,9 @@ namespace IRaCIS.Core.Application.Service.ImageAndDoc
|
|||
{
|
||||
var study = _mapper.Map<DicomStudy>(incommand.Study);
|
||||
|
||||
using (await _mutex.LockAsync())
|
||||
var @lock = _distributedLockProvider.CreateLock($"StudyCode");
|
||||
|
||||
using (await @lock.AcquireAsync())
|
||||
{
|
||||
//查询数据库获取最大的Code 没有记录则为0
|
||||
var dbStudyCodeIntMax = _dicomstudyRepository.Where(s => s.TrialId == trialId).Select(t => t.Code).DefaultIfEmpty().Max();
|
||||
|
@ -306,11 +306,11 @@ namespace IRaCIS.Core.Application.Service.ImageAndDoc
|
|||
|
||||
}
|
||||
|
||||
using (await _mutex2.LockAsync())
|
||||
var @lock2 = _distributedLockProvider.CreateLock($"StudyCommit");
|
||||
|
||||
using (await @lock2.AcquireAsync())
|
||||
{
|
||||
await _dicomInstanceRepository.SaveChangesAsync();
|
||||
|
||||
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
|
@ -765,7 +765,7 @@ namespace IRaCIS.Core.Application.Service.ImageAndDoc
|
|||
|
||||
if (_provider.Exists($"StudyUid_{trialId}_{studyInstanceUid}"))
|
||||
{
|
||||
|
||||
|
||||
result.AllowUpload = false;
|
||||
|
||||
result.AllowReUpload = false;
|
||||
|
@ -826,22 +826,22 @@ namespace IRaCIS.Core.Application.Service.ImageAndDoc
|
|||
}
|
||||
result.StudyInstanceUid = studyInstanceUid;
|
||||
|
||||
var @lock = _distributedLockProvider.CreateLock($"StudyUpload");
|
||||
|
||||
if (result.AllowReUpload || result.AllowUpload)
|
||||
using (@lock.Acquire())
|
||||
{
|
||||
lock (lockObj)
|
||||
if (result.AllowReUpload || result.AllowUpload)
|
||||
{
|
||||
_provider.Set($"StudyUid_{trialId}_{studyInstanceUid}", _userInfo.Id, TimeSpan.FromSeconds(30));
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
lock (lockObj)
|
||||
else
|
||||
{
|
||||
_provider.Remove($"StudyUid_{trialId}_{studyInstanceUid}");
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
|
|
|
@ -3,7 +3,7 @@ using IRaCIS.Application.Contracts;
|
|||
using IRaCIS.Core.Infra.EFCore;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using IRaCIS.Core.Domain.Share;
|
||||
using Nito.AsyncEx;
|
||||
using Medallion.Threading;
|
||||
|
||||
namespace IRaCIS.Application.Services
|
||||
{
|
||||
|
@ -12,13 +12,13 @@ namespace IRaCIS.Application.Services
|
|||
{
|
||||
private readonly IRepository<Site> _siteRepository;
|
||||
private readonly IRepository<TrialSiteUser> _trialSiteUserRepository;
|
||||
private readonly IDistributedLockProvider _distributedLockProvider;
|
||||
|
||||
private readonly AsyncLock _mutex = new AsyncLock();
|
||||
|
||||
public SiteService(IRepository<Site> siteRepository, IRepository<TrialSiteUser> trialSiteUserRepository)
|
||||
public SiteService(IRepository<Site> siteRepository, IRepository<TrialSiteUser> trialSiteUserRepository, IDistributedLockProvider distributedLockProvider)
|
||||
{
|
||||
_siteRepository = siteRepository;
|
||||
this._trialSiteUserRepository = trialSiteUserRepository;
|
||||
_trialSiteUserRepository = trialSiteUserRepository;
|
||||
_distributedLockProvider = distributedLockProvider;
|
||||
}
|
||||
|
||||
/// <summary> 分页获取研究中心列表 </summary>
|
||||
|
@ -27,7 +27,7 @@ namespace IRaCIS.Application.Services
|
|||
{
|
||||
|
||||
var siteQueryable = _siteRepository
|
||||
.WhereIf(!string.IsNullOrWhiteSpace(searchModel.SiteName), t => t.SiteName.Contains(searchModel.SiteName))
|
||||
.WhereIf(!string.IsNullOrWhiteSpace(searchModel.SiteName), t => t.SiteName.Contains(searchModel.SiteName) || t.SiteNameCN.Contains(searchModel.SiteName))
|
||||
.WhereIf(!string.IsNullOrWhiteSpace(searchModel.AliasName), t => t.AliasName.Contains(searchModel.AliasName))
|
||||
.WhereIf(!string.IsNullOrWhiteSpace(searchModel.City), t => t.City.Contains(searchModel.City))
|
||||
.WhereIf(!string.IsNullOrWhiteSpace(searchModel.Country), t => t.Country.Contains(searchModel.Country))
|
||||
|
@ -58,7 +58,9 @@ namespace IRaCIS.Application.Services
|
|||
VerifyMsg = _localizer["Site_DupName"]
|
||||
};
|
||||
|
||||
using (await _mutex.LockAsync())
|
||||
var @lock = _distributedLockProvider.CreateLock($"SiteAdd");
|
||||
|
||||
using (await @lock.AcquireAsync())
|
||||
{
|
||||
if (siteCommand.Id == null)
|
||||
{
|
||||
|
|
|
@ -8,10 +8,10 @@ using Panda.DynamicWebApi.Attributes;
|
|||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.Extensions.Options;
|
||||
using Microsoft.Extensions.Caching.Memory;
|
||||
using IRaCIS.Core.Infra.Common.Cache;
|
||||
using Microsoft.Identity.Client;
|
||||
using static IRaCIS.Core.Domain.Share.StaticData;
|
||||
using IRaCIS.Core.Application.ViewModel;
|
||||
using Medallion.Threading;
|
||||
|
||||
namespace IRaCIS.Application.Services
|
||||
{
|
||||
|
@ -24,7 +24,7 @@ namespace IRaCIS.Application.Services
|
|||
private readonly IRepository<TrialUser> _userTrialRepository;
|
||||
private readonly IRepository<UserLog> _userLogRepository;
|
||||
|
||||
|
||||
private readonly IDistributedLockProvider _distributedLockProvider;
|
||||
private readonly IMemoryCache _cache;
|
||||
|
||||
private readonly IOptionsMonitor<ServiceVerifyConfigOption> _verifyConfig;
|
||||
|
@ -38,7 +38,8 @@ namespace IRaCIS.Application.Services
|
|||
IRepository<TrialUser> userTrialRepository,
|
||||
IOptionsMonitor<ServiceVerifyConfigOption> verifyConfig,
|
||||
IRepository<UserLog> userLogRepository
|
||||
)
|
||||
,
|
||||
IDistributedLockProvider distributedLockProvider)
|
||||
{
|
||||
_userLogRepository = userLogRepository;
|
||||
|
||||
|
@ -47,9 +48,10 @@ namespace IRaCIS.Application.Services
|
|||
_userRepository = userRepository;
|
||||
_mailVerificationService = mailVerificationService;
|
||||
_verificationCodeRepository = verificationCodeRepository;
|
||||
|
||||
|
||||
_userTrialRepository = userTrialRepository;
|
||||
_userLogRepository = userLogRepository;
|
||||
_distributedLockProvider = distributedLockProvider;
|
||||
}
|
||||
|
||||
|
||||
|
@ -502,29 +504,32 @@ namespace IRaCIS.Application.Services
|
|||
|
||||
var saveItem = _mapper.Map<User>(userAddModel);
|
||||
|
||||
saveItem.Code = await _userRepository.Select(t => t.Code).DefaultIfEmpty().MaxAsync() + 1;
|
||||
var @lock = _distributedLockProvider.CreateLock($"UserAccount");
|
||||
|
||||
saveItem.UserCode = AppSettings.GetCodeStr(saveItem.Code, nameof(User));
|
||||
|
||||
if (saveItem.IsZhiZhun)
|
||||
using (await @lock.AcquireAsync())
|
||||
{
|
||||
saveItem.OrganizationName = AppSettings.DefaultInternalOrganizationName;
|
||||
saveItem.Code = await _userRepository.Select(t => t.Code).DefaultIfEmpty().MaxAsync() + 1;
|
||||
|
||||
saveItem.UserCode = AppSettings.GetCodeStr(saveItem.Code, nameof(User));
|
||||
|
||||
if (saveItem.IsZhiZhun)
|
||||
{
|
||||
saveItem.OrganizationName = AppSettings.DefaultInternalOrganizationName;
|
||||
}
|
||||
|
||||
|
||||
saveItem.Password = MD5Helper.Md5("123456");
|
||||
|
||||
await _userRepository.AddAsync(saveItem);
|
||||
|
||||
var success = await _userRepository.SaveChangesAsync();
|
||||
}
|
||||
|
||||
|
||||
saveItem.Password = MD5Helper.Md5("123456");
|
||||
|
||||
await _userRepository.AddAsync(saveItem);
|
||||
|
||||
var success = await _userRepository.SaveChangesAsync();
|
||||
|
||||
|
||||
|
||||
await _mailVerificationService.AddUserSendEmailAsync(saveItem.Id, userAddModel.BaseUrl, userAddModel.RouteUrl);
|
||||
|
||||
|
||||
|
||||
|
||||
return ResponseOutput.Result(success, new UserAddedReturnDTO { Id = saveItem.Id, UserCode = saveItem.UserCode });
|
||||
return ResponseOutput.Ok( new UserAddedReturnDTO { Id = saveItem.Id, UserCode = saveItem.UserCode });
|
||||
|
||||
}
|
||||
|
||||
|
|
|
@ -5,10 +5,10 @@
|
|||
//--------------------------------------------------------------------
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using IRaCIS.Core.Application.Filter;
|
||||
using Nito.AsyncEx;
|
||||
using System.ComponentModel.DataAnnotations;
|
||||
using IRaCIS.Core.Application.Service;
|
||||
using IRaCIS.Core.Domain.Share;
|
||||
using Medallion.Threading;
|
||||
|
||||
namespace IRaCIS.Core.Application.Contracts
|
||||
{
|
||||
|
@ -20,19 +20,19 @@ namespace IRaCIS.Core.Application.Contracts
|
|||
{
|
||||
private readonly IRepository<NoneDicomStudy> _noneDicomStudyRepository;
|
||||
private readonly IRepository<NoneDicomStudyFile> _noneDicomStudyFileRepository;
|
||||
private readonly AsyncLock _mutex = new AsyncLock();
|
||||
private readonly IDistributedLockProvider _distributedLockProvider;
|
||||
private readonly QCCommon _qCCommon;
|
||||
|
||||
|
||||
public NoneDicomStudyService(IRepository<NoneDicomStudy> noneDicomStudyRepository,
|
||||
QCCommon qCCommon,
|
||||
IRepository<NoneDicomStudyFile> noneDicomStudyFileRepository)
|
||||
IRepository<NoneDicomStudyFile> noneDicomStudyFileRepository, IDistributedLockProvider distributedLockProvider)
|
||||
{
|
||||
_qCCommon = qCCommon;
|
||||
_noneDicomStudyRepository = noneDicomStudyRepository;
|
||||
|
||||
_noneDicomStudyFileRepository = noneDicomStudyFileRepository;
|
||||
|
||||
_distributedLockProvider = distributedLockProvider;
|
||||
}
|
||||
|
||||
|
||||
|
@ -62,7 +62,9 @@ namespace IRaCIS.Core.Application.Contracts
|
|||
}
|
||||
|
||||
NoneDicomStudy? optEntity = null;
|
||||
using (await _mutex.LockAsync())
|
||||
var @lock = _distributedLockProvider.CreateLock($"NoneDicomCode");
|
||||
|
||||
using (await @lock.AcquireAsync())
|
||||
{
|
||||
if (addOrEditNoneDicomStudy.Id == Guid.Empty || addOrEditNoneDicomStudy.Id == null)
|
||||
{
|
||||
|
|
|
@ -10,13 +10,13 @@ using WinSCP;
|
|||
using Newtonsoft.Json;
|
||||
using IRaCIS.Core.Infrastructure;
|
||||
using IRaCIS.Core.Application.Service.Inspection.DTO;
|
||||
using Nito.AsyncEx;
|
||||
using System.ComponentModel.DataAnnotations;
|
||||
using IRaCIS.Core.Application.Auth;
|
||||
using IRaCIS.Core.Application.Helper;
|
||||
using IRaCIS.Core.Application.ViewModel;
|
||||
using IRaCIS.Core.Domain.Models;
|
||||
using IRaCIS.Core.Application.Service;
|
||||
using Medallion.Threading;
|
||||
|
||||
namespace IRaCIS.Core.Application.Image.QA
|
||||
{
|
||||
|
@ -35,8 +35,7 @@ namespace IRaCIS.Core.Application.Image.QA
|
|||
private readonly IRepository<Trial> _trialRepository;
|
||||
private readonly IRepository<VisitTask> _visitTaskRepository;
|
||||
private readonly IVisitTaskHelpeService _IVisitTaskHelpeService;
|
||||
|
||||
private readonly AsyncLock _mutex = new AsyncLock();
|
||||
private readonly IDistributedLockProvider _distributedLockProvider;
|
||||
|
||||
public QCOperationService(IRepository<SubjectVisit> subjectVisitRepository,
|
||||
IRepository<QCChallenge> qcChallengeRepository,
|
||||
|
@ -48,7 +47,8 @@ namespace IRaCIS.Core.Application.Image.QA
|
|||
IRepository<ReadingClinicalData> readingClinicalDataRepository,
|
||||
IRepository<QCChallengeDialog> qCChallengeDialogrepository,
|
||||
IRepository<CheckChallengeDialog> checkChallengeDialogrepository,
|
||||
IVisitTaskHelpeService visitTaskHelpeService
|
||||
IVisitTaskHelpeService visitTaskHelpeService,
|
||||
IDistributedLockProvider distributedLockProvider
|
||||
)
|
||||
{
|
||||
_subjectVisitRepository = subjectVisitRepository;
|
||||
|
@ -62,6 +62,7 @@ namespace IRaCIS.Core.Application.Image.QA
|
|||
_trialRepository = trialRepository;
|
||||
this._visitTaskRepository = visitTaskRepository;
|
||||
_IVisitTaskHelpeService = visitTaskHelpeService;
|
||||
_distributedLockProvider = distributedLockProvider;
|
||||
}
|
||||
|
||||
#region QC质疑 以及回复 关闭
|
||||
|
@ -108,9 +109,9 @@ namespace IRaCIS.Core.Application.Image.QA
|
|||
|
||||
var trialConfig = (await _trialRepository.Where(t => t.Id == trialId).Select(t => new { TrialId = t.Id, t.QCProcessEnum, t.IsImageConsistencyVerification }).FirstOrDefaultAsync()).IfNullThrowException();
|
||||
|
||||
var @lock = _distributedLockProvider.CreateLock($"QCChallengeCode");
|
||||
|
||||
|
||||
using (await _mutex.LockAsync())
|
||||
using (await @lock.AcquireAsync())
|
||||
{
|
||||
//获取编号
|
||||
var code = _qcChallengeRepository.Where(t => t.TrialId == trialId).Select(t => t.Code).DefaultIfEmpty().Max();
|
||||
|
@ -1968,6 +1969,18 @@ namespace IRaCIS.Core.Application.Image.QA
|
|||
//已确认临床数据完整性
|
||||
dbSubjectVisit.IsConfirmedClinicalData = true;
|
||||
|
||||
|
||||
await _readingClinicalDataRepository.UpdatePartialFromQueryAsync(x =>
|
||||
|
||||
(x.ClinicalDataTrialSet.ClinicalDataLevel == ClinicalLevel.Subject || x.ClinicalDataTrialSet.ClinicalDataLevel == ClinicalLevel.SubjectVisit) &&
|
||||
|
||||
|
||||
x.ClinicalDataTrialSet.UploadRole == UploadRole.CRC && x.ReadingId == dbSubjectVisit.Id && x.IsSign == false, x => new ReadingClinicalData()
|
||||
{
|
||||
IsSign = true,
|
||||
ReadingClinicalDataState = ReadingClinicalDataStatus.HaveSigned
|
||||
});
|
||||
|
||||
//var signSuccess = await _repository.BatchUpdateAsync<TrialSign>(t => t.Id == cRCReuploadFinishedCommand.SignId, u => new TrialSign() { IsCompleted = true });
|
||||
}
|
||||
|
||||
|
|
|
@ -148,6 +148,7 @@ namespace IRaCIS.Application.Services
|
|||
|
||||
var fileCount = await _readingClinicalDataPDFRepository.Where(t => t.ReadingClinicalDataId == indto.Id).CountAsync();
|
||||
entity.ReadingClinicalDataState = ReadingClinicalDataStatus.HaveUploaded;
|
||||
entity.IsSign = false;
|
||||
entity.FileCount = fileCount;
|
||||
var success = await _readingClinicalDataRepository.SaveChangesAsync();
|
||||
return ResponseOutput.Ok(entity.Id);
|
||||
|
|
|
@ -266,7 +266,7 @@ namespace IRaCIS.Core.Application.Service.Reading.Dto
|
|||
public string ImagePath { get; set; } = string.Empty;
|
||||
|
||||
|
||||
public List<ImageInfo> FileList { get; set; } = new List<ImageInfo>();
|
||||
public List<OSSImageInfo> FileList { get; set; } = new List<OSSImageInfo>();
|
||||
|
||||
|
||||
}
|
||||
|
@ -314,7 +314,7 @@ namespace IRaCIS.Core.Application.Service.Reading.Dto
|
|||
|
||||
|
||||
|
||||
public List<ImageInfo> FileList { get; set; } = new List<ImageInfo>();
|
||||
public List<OSSImageInfo> FileList { get; set; } = new List<OSSImageInfo>();
|
||||
|
||||
|
||||
|
||||
|
@ -455,7 +455,7 @@ namespace IRaCIS.Core.Application.Service.Reading.Dto
|
|||
public Guid TaskMedicalReviewId { get; set; }
|
||||
|
||||
|
||||
public List<ImageInfo> FileList { get; set; } = new List<ImageInfo>();
|
||||
public List<OSSImageInfo> FileList { get; set; } = new List<OSSImageInfo>();
|
||||
|
||||
|
||||
/// <summary>
|
||||
|
@ -502,7 +502,7 @@ namespace IRaCIS.Core.Application.Service.Reading.Dto
|
|||
public string Questioning { get; set; } = string.Empty;
|
||||
|
||||
|
||||
public List<ImageInfo> FileList { get; set; } = new List<ImageInfo>();
|
||||
public List<OSSImageInfo> FileList { get; set; } = new List<OSSImageInfo>();
|
||||
|
||||
/// <summary>
|
||||
/// 审核建议
|
||||
|
|
|
@ -1,51 +0,0 @@
|
|||
using Microsoft.AspNetCore.JsonPatch.Operations;
|
||||
using Swashbuckle.AspNetCore.Filters;
|
||||
|
||||
namespace IRaCIS.Core.Application.Contracts
|
||||
{
|
||||
/// <summary>
|
||||
/// 实测 标注在服务方法上 没用
|
||||
/// </summary>
|
||||
public class JsonPatchUserRequestExample : IExamplesProvider<object>
|
||||
{
|
||||
public Operation[] GetExamples()
|
||||
{
|
||||
return new[]
|
||||
{
|
||||
new Operation
|
||||
{
|
||||
op = "replace",
|
||||
path = "/name",
|
||||
value = "Gordon"
|
||||
},
|
||||
new Operation
|
||||
{
|
||||
op = "replace",
|
||||
path = "/surname",
|
||||
value = "Freeman"
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
object IExamplesProvider<object>.GetExamples()
|
||||
{
|
||||
return new[]
|
||||
{
|
||||
new Operation
|
||||
{
|
||||
op = "replace",
|
||||
path = "/name",
|
||||
value = "Gordon"
|
||||
},
|
||||
new Operation
|
||||
{
|
||||
op = "replace",
|
||||
path = "/surname",
|
||||
value = "Freeman"
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
}
|
|
@ -20,7 +20,7 @@ using Microsoft.VisualBasic;
|
|||
using DocumentFormat.OpenXml.Spreadsheet;
|
||||
using IRaCIS.Core.Domain.Models;
|
||||
using IRaCIS.Core.Application.ViewModel;
|
||||
using Dicom;
|
||||
using Medallion.Threading;
|
||||
|
||||
namespace IRaCIS.Core.Application.Contracts
|
||||
{
|
||||
|
@ -36,13 +36,14 @@ namespace IRaCIS.Core.Application.Contracts
|
|||
private readonly IRepository<TrialSite> _trialSiteRepository;
|
||||
private readonly IRepository<TrialUser> _trialUserRepository;
|
||||
private readonly IRepository<TrialSiteUser> _trialSiteUserRepository;
|
||||
private readonly IDistributedLockProvider _distributedLockProvider;
|
||||
private readonly ITokenService _tokenService;
|
||||
private readonly IMailVerificationService _mailVerificationService;
|
||||
|
||||
public TrialSiteSurveyService(IRepository<TrialSiteSurvey> trialSiteSurveyRepository, IRepository<TrialUser> trialUserRepository, IRepository<TrialSiteUserSurvey> trialSiteUserSurveyRepository,
|
||||
IRepository<User> userRepository, IRepository<TrialSite> trialSiteRepository,
|
||||
ITokenService tokenService,
|
||||
IMailVerificationService mailVerificationService, IRepository<TrialSiteUser> trialSiteUserRepository)
|
||||
IMailVerificationService mailVerificationService, IRepository<TrialSiteUser> trialSiteUserRepository, IDistributedLockProvider distributedLockProvider)
|
||||
{
|
||||
_trialSiteSurveyRepository = trialSiteSurveyRepository;
|
||||
_trialSiteUserSurveyRepository = trialSiteUserSurveyRepository;
|
||||
|
@ -52,9 +53,9 @@ namespace IRaCIS.Core.Application.Contracts
|
|||
_tokenService = tokenService;
|
||||
_mailVerificationService = mailVerificationService;
|
||||
_trialSiteUserRepository = trialSiteUserRepository;
|
||||
_distributedLockProvider = distributedLockProvider;
|
||||
}
|
||||
|
||||
private object lockObj { get; set; } = new object();
|
||||
|
||||
/// <summary>
|
||||
/// 发送验证码
|
||||
|
@ -503,7 +504,7 @@ namespace IRaCIS.Core.Application.Contracts
|
|||
.WhereIf(surveyQueryDTO.UpdateTimeBegin != null, t => t.UpdateTime >= surveyQueryDTO.UpdateTimeBegin)
|
||||
.WhereIf(surveyQueryDTO.UpdateTimeEnd != null, t => t.UpdateTime <= surveyQueryDTO.UpdateTimeEnd)
|
||||
|
||||
.ProjectTo<TrialSiteSurveyView>(_mapper.ConfigurationProvider);
|
||||
.ProjectTo<TrialSiteSurveyView>(_mapper.ConfigurationProvider,new { isEn_Us =_userInfo.IsEn_Us});
|
||||
|
||||
return await trialSiteSurveyQueryable.ToPagedListAsync(surveyQueryDTO.PageIndex, surveyQueryDTO.PageSize, surveyQueryDTO.SortField, surveyQueryDTO.Asc);
|
||||
}
|
||||
|
@ -792,7 +793,9 @@ namespace IRaCIS.Core.Application.Contracts
|
|||
if (sysUserInfo == null)
|
||||
{
|
||||
|
||||
lock (lockObj)
|
||||
var @lock = _distributedLockProvider.CreateLock($"UserCode");
|
||||
|
||||
using (await @lock.AcquireAsync())
|
||||
{
|
||||
var saveItem = _mapper.Map<User>(item);
|
||||
|
||||
|
@ -972,7 +975,9 @@ namespace IRaCIS.Core.Application.Contracts
|
|||
if (sysUserInfo == null)
|
||||
{
|
||||
|
||||
lock (lockObj)
|
||||
var @lock = _distributedLockProvider.CreateLock($"UserCode");
|
||||
|
||||
using (await @lock.AcquireAsync())
|
||||
{
|
||||
var saveItem = _mapper.Map<User>(item);
|
||||
|
||||
|
|
|
@ -12,6 +12,7 @@ namespace IRaCIS.Core.Application.AutoMapper
|
|||
{
|
||||
public SiteSurveyConfig()
|
||||
{
|
||||
var isEn_Us = false;
|
||||
//编辑
|
||||
CreateMap<TrialSiteSurvey, TrialSiteSurveyAddOrEdit>().ReverseMap();
|
||||
|
||||
|
@ -47,12 +48,12 @@ namespace IRaCIS.Core.Application.AutoMapper
|
|||
|
||||
CreateMap<TrialSiteSurvey, TrialSiteSurveyView>()
|
||||
.ForMember(d => d.TrialSiteAliasName, u => u.MapFrom(s => s.TrialSite.TrialSiteAliasName))
|
||||
.ForMember(d => d.SiteName, u => u.MapFrom(s => s.Site.SiteName))
|
||||
.ForMember(d => d.SiteName, u => u.MapFrom(s => isEn_Us? s.Site.SiteName:s.Site.SiteNameCN))
|
||||
.ForMember(d => d.TrialSiteCode, u => u.MapFrom(s => s.TrialSite.TrialSiteCode));
|
||||
|
||||
CreateMap<TrialSiteSurvey, TrialSiteSurveySelectView>();
|
||||
|
||||
var isEn_Us = false;
|
||||
|
||||
CreateMap<TrialSiteUserSurvey, TrialSiteUserSurveyView>()
|
||||
.ForMember(d => d.UserType, u => u.MapFrom(s => s.UserTypeRole.UserTypeShortName))
|
||||
.ForMember(d => d.UserTypeEnum, u => u.MapFrom(s => s.UserTypeRole.UserTypeEnum));
|
||||
|
|
|
@ -518,7 +518,7 @@ namespace IRaCIS.Core.Application.Contracts
|
|||
public bool IsAutoCreate { get; set; }
|
||||
|
||||
|
||||
public List<TrialCriterionAdditionalAssessmentType> TrialCriterionAdditionalAssessmentTypeList { get; set; } = new List<TrialCriterionAdditionalAssessmentType>();
|
||||
|
||||
|
||||
|
||||
public int ReadingDivisionEnum { get; set; }
|
||||
|
@ -986,7 +986,6 @@ namespace IRaCIS.Core.Application.Contracts
|
|||
/// </summary>
|
||||
public bool IsUrgent { get; set; } = false;
|
||||
|
||||
public List<AddOrUpdateTrialCriterionAdditional> TrialCriterionAdditionalAssessmentTypeList { get; set; }=new List<AddOrUpdateTrialCriterionAdditional>();
|
||||
|
||||
public ReadingDivisionEnum ReadingDivisionEnum { get; set; }
|
||||
|
||||
|
|
|
@ -115,8 +115,9 @@ namespace IRaCIS.Core.Application.Contracts.DTO
|
|||
public string SiteCode { get; set; } = String.Empty;
|
||||
public string City { get; set; } = String.Empty;
|
||||
public string Country { get; set; } = String.Empty;
|
||||
public Guid? HospitalId { get; set; }
|
||||
public Guid? HospitalId { get; set; }
|
||||
|
||||
public string Address { get; set; } = String.Empty;
|
||||
|
||||
public string HospitalName { get; set; } = String.Empty;
|
||||
|
||||
|
|
|
@ -1031,7 +1031,7 @@ namespace IRaCIS.Core.Application
|
|||
.WhereIf(!string.IsNullOrEmpty(inQuery.Code), o => o.TrialCode.Contains(inQuery.Code))
|
||||
.WhereIf(!string.IsNullOrEmpty(inQuery.ResearchProgramNo), o => o.ResearchProgramNo.Contains(inQuery.ResearchProgramNo))
|
||||
.WhereIf(!string.IsNullOrWhiteSpace(inQuery.ExperimentName), o => o.ExperimentName.Contains(inQuery.ExperimentName))
|
||||
.WhereIf(_userInfo.UserTypeEnumInt != (int)UserTypeEnum.SuperAdmin, t => t.TrialUserList.Any(t => t.UserId == _userInfo.Id && t.IsDeleted == false) && t.IsDeleted == false)
|
||||
.WhereIf(_userInfo.UserTypeEnumInt != (int)UserTypeEnum.SuperAdmin && _userInfo.UserTypeEnumInt != (int)UserTypeEnum.Admin, t => t.TrialUserList.Any(t => t.UserId == _userInfo.Id && t.IsDeleted == false) && t.IsDeleted == false)
|
||||
.Select(t => new TrialToBeDoneDto()
|
||||
{
|
||||
TrialId = t.Id,
|
||||
|
|
|
@ -40,7 +40,6 @@ namespace IRaCIS.Core.Application
|
|||
private readonly IRepository<ReadingSystemCriterionDictionary> _readingCriterionDictionaryRepository;
|
||||
private readonly IRepository<ReadingTrialCriterionDictionary> _readingTrialCriterionDictionaryRepository;
|
||||
private readonly IReadingQuestionService iReadingQuestionService;
|
||||
private readonly IRepository<TrialCriterionAdditionalAssessmentType> _trialCriterionAdditionalAssessmentTypeRepository;
|
||||
|
||||
private readonly IRepository<ReadingTaskQuestionAnswer> _readingTaskQuestionAnswer;
|
||||
|
||||
|
@ -65,7 +64,6 @@ namespace IRaCIS.Core.Application
|
|||
IReadingQuestionService iReadingQuestionService,
|
||||
IEasyCachingProvider provider,
|
||||
IOrganInfoService iOrganInfoService,
|
||||
IRepository<TrialCriterionAdditionalAssessmentType> trialCriterionAdditionalAssessmentTypeRepository,
|
||||
IRepository<VisitTask> visitTaskRepository,
|
||||
IRepository<ReadingTableQuestionTrial> readingTableQuestionTrialRepository,
|
||||
IRepository<ReadingTableQuestionAnswer> readingTableQuestionAnswerRepository,
|
||||
|
@ -74,7 +72,6 @@ namespace IRaCIS.Core.Application
|
|||
|
||||
)
|
||||
{
|
||||
_trialCriterionAdditionalAssessmentTypeRepository = trialCriterionAdditionalAssessmentTypeRepository;
|
||||
_trialRepository = trialRepository;
|
||||
|
||||
this._readingCriterionDictionaryRepository = readingCriterionDictionaryRepository;
|
||||
|
@ -188,7 +185,6 @@ namespace IRaCIS.Core.Application
|
|||
trialInfo.ReadingTool = ReadingTool.Dicom;
|
||||
}
|
||||
|
||||
trialInfo.TrialCriterionAdditionalAssessmentTypeList = await _trialCriterionAdditionalAssessmentTypeRepository.Where(t => t.TrialReadingCriterionId == inDto.TrialReadingCriterionId).ToListAsync();
|
||||
|
||||
|
||||
return trialInfo;
|
||||
|
@ -212,23 +208,7 @@ namespace IRaCIS.Core.Application
|
|||
if (trialCriterion.SynchronizeOriginalTime == null)
|
||||
{
|
||||
|
||||
//同步附加评估类型
|
||||
|
||||
if (!await _trialCriterionAdditionalAssessmentTypeRepository.AnyAsync(t => t.TrialReadingCriterionId == inDto.TrialReadingCriterionId))
|
||||
{
|
||||
AdditionalAssessment additional = new AdditionalAssessment();
|
||||
var addList = additional.GetSystemDefeaultAdditionalAssessmentList(trialCriterion.CriterionType);
|
||||
|
||||
foreach (var addItem in addList)
|
||||
{
|
||||
await _trialCriterionAdditionalAssessmentTypeRepository.AddAsync(new TrialCriterionAdditionalAssessmentType()
|
||||
{
|
||||
CriterionType = trialCriterion.CriterionType,
|
||||
TrialReadingCriterionId = inDto.TrialReadingCriterionId,
|
||||
AdditionalAssessmentType = addItem.AdditionalAssessmentType
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
@ -604,72 +584,7 @@ namespace IRaCIS.Core.Application
|
|||
|
||||
});
|
||||
|
||||
//判断是否存在附加评估
|
||||
if (inDto.IsAdditionalAssessment)
|
||||
{
|
||||
#region 存在,就将标准对应的附加评估选项加进去--废弃 修改到同步标准的地方去了,不管存在附加评估与否,都增加附加评估类型
|
||||
//if (!await _trialCriterionAdditionalAssessmentTypeRepository.AnyAsync(t => t.TrialReadingCriterionId == inDto.TrialReadingCriterionId))
|
||||
//{
|
||||
// AdditionalAssessment additional = new AdditionalAssessment();
|
||||
// var addList = additional.GetSystemDefeaultAdditionalAssessmentList(inDto.CriterionType);
|
||||
|
||||
// foreach (var addItem in addList)
|
||||
// {
|
||||
// await _trialCriterionAdditionalAssessmentTypeRepository.AddAsync(new TrialCriterionAdditionalAssessmentType()
|
||||
// {
|
||||
// CriterionType = inDto.CriterionType,
|
||||
// TrialReadingCriterionId = inDto.TrialReadingCriterionId,
|
||||
// AdditionalAssessmentType = addItem.AdditionalAssessmentType
|
||||
// });
|
||||
// }
|
||||
//}
|
||||
#endregion
|
||||
|
||||
|
||||
if (inDto.TrialCriterionAdditionalAssessmentTypeList.All(t => t.IsSelected != true))
|
||||
{
|
||||
//---选择了附加评估,必须勾选附加评估类型
|
||||
throw new BusinessValidationFailedException(_localizer["TrialConfig_AddEvalReq"]);
|
||||
}
|
||||
|
||||
var trialId = _readingQuestionTrialRepository.Where(t => t.ReadingQuestionCriterionTrialId == inDto.TrialReadingCriterionId).Select(t => t.TrialId).FirstOrDefault();
|
||||
|
||||
|
||||
if (inDto.TrialCriterionAdditionalAssessmentTypeList.Count != 0)
|
||||
{
|
||||
foreach (var updateItem in inDto.TrialCriterionAdditionalAssessmentTypeList)
|
||||
{
|
||||
if (updateItem.IsSelected == true)
|
||||
{
|
||||
//添加默认问题
|
||||
AdditionalAssessment additional = new AdditionalAssessment();
|
||||
var addTypeList = additional.GetSystemDefeaultAdditionalAssessmentList(updateItem.CriterionType, updateItem.AdditionalAssessmentType);
|
||||
|
||||
if (!await _readingQuestionTrialRepository.AsQueryable().IgnoreQueryFilters().AnyAsync(t => t.ReadingQuestionCriterionTrialId == updateItem.TrialReadingCriterionId && t.IsAdditional == true))
|
||||
{
|
||||
foreach (var addType in addTypeList)
|
||||
{
|
||||
foreach (var question in addType.AdditionalQuestionList)
|
||||
{
|
||||
question.ReadingQuestionCriterionTrialId = updateItem.TrialReadingCriterionId;
|
||||
question.TrialId = trialId;
|
||||
|
||||
await _readingQuestionTrialRepository.AddAsync(question);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
await _trialCriterionAdditionalAssessmentTypeRepository.UpdatePartialFromQueryAsync(updateItem.Id, t => new TrialCriterionAdditionalAssessmentType() { IsSelected = updateItem.IsSelected });
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
//删除附加问题
|
||||
await _readingQuestionTrialRepository.BatchDeleteNoTrackingAsync(t => t.ReadingQuestionCriterionTrialId == inDto.TrialReadingCriterionId && t.IsAdditional == true);
|
||||
}
|
||||
|
||||
var result = await _readingQuestionCriterionTrialRepository.SaveChangesAsync();
|
||||
|
||||
|
@ -677,67 +592,9 @@ namespace IRaCIS.Core.Application
|
|||
return ResponseOutput.Ok(result);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 获取附加评估选项列表
|
||||
/// </summary>
|
||||
/// <param name="trialReadingCriterionId"></param>
|
||||
/// <returns></returns>
|
||||
[Obsolete]
|
||||
public async Task<List<TrialCriterionAdditionalAssessmentType>> GetTrialCriterionAdditionalAssessmentOptionList(Guid trialReadingCriterionId)
|
||||
{
|
||||
return await _trialCriterionAdditionalAssessmentTypeRepository.Where(t => t.TrialReadingCriterionId == trialReadingCriterionId).ToListAsync();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// 保存附加评估设置 (自动添加 或者删除附加评估问题)
|
||||
/// </summary>
|
||||
/// <param name="updateList"></param>
|
||||
/// <returns></returns>
|
||||
[Obsolete]
|
||||
public async Task<IResponseOutput> SetTrialCriterionAdditionalAssessment(List<AddOrUpdateTrialCriterionAdditional> updateList)
|
||||
{
|
||||
|
||||
if (updateList.Count == 0)
|
||||
{
|
||||
return ResponseOutput.Ok();
|
||||
}
|
||||
|
||||
var trialId = _readingQuestionTrialRepository.Where(t => t.ReadingQuestionCriterionTrialId == updateList.First().TrialReadingCriterionId).Select(t => t.TrialId).FirstOrDefault();
|
||||
|
||||
foreach (var updateItem in updateList)
|
||||
{
|
||||
if (updateItem.IsSelected == true)
|
||||
{
|
||||
//添加默认问题
|
||||
AdditionalAssessment additional = new AdditionalAssessment();
|
||||
var addTypeList = additional.GetSystemDefeaultAdditionalAssessmentList(updateItem.CriterionType, updateItem.AdditionalAssessmentType);
|
||||
|
||||
foreach (var addType in addTypeList)
|
||||
{
|
||||
foreach (var question in addType.AdditionalQuestionList)
|
||||
{
|
||||
question.ReadingQuestionCriterionTrialId = updateItem.TrialReadingCriterionId;
|
||||
question.TrialId = trialId;
|
||||
|
||||
await _readingQuestionTrialRepository.AddAsync(question);
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
//删除附加问题
|
||||
|
||||
await _readingQuestionTrialRepository.BatchDeleteNoTrackingAsync(t => t.ReadingQuestionCriterionTrialId == updateItem.TrialReadingCriterionId && t.IsAdditional == true);
|
||||
}
|
||||
|
||||
await _trialCriterionAdditionalAssessmentTypeRepository.UpdatePartialFromQueryAsync(updateItem.Id, t => new TrialCriterionAdditionalAssessmentType() { IsSelected = updateItem.IsSelected });
|
||||
}
|
||||
|
||||
|
||||
await _readingQuestionTrialRepository.SaveChangesAsync();
|
||||
return ResponseOutput.Ok();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
|
|
|
@ -16,6 +16,7 @@ using Panda.DynamicWebApi.Attributes;
|
|||
using IRaCIS.Core.Application.Auth;
|
||||
using IRaCIS.Application.Services;
|
||||
using IRaCIS.Core.Application.Filter;
|
||||
using Medallion.Threading;
|
||||
|
||||
namespace IRaCIS.Core.Application.Service
|
||||
{
|
||||
|
@ -31,10 +32,11 @@ namespace IRaCIS.Core.Application.Service
|
|||
private readonly IRepository<TrialSiteUserSurvey> _trialSiteSurveyUserRepository;
|
||||
private readonly IRepository<TrialSiteUser> _trialSiteUserRepository;
|
||||
private readonly IMailVerificationService _mailVerificationService;
|
||||
private readonly IDistributedLockProvider _distributedLockProvider;
|
||||
|
||||
public TrialExternalUserService(IRepository<TrialExternalUser> trialExternalUseRepository, IRepository<User> userRepository, IRepository<TrialUser> trialUserRepository,
|
||||
IRepository<TrialSiteUserSurvey> trialSiteSurveyUserRepository, IRepository<TrialSiteUser> trialSiteUserRepository,
|
||||
IMailVerificationService mailVerificationService)
|
||||
IMailVerificationService mailVerificationService, IDistributedLockProvider distributedLockProvider)
|
||||
{
|
||||
_trialExternalUseRepository = trialExternalUseRepository;
|
||||
_userRepository = userRepository;
|
||||
|
@ -43,6 +45,7 @@ namespace IRaCIS.Core.Application.Service
|
|||
_trialSiteUserRepository = trialSiteUserRepository;
|
||||
|
||||
_mailVerificationService = mailVerificationService;
|
||||
_distributedLockProvider = distributedLockProvider;
|
||||
}
|
||||
|
||||
|
||||
|
@ -75,121 +78,125 @@ namespace IRaCIS.Core.Application.Service
|
|||
|
||||
if (addOrEditTrialExternalUser.Id == null)
|
||||
{
|
||||
var existSysUser = await _userRepository.FirstOrDefaultAsync(t => t.EMail == addOrEditTrialExternalUser.Email && t.UserTypeId == addOrEditTrialExternalUser.UserTypeId);
|
||||
var @lock = _distributedLockProvider.CreateLock($"UserCode");
|
||||
|
||||
if (existSysUser != null)
|
||||
using (await @lock.AcquireAsync())
|
||||
{
|
||||
if (existSysUser.LastName != addOrEditTrialExternalUser.LastName || existSysUser.FirstName != addOrEditTrialExternalUser.FirstName)
|
||||
var existSysUser = await _userRepository.FirstOrDefaultAsync(t => t.EMail == addOrEditTrialExternalUser.Email && t.UserTypeId == addOrEditTrialExternalUser.UserTypeId);
|
||||
|
||||
if (existSysUser != null)
|
||||
{
|
||||
//$"该用户在系统中的用户名为:{existSysUser.LastName + " / " + existSysUser.FirstName} 电话:{existSysUser.Phone},与填写信息存在不一致项, 请将界面信息修改为与系统一致,再进行保存",
|
||||
return ResponseOutput.NotOk(_localizer["TrialExternalUser_Inconsistency", existSysUser.LastName + " / " + existSysUser.FirstName, existSysUser.Phone], new { existSysUser.LastName, existSysUser.FirstName, existSysUser.Phone, existSysUser.IsZhiZhun, existSysUser.IsTestUser }, ApiResponseCodeEnum.NeedTips);
|
||||
if (existSysUser.LastName != addOrEditTrialExternalUser.LastName || existSysUser.FirstName != addOrEditTrialExternalUser.FirstName)
|
||||
{
|
||||
//$"该用户在系统中的用户名为:{existSysUser.LastName + " / " + existSysUser.FirstName} 电话:{existSysUser.Phone},与填写信息存在不一致项, 请将界面信息修改为与系统一致,再进行保存",
|
||||
return ResponseOutput.NotOk(_localizer["TrialExternalUser_Inconsistency", existSysUser.LastName + " / " + existSysUser.FirstName, existSysUser.Phone], new { existSysUser.LastName, existSysUser.FirstName, existSysUser.Phone, existSysUser.IsZhiZhun, existSysUser.IsTestUser }, ApiResponseCodeEnum.NeedTips);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
//处理 生成账户
|
||||
|
||||
//处理 生成账户
|
||||
|
||||
if (await _trialExternalUseRepository.AnyAsync(t =>
|
||||
t.Email == addOrEditTrialExternalUser.Email &&
|
||||
t.UserTypeId == addOrEditTrialExternalUser.UserTypeId && t.TrialId == addOrEditTrialExternalUser.TrialId))
|
||||
{
|
||||
//---系统已经存在与列表中填写的邮箱和用户类型相同的账户,请确认。
|
||||
return ResponseOutput.NotOk(_localizer["TrialExternalUser_EmailTypeDuplicate"]);
|
||||
}
|
||||
if (await _trialExternalUseRepository.AnyAsync(t =>
|
||||
t.Email == addOrEditTrialExternalUser.Email &&
|
||||
t.UserTypeId == addOrEditTrialExternalUser.UserTypeId && t.TrialId == addOrEditTrialExternalUser.TrialId))
|
||||
{
|
||||
//---系统已经存在与列表中填写的邮箱和用户类型相同的账户,请确认。
|
||||
return ResponseOutput.NotOk(_localizer["TrialExternalUser_EmailTypeDuplicate"]);
|
||||
}
|
||||
|
||||
|
||||
|
||||
var addEntity = _mapper.Map<TrialExternalUser>(addOrEditTrialExternalUser);
|
||||
var addEntity = _mapper.Map<TrialExternalUser>(addOrEditTrialExternalUser);
|
||||
|
||||
await _trialExternalUseRepository.AddAsync(addEntity);
|
||||
await _trialExternalUseRepository.AddAsync(addEntity);
|
||||
|
||||
|
||||
var existUser = await _userRepository.FirstOrDefaultAsync(t => t.EMail == addOrEditTrialExternalUser.Email && t.UserTypeId == addOrEditTrialExternalUser.UserTypeId);
|
||||
var trialType = await _repository.Where<Trial>(t => t.Id == addOrEditTrialExternalUser.TrialId).Select(t => t.TrialType).FirstOrDefaultAsync();
|
||||
var existUser = await _userRepository.FirstOrDefaultAsync(t => t.EMail == addOrEditTrialExternalUser.Email && t.UserTypeId == addOrEditTrialExternalUser.UserTypeId);
|
||||
var trialType = await _repository.Where<Trial>(t => t.Id == addOrEditTrialExternalUser.TrialId).Select(t => t.TrialType).FirstOrDefaultAsync();
|
||||
|
||||
if (existUser != null)
|
||||
{
|
||||
addEntity.IsSystemUser = true;
|
||||
addEntity.SystemUserId = existUser.Id;
|
||||
if (existUser != null)
|
||||
{
|
||||
addEntity.IsSystemUser = true;
|
||||
addEntity.SystemUserId = existUser.Id;
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
}
|
||||
else
|
||||
{
|
||||
|
||||
//生成账户 并插入
|
||||
//生成账户 并插入
|
||||
|
||||
var generateUser = _mapper.Map<User>(addOrEditTrialExternalUser);
|
||||
var generateUser = _mapper.Map<User>(addOrEditTrialExternalUser);
|
||||
|
||||
if (trialType == TrialType.NoneOfficial)
|
||||
{
|
||||
generateUser.IsTestUser = true;
|
||||
}
|
||||
|
||||
// 外部人员生成账号 都是外部的
|
||||
generateUser.IsZhiZhun = false;
|
||||
|
||||
generateUser.Code = _userRepository.Select(t => t.Code).DefaultIfEmpty().Max() + 1;
|
||||
|
||||
|
||||
generateUser.UserCode = AppSettings.GetCodeStr(generateUser.Code, nameof(User));
|
||||
|
||||
generateUser.UserName = generateUser.UserCode;
|
||||
|
||||
generateUser.UserTypeEnum = _repository.Where<UserType>(t => t.Id == generateUser.UserTypeId).Select(t => t.UserTypeEnum).First();
|
||||
|
||||
generateUser.Password = MD5Helper.Md5("123456");
|
||||
|
||||
generateUser.Status = UserStateEnum.Disable;
|
||||
|
||||
var newAddUser = await _repository.AddAsync(generateUser);
|
||||
|
||||
|
||||
addEntity.IsSystemUser = false;
|
||||
addEntity.SystemUserId = newAddUser.Id;
|
||||
|
||||
|
||||
existUser = newAddUser;
|
||||
|
||||
}
|
||||
|
||||
#region 验证用户 能否加入
|
||||
|
||||
if (trialType == TrialType.OfficialTrial || trialType == TrialType.Training)
|
||||
{
|
||||
|
||||
if (existUser.IsTestUser)
|
||||
{
|
||||
//---正式类型 、培训类型的项目 不允许加入测试用户
|
||||
throw new BusinessValidationFailedException(_localizer["TrialExternalUser_TestUserNotAllowed"]);
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
if (trialType == TrialType.NoneOfficial)
|
||||
{
|
||||
generateUser.IsTestUser = true;
|
||||
|
||||
if (existUser.IsTestUser == false)
|
||||
{
|
||||
//---测试项目 不允许加入正式用户
|
||||
throw new BusinessValidationFailedException(_localizer["TrialExternalUser_FormalUserNotAllowed"]);
|
||||
}
|
||||
}
|
||||
|
||||
// 外部人员生成账号 都是外部的
|
||||
generateUser.IsZhiZhun = false;
|
||||
|
||||
generateUser.Code = _userRepository.Select(t => t.Code).DefaultIfEmpty().Max() + 1;
|
||||
#endregion
|
||||
|
||||
|
||||
generateUser.UserCode = AppSettings.GetCodeStr(generateUser.Code, nameof(User));
|
||||
|
||||
generateUser.UserName = generateUser.UserCode;
|
||||
|
||||
generateUser.UserTypeEnum = _repository.Where<UserType>(t => t.Id == generateUser.UserTypeId).Select(t => t.UserTypeEnum).First();
|
||||
|
||||
generateUser.Password = MD5Helper.Md5("123456");
|
||||
|
||||
generateUser.Status = UserStateEnum.Disable;
|
||||
|
||||
var newAddUser = await _repository.AddAsync(generateUser);
|
||||
await _trialExternalUseRepository.SaveChangesAsync();
|
||||
|
||||
|
||||
addEntity.IsSystemUser = false;
|
||||
addEntity.SystemUserId = newAddUser.Id;
|
||||
|
||||
|
||||
existUser = newAddUser;
|
||||
|
||||
}
|
||||
|
||||
#region 验证用户 能否加入
|
||||
|
||||
if (trialType == TrialType.OfficialTrial || trialType == TrialType.Training)
|
||||
{
|
||||
|
||||
if (existUser.IsTestUser)
|
||||
//添加的时候就发邮件 现在省略
|
||||
if (addOrEditTrialExternalUser.IsSendEmail)
|
||||
{
|
||||
//---正式类型 、培训类型的项目 不允许加入测试用户
|
||||
throw new BusinessValidationFailedException(_localizer["TrialExternalUser_TestUserNotAllowed"]);
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
if (trialType == TrialType.NoneOfficial)
|
||||
{
|
||||
|
||||
if (existUser.IsTestUser == false )
|
||||
{
|
||||
//---测试项目 不允许加入正式用户
|
||||
throw new BusinessValidationFailedException(_localizer["TrialExternalUser_FormalUserNotAllowed"]);
|
||||
}
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
|
||||
await _trialExternalUseRepository.SaveChangesAsync();
|
||||
|
||||
|
||||
//添加的时候就发邮件 现在省略
|
||||
if (addOrEditTrialExternalUser.IsSendEmail)
|
||||
{
|
||||
await SendExternalUserJoinEmail(new TrialExternalUserSendEmail()
|
||||
{
|
||||
BaseUrl = addOrEditTrialExternalUser.BaseUrl,
|
||||
RouteUrl = addOrEditTrialExternalUser.RouteUrl,
|
||||
TrialId = addOrEditTrialExternalUser.TrialId,
|
||||
SendUsers = new List<UserEmail>()
|
||||
await SendExternalUserJoinEmail(new TrialExternalUserSendEmail()
|
||||
{
|
||||
BaseUrl = addOrEditTrialExternalUser.BaseUrl,
|
||||
RouteUrl = addOrEditTrialExternalUser.RouteUrl,
|
||||
TrialId = addOrEditTrialExternalUser.TrialId,
|
||||
SendUsers = new List<UserEmail>()
|
||||
{
|
||||
new UserEmail()
|
||||
{
|
||||
|
@ -199,12 +206,13 @@ namespace IRaCIS.Core.Application.Service
|
|||
SystemUserId=addEntity.SystemUserId
|
||||
}
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
return ResponseOutput.Ok(addEntity.Id.ToString());
|
||||
}
|
||||
|
||||
|
||||
return ResponseOutput.Ok(addEntity.Id.ToString());
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
|
|
|
@ -25,13 +25,17 @@ namespace IRaCIS.Application.Services
|
|||
private readonly IRepository<TrialUser> _trialUserRepository;
|
||||
private readonly IOptionsMonitor<ServiceVerifyConfigOption> _verifyConfig;
|
||||
|
||||
private readonly IOptionsMonitor<SystemEmailSendConfig> _systemEmailSendConfig;
|
||||
|
||||
public bool TrialExpeditedChange { get; set; } = false;
|
||||
|
||||
|
||||
public TrialService(IEasyCachingProvider provider, IRepository<Trial> trialRepository,
|
||||
IRepository<TrialUser> trialUserRepository, IOptionsMonitor<ServiceVerifyConfigOption> verifyConfig
|
||||
, IOptionsMonitor<SystemEmailSendConfig> systemEmailSendConfig
|
||||
)
|
||||
{
|
||||
_systemEmailSendConfig = systemEmailSendConfig;
|
||||
_verifyConfig = verifyConfig;
|
||||
_provider = provider;
|
||||
_trialRepository = trialRepository;
|
||||
|
@ -92,7 +96,7 @@ namespace IRaCIS.Application.Services
|
|||
.WhereIf(multiCriteriaSelectCount > 0, t => t.TrialDicList.Count(t => t.KeyName == StaticData.Criterion) == multiCriteriaSelectCount)
|
||||
.WhereIf(multiReviewTypeSelectCount > 0, t => t.TrialDicList.Count(t => t.KeyName == StaticData.ReviewType) == multiReviewTypeSelectCount)
|
||||
.WhereIf(_userInfo.UserTypeEnumInt != (int)UserTypeEnum.SuperAdmin, t => t.TrialUserList.Any(t => t.UserId == _userInfo.Id && t.IsDeleted == false) && t.IsDeleted == false)
|
||||
.ProjectTo<TrialDetailDTO>(_mapper.ConfigurationProvider, new { userTypeEnumInt = _userInfo.UserTypeEnumInt, userId = _userInfo.Id });
|
||||
.ProjectTo<TrialDetailDTO>(_mapper.ConfigurationProvider, new { userTypeEnumInt = _userInfo.UserTypeEnumInt, userId = _userInfo.Id , isEn_Us= _userInfo.IsEn_Us });
|
||||
|
||||
return await query.ToPagedListAsync(searchParam.PageIndex, searchParam.PageSize, string.IsNullOrWhiteSpace(searchParam.SortField) ? "CreateTime" : searchParam.SortField, searchParam.Asc);
|
||||
|
||||
|
@ -118,7 +122,7 @@ namespace IRaCIS.Application.Services
|
|||
[HttpGet("{projectId:guid}")]
|
||||
public async Task<TrialDetailDTO> GetTrialInfoAndLockState(Guid projectId)
|
||||
{
|
||||
return (await _trialRepository.Where(o => o.Id == projectId).IgnoreQueryFilters().ProjectTo<TrialDetailDTO>(_mapper.ConfigurationProvider).FirstOrDefaultAsync()).IfNullThrowException();
|
||||
return (await _trialRepository.Where(o => o.Id == projectId).IgnoreQueryFilters().ProjectTo<TrialDetailDTO>(_mapper.ConfigurationProvider, new {isEn_Us = _userInfo.IsEn_Us }).FirstOrDefaultAsync()).IfNullThrowException();
|
||||
|
||||
}
|
||||
|
||||
|
@ -213,6 +217,15 @@ namespace IRaCIS.Application.Services
|
|||
await _repository.AddAsync(new VisitStage { TrialId = trial.Id, VisitNum = 0, BlindName = "B" + 0.ToString("D3"), VisitDay = 0, VisitName = "Baseline", IsBaseLine = true });
|
||||
await _repository.AddAsync(new VisitStage { TrialId = trial.Id, VisitNum = 1, BlindName = "B" + 10.ToString("D3"), VisitDay = 30, VisitName = "Visit 1" });
|
||||
|
||||
//默认采用系统邮件
|
||||
|
||||
trial.EmailAuthorizationCode = _systemEmailSendConfig.CurrentValue.AuthorizationCode;
|
||||
trial.EmailFromEmail = _systemEmailSendConfig.CurrentValue.FromEmail;
|
||||
trial.EmailFromName = _systemEmailSendConfig.CurrentValue.FromName;
|
||||
trial.EmailSMTPServerAddress = _systemEmailSendConfig.CurrentValue.Host;
|
||||
trial.EmailSMTPServerPort = _systemEmailSendConfig.CurrentValue.Port;
|
||||
trial.IsConfigureEmail = true;
|
||||
|
||||
|
||||
var success = await _repository.SaveChangesAsync();
|
||||
|
||||
|
@ -286,8 +299,16 @@ namespace IRaCIS.Application.Services
|
|||
|
||||
await _repository.BatchDeleteAsync<CheckChallengeDialog>(o => o.SubjectVisit.TrialId == trialId);
|
||||
await _repository.BatchDeleteAsync<ClinicalDataTrialSet>(o => o.TrialId == trialId);
|
||||
|
||||
await _repository.BatchDeleteAsync<ClinicalQuestionAnswer>(o => o.ClinicalForm.TrialId == trialId);
|
||||
await _repository.BatchDeleteAsync<ClinicalQuestionAnswer>(o => o.ClinicalForm.TrialId == trialId);
|
||||
await _repository.BatchDeleteAsync<ClinicalForm>(o => o.TrialId == trialId);
|
||||
|
||||
await _repository.BatchDeleteAsync<UserUploadFile>(o => o.TrialId == trialId);
|
||||
await _repository.BatchDeleteAsync<CriterionNidusSystem>(o => o.TrialReadingCriterion.TrialId == trialId);
|
||||
|
||||
await _repository.BatchDeleteAsync<CriterionNidusTrial>(o => o.TrialReadingCriterion.TrialId == trialId);
|
||||
|
||||
await _repository.BatchDeleteAsync<DataInspection>(o => o.TrialId == trialId);
|
||||
await _repository.BatchDeleteAsync<DicomStudy>(t => t.TrialId == trialId);
|
||||
await _repository.BatchDeleteAsync<StudyMonitor>(t => t.TrialId == trialId);
|
||||
|
@ -374,8 +395,7 @@ namespace IRaCIS.Application.Services
|
|||
await _repository.BatchDeleteAsync<TrialQCQuestion>(t => t.TrialId == trialId);
|
||||
await _repository.BatchDeleteAsync<TrialQCQuestionAnswer>(t => t.TrialId == trialId);
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
await _repository.BatchDeleteAsync<TrialSign>(t => t.TrialId == trialId);
|
||||
|
|
|
@ -194,7 +194,7 @@ namespace IRaCIS.Core.Application.Services
|
|||
|
||||
|
||||
var siteQueryable = _siteRepository.AsQueryable(true)
|
||||
.WhereIf(!string.IsNullOrWhiteSpace(searchModel.SiteName), t => t.SiteName.Contains(searchModel.SiteName))
|
||||
.WhereIf(!string.IsNullOrWhiteSpace(searchModel.SiteName), t => t.SiteName.Contains(searchModel.SiteName)|| t.SiteNameCN.Contains(searchModel.SiteName))
|
||||
.WhereIf(!string.IsNullOrWhiteSpace(searchModel.AliasName), t => t.AliasName.Contains(searchModel.AliasName))
|
||||
.WhereIf(!string.IsNullOrWhiteSpace(searchModel.City), t => t.City.Contains(searchModel.City))
|
||||
.WhereIf(!string.IsNullOrWhiteSpace(searchModel.Country), t => t.Country.Contains(searchModel.Country))
|
||||
|
|
|
@ -65,16 +65,17 @@ namespace IRaCIS.Core.Application.Service
|
|||
|
||||
var userId = Guid.Empty;
|
||||
var userTypeEnumInt = 0;
|
||||
var isEn_Us = false;
|
||||
CreateMap<Trial, TrialDetailDTO>()
|
||||
.ForMember(x=>x.CriterionList,y=>y.MapFrom(z=>z.ReadingQuestionCriterionTrialList.Where(n=>n.IsConfirm).Select(m=>m.CriterionName)))
|
||||
.ForMember(d => d.DictionaryList, u => u.MapFrom(s => s.TrialDicList.Select(t => t.Dictionary).OrderBy(t => t.ShowOrder)))
|
||||
//.ForMember(d => d.Code, u => u.MapFrom(s => s.TrialCode))
|
||||
.ForMember(d => d.Sponsor, u => u.MapFrom(s => s.Sponsor.SponsorName))
|
||||
.ForMember(d => d.Phase, u => u.MapFrom(s => s.Phase.MappedValue))
|
||||
.ForMember(d => d.Phase, u => u.MapFrom(s => isEn_Us? s.Phase.Value: s.Phase.ValueCN))
|
||||
//.ForMember(d => d.DeclarationType, u => u.MapFrom(s => s.DeclarationType.MappedValue))
|
||||
.ForMember(d => d.IndicationType, u => u.MapFrom(s => s.IndicationType.MappedValue))
|
||||
.ForMember(d => d.IndicationType, u => u.MapFrom(s => isEn_Us ? s.IndicationType.Value:s.IndicationType.ValueCN))
|
||||
.ForMember(d => d.CRO, u => u.MapFrom(s => s.CRO.CROName))
|
||||
.ForMember(d => d.ReviewMode, u => u.MapFrom(s => s.ReviewMode.MappedValue))
|
||||
.ForMember(d => d.ReviewMode, u => u.MapFrom(s => isEn_Us ? s.ReviewMode.Value:s.ReviewMode.ValueCN))
|
||||
//.ForMember(d => d.ReviewType, u => u.MapFrom(s => s.ReviewType.Value))
|
||||
|
||||
//.ForMember(d => d.SiteCount, u => u.MapFrom(s => userTypeEnumInt == (int)UserTypeEnum.ClinicalResearchCoordinator ? s.TrialSiteUserList.Count(k => k.UserId == userId) : s.TrialSiteList.Count()))
|
||||
|
@ -106,12 +107,10 @@ namespace IRaCIS.Core.Application.Service
|
|||
.ForMember(d => d.TrialId, u => u.MapFrom(s => trialId))
|
||||
.ForMember(d => d.IsSelect, u => u.MapFrom(t => t.UserTrials.Any(t => t.TrialId == trialId)));
|
||||
|
||||
|
||||
CreateMap<Site, SiteSelectDTO>()
|
||||
.ForMember(d => d.HospitalName, u => u.MapFrom(s => s.Hospital.HospitalName));
|
||||
|
||||
//trial site 选择列表 subjectVisit pannel 模式添加的时候
|
||||
var isEn_Us = false;
|
||||
|
||||
CreateMap<Site, TrialSiteScreeningDTO>()
|
||||
.ForMember(d => d.IsSelect, u => u.MapFrom(s => s.TrialSiteList.Any(k => k.TrialId == trialId)))
|
||||
|
|
|
@ -1,15 +1,19 @@
|
|||
using IRaCIS.Core.Application.Service;
|
||||
using DocumentFormat.OpenXml.Office2010.Excel;
|
||||
using IRaCIS.Core.Application.Service;
|
||||
using IRaCIS.Core.Application.ViewModel;
|
||||
using IRaCIS.Core.Domain.Share;
|
||||
using IRaCIS.Core.Infrastructure;
|
||||
using MassTransit;
|
||||
using Medallion.Threading;
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Hosting;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.Extensions.Caching.Distributed;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using Microsoft.Extensions.Options;
|
||||
using MiniExcelLibs;
|
||||
using System.Linq.Expressions;
|
||||
using System.Reflection.Metadata;
|
||||
using System.Security.Cryptography;
|
||||
using System.Text;
|
||||
using System.Text.RegularExpressions;
|
||||
|
@ -20,6 +24,8 @@ namespace IRaCIS.Application.Services
|
|||
[ApiExplorerSettings(GroupName = "Institution")]
|
||||
public class TestService : BaseService
|
||||
{
|
||||
|
||||
public static int IntValue = 100;
|
||||
private readonly IRepository<Dictionary> _dicRepository;
|
||||
private readonly IRepository<Trial> _trialRepository;
|
||||
|
||||
|
@ -30,10 +36,13 @@ namespace IRaCIS.Application.Services
|
|||
private readonly IOptionsMonitor<ServiceVerifyConfigOption> _basicConfig;
|
||||
private readonly IRepository<VisitTask> _visitTaskRepositoryy;
|
||||
|
||||
private readonly IDistributedLockProvider _distributedLockProvider;
|
||||
|
||||
public TestService(IRepository<Dictionary> dicRepository, IRepository<Trial> trialRepository/*, IDistributedCache cache*/
|
||||
private readonly ILogger<TestService> _logger;
|
||||
|
||||
, IOptionsMonitor<SystemEmailSendConfig> systemEmailConfig, IOptionsMonitor<ServiceVerifyConfigOption> basicConfig, IRepository<VisitTask> visitTaskRepository)
|
||||
public TestService(IRepository<Dictionary> dicRepository, IRepository<Trial> trialRepository,ILogger<TestService> logger
|
||||
|
||||
, IOptionsMonitor<SystemEmailSendConfig> systemEmailConfig, IOptionsMonitor<ServiceVerifyConfigOption> basicConfig, IRepository<VisitTask> visitTaskRepository, IDistributedLockProvider distributedLockProvider)
|
||||
{
|
||||
_visitTaskRepositoryy = visitTaskRepository;
|
||||
|
||||
|
@ -42,10 +51,39 @@ namespace IRaCIS.Application.Services
|
|||
|
||||
_dicRepository = dicRepository;
|
||||
_trialRepository = trialRepository;
|
||||
|
||||
_distributedLockProvider= distributedLockProvider;
|
||||
|
||||
_logger= logger;
|
||||
//_cache = cache;
|
||||
}
|
||||
|
||||
|
||||
|
||||
[AllowAnonymous]
|
||||
public async Task<IResponseOutput> TestDistributedLock( )
|
||||
{
|
||||
|
||||
_repository.Where<User>().Select(t => t.FullName).FirstOrDefault();
|
||||
|
||||
Console.WriteLine($"我进来了当前值是:" + IntValue);
|
||||
_logger.LogWarning($"我进来了当前值是:" + IntValue);
|
||||
|
||||
var @lock = _distributedLockProvider.CreateLock($"UserAccount");
|
||||
|
||||
using (await @lock.AcquireAsync())
|
||||
{
|
||||
await Task.Delay(4);
|
||||
IntValue--;
|
||||
|
||||
_logger.LogWarning( IntValue.ToString());
|
||||
Console.WriteLine(IntValue);
|
||||
}
|
||||
|
||||
return ResponseOutput.Ok(IntValue);
|
||||
}
|
||||
|
||||
|
||||
[AllowAnonymous]
|
||||
public async Task<IResponseOutput> GetMemoryStoreData()
|
||||
{
|
||||
|
|
|
@ -22,14 +22,13 @@ namespace IRaCIS.Core.Application.Triggers
|
|||
|
||||
private readonly IRepository<ReadingTaskQuestionAnswer> _readingTaskQuestionAnswerRepository;
|
||||
|
||||
private readonly IRepository<SubjectAdditionalEvaluationResult> _subjectAdditionalEvaluationResultRepository;
|
||||
|
||||
|
||||
|
||||
public VisitTaskIsFrontTaskNeedSignButNotSignTrigger(
|
||||
|
||||
IRepository<VisitTask> visitTaskRepository, IRepository<ReadingQuestionCriterionTrial> trialReadingCriterionRepository, IRepository<ReadingQuestionTrial> trialReadingQuestionRepository
|
||||
, IRepository<ReadingTaskQuestionAnswer> readingTaskQuestionAnswerRepository, IRepository<SubjectAdditionalEvaluationResult> subjectAdditionalEvaluationResultRepository)
|
||||
, IRepository<ReadingTaskQuestionAnswer> readingTaskQuestionAnswerRepository)
|
||||
{
|
||||
_trialReadingCriterionRepository = trialReadingCriterionRepository;
|
||||
|
||||
|
@ -37,7 +36,6 @@ namespace IRaCIS.Core.Application.Triggers
|
|||
_trialReadingQuestionRepository = trialReadingQuestionRepository;
|
||||
|
||||
_readingTaskQuestionAnswerRepository = readingTaskQuestionAnswerRepository;
|
||||
_subjectAdditionalEvaluationResultRepository = subjectAdditionalEvaluationResultRepository;
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -8,8 +8,4 @@
|
|||
<OutputPath>..\bin</OutputPath>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.AspNetCore.Http.Abstractions" Version="2.2.0" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
@ -35,6 +35,8 @@ namespace IRaCIS.Core.Domain.Models
|
|||
|
||||
public string NotAgreeReason { get; set; } = string.Empty;
|
||||
|
||||
public PIAuditState? PIAuditState { get; set; }
|
||||
|
||||
|
||||
public string PIAuditImagePath { get; set; } = string.Empty;
|
||||
|
||||
|
|
|
@ -178,7 +178,7 @@ namespace IRaCIS.Core.Domain.Models
|
|||
/// 文件
|
||||
/// </summary>
|
||||
[NotMapped]
|
||||
public List<ImageInfo> FileList
|
||||
public List<OSSImageInfo> FileList
|
||||
{
|
||||
get
|
||||
{
|
||||
|
@ -186,13 +186,13 @@ namespace IRaCIS.Core.Domain.Models
|
|||
|
||||
try
|
||||
{
|
||||
var result= JsonConvert.DeserializeObject<List<ImageInfo>>(this.ImagePath);
|
||||
return result==null?new List<ImageInfo>() : result;
|
||||
var result= JsonConvert.DeserializeObject<List<OSSImageInfo>>(this.ImagePath);
|
||||
return result==null?new List<OSSImageInfo>() : result;
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
|
||||
return new List<ImageInfo>();
|
||||
return new List<OSSImageInfo>();
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -210,7 +210,7 @@ namespace IRaCIS.Core.Domain.Models
|
|||
|
||||
#region 文件对象
|
||||
|
||||
public class ImageInfo
|
||||
public class OSSImageInfo
|
||||
{
|
||||
public string FileName { get; set; }
|
||||
|
||||
|
|
|
@ -1,4 +1,3 @@
|
|||
using EntityFrameworkCore.Projectables;
|
||||
using IRaCIS.Core.Domain.Share;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
|
@ -56,12 +55,6 @@ namespace IRaCIS.Core.Domain.Models
|
|||
public List<Dictionary> ChildList { get; set; } = new List<Dictionary>();
|
||||
|
||||
|
||||
[NotMapped]
|
||||
public string MappedValue { get; set; }
|
||||
|
||||
|
||||
[Projectable]
|
||||
public string TranslateValue( string value, string valueCN,bool isCN) => isCN?valueCN:value;
|
||||
|
||||
|
||||
}
|
||||
|
|
|
@ -1,29 +1,27 @@
|
|||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFramework>net6.0</TargetFramework>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup>
|
||||
<TargetFramework>net6.0</TargetFramework>
|
||||
</PropertyGroup>
|
||||
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|AnyCPU'">
|
||||
<OutputPath>..\bin</OutputPath>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|AnyCPU'">
|
||||
<OutputPath>..\bin</OutputPath>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="EntityFrameworkCore.Projectables.Abstractions" Version="2.3.0" />
|
||||
<PackageReference Include="Microsoft.Extensions.Configuration.Binder" Version="6.0.0" />
|
||||
<PackageReference Include="Microsoft.Extensions.Configuration.Json" Version="6.0.0" />
|
||||
<PackageReference Include="Newtonsoft.Json" Version="13.0.1" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\IRaCIS.Core.Domain.Share\IRaCIS.Core.Domain.Share.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\IRaCIS.Core.Domain.Share\IRaCIS.Core.Domain.Share.csproj" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<PackageReference Include="EntityFrameworkCore.Projectables.Abstractions" Version="2.3.0" />
|
||||
<PackageReference Include="Newtonsoft.Json" Version="13.0.3" />
|
||||
<PackageReference Include="Microsoft.Extensions.Configuration.Binder" Version="7.0.4" />
|
||||
<PackageReference Include="Microsoft.Extensions.Configuration.Json" Version="7.0.0" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<Using Include=" Newtonsoft.Json;" />
|
||||
<!-- Global using -->
|
||||
|
||||
|
||||
<ItemGroup>
|
||||
<Using Include=" Newtonsoft.Json;" />
|
||||
<!-- Global using -->
|
||||
|
||||
</ItemGroup>
|
||||
</ItemGroup>
|
||||
</Project>
|
||||
|
|
|
@ -87,7 +87,8 @@ namespace IRaCIS.Core.Domain.Models
|
|||
/// </summary>
|
||||
public bool AutoCutNextTask { get; set; } = false;
|
||||
|
||||
[Projectable] public string FullName => LastName + " / " + FirstName;
|
||||
[Projectable]
|
||||
public string FullName => LastName + " / " + FirstName;
|
||||
|
||||
//[Projectable] public string FullName => $"{LastName} / {FirstName}";
|
||||
}
|
||||
|
|
|
@ -1,79 +0,0 @@
|
|||
|
||||
//--------------------------------------------------------------------
|
||||
// 此代码由T4模板自动生成 byzhouhang 20210918
|
||||
// 生成时间 2023-03-17 11:50:31
|
||||
// 对此文件的更改可能会导致不正确的行为,并且如果重新生成代码,这些更改将会丢失。
|
||||
using System;
|
||||
using IRaCIS.Core.Domain.Share;
|
||||
using System.ComponentModel.DataAnnotations;
|
||||
using System.ComponentModel.DataAnnotations.Schema;
|
||||
namespace IRaCIS.Core.Domain.Models
|
||||
{
|
||||
///<summary>
|
||||
///SubjectAdditionalEvaluationResult
|
||||
///</summary>
|
||||
[Table("SubjectAdditionalEvaluationResult")]
|
||||
public class SubjectAdditionalEvaluationResult : Entity, IAuditUpdate, IAuditAdd
|
||||
{
|
||||
|
||||
|
||||
[JsonIgnore]
|
||||
[ForeignKey("TrialReadingQuestionId")]
|
||||
public ReadingQuestionTrial TrialReadingQuestion { get; set; }
|
||||
|
||||
|
||||
public Guid TrialReadingQuestionId { get; set; }
|
||||
|
||||
|
||||
|
||||
|
||||
public Guid SubjectId { get; set; }
|
||||
|
||||
|
||||
public Guid TrialReadingCriterionId { get; set; }
|
||||
|
||||
|
||||
public DateTime CreateTime { get; set; }
|
||||
|
||||
|
||||
public Guid CreateUserId { get; set; }
|
||||
|
||||
|
||||
public Guid UpdateUserId { get; set; }
|
||||
|
||||
|
||||
public DateTime UpdateTime { get; set; }
|
||||
|
||||
|
||||
public Guid? VisitTaskId { get; set; }
|
||||
|
||||
|
||||
public string Answer { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// 附加评估答案翻译字典
|
||||
/// </summary>
|
||||
[Required]
|
||||
public string TranslateDictionaryCode { get; set; }=string.Empty;
|
||||
|
||||
/// <summary>
|
||||
/// 是否是最终结果
|
||||
/// </summary>
|
||||
[Required]
|
||||
public bool IsFinalResult { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// 最终结果
|
||||
/// </summary>
|
||||
[Required]
|
||||
public string FinalAnswer { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// 最终结果翻字典
|
||||
/// </summary>
|
||||
[Required]
|
||||
public string FinalTranslateDictionaryCode { get; set; }
|
||||
|
||||
}
|
||||
|
||||
}
|
|
@ -113,7 +113,7 @@ namespace IRaCIS.Core.Domain.Models
|
|||
/// 文件
|
||||
/// </summary>
|
||||
[NotMapped]
|
||||
public List<ImageInfo> FileList
|
||||
public List<OSSImageInfo> FileList
|
||||
{
|
||||
get
|
||||
{
|
||||
|
@ -121,13 +121,13 @@ namespace IRaCIS.Core.Domain.Models
|
|||
|
||||
try
|
||||
{
|
||||
var result = JsonConvert.DeserializeObject<List<ImageInfo>>(this.ImagePath);
|
||||
return result == null ? new List<ImageInfo>() : result;
|
||||
var result = JsonConvert.DeserializeObject<List<OSSImageInfo>>(this.ImagePath);
|
||||
return result == null ? new List<OSSImageInfo>() : result;
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
|
||||
return new List<ImageInfo>();
|
||||
return new List<OSSImageInfo>();
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -15,11 +15,14 @@ namespace IRaCIS.Core.Domain.Models
|
|||
[Table("CriterionNidusTrial")]
|
||||
public class CriterionNidusTrial : Entity, IAuditAdd
|
||||
{
|
||||
|
||||
/// <summary>
|
||||
[JsonIgnore]
|
||||
[ForeignKey("CriterionId")]
|
||||
public ReadingQuestionCriterionTrial TrialReadingCriterion { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// CriterionId
|
||||
/// </summary>
|
||||
[Required]
|
||||
[Required]
|
||||
public Guid CriterionId { get; set; }
|
||||
|
||||
/// <summary>
|
||||
|
|
|
@ -264,9 +264,7 @@ namespace IRaCIS.Core.Domain.Models
|
|||
|
||||
public List<ReadingQuestionTrial> ReadingQuestionTrialList = new List<ReadingQuestionTrial>();
|
||||
|
||||
[JsonIgnore]
|
||||
|
||||
public List<TrialCriterionAdditionalAssessmentType> TrialCriterionAdditionalAssessmentTypeList { get; set; } = new List<TrialCriterionAdditionalAssessmentType>();
|
||||
|
||||
|
||||
[JsonIgnore]
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
--医生相关
|
||||
DROP TABLE Attachment;
|
||||
DROP TABLE Doctor;
|
||||
DROP TABLE DoctorPayInformation
|
||||
DROP TABLE Postgraduate;
|
||||
DROP TABLE Education;
|
||||
DROP TABLE ResearchPublication;
|
||||
|
@ -9,6 +10,8 @@ DROP TABLE Vacation;
|
|||
DROP TABLE DoctorCriterionFile;
|
||||
DROP TABLE DoctorDictionary;
|
||||
|
||||
DROP TABLE TrialExperienceCriteria
|
||||
|
||||
|
||||
|
||||
--费用相关
|
||||
|
@ -22,6 +25,10 @@ DROP TABLE TrialRevenuesPrice;
|
|||
DROP TABLE TrialRevenuesPriceVerification;
|
||||
DROP TABLE VolumeReward;
|
||||
|
||||
--new
|
||||
DROP TABLE Payment
|
||||
DROP TABLE PaymentDetail
|
||||
|
||||
|
||||
--工作量
|
||||
DROP TABLE [Workload];
|
||||
|
@ -48,6 +55,11 @@ DROP TABLE SubjectCriteriaEvaluation;
|
|||
DROP TABLE SubjectCriteriaEvaluationVisitFilter;
|
||||
DROP TABLE SubjectCriteriaEvaluationVisitStudyFilter;
|
||||
|
||||
--new
|
||||
DROP TABLE SubjectAdditionalEvaluationResult
|
||||
DROP TABLE TrialCriterionAdditionalAssessmentType
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
|
|
@ -26,11 +26,6 @@ namespace IRaCIS.Core.Domain.Models
|
|||
|
||||
|
||||
|
||||
[JsonIgnore]
|
||||
|
||||
public List<SubjectAdditionalEvaluationResult> SubjectAdditionalEvaluationResult { get; set; }
|
||||
|
||||
|
||||
[JsonIgnore]
|
||||
public List<ReadingTaskQuestionAnswer> ReadingTaskQuestionAnswerList { get; set; }
|
||||
|
||||
|
|
|
@ -212,7 +212,7 @@ namespace IRaCIS.Core.Domain.Share
|
|||
get
|
||||
{
|
||||
|
||||
return _accessor?.HttpContext?.Connection.RemoteIpAddress.ToString();
|
||||
return _accessor?.HttpContext.GetClientIP();
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -341,4 +341,33 @@ namespace IRaCIS.Core.Domain.Share
|
|||
|
||||
|
||||
}
|
||||
|
||||
public static class HttpContextExtension
|
||||
{
|
||||
public static string GetClientIP(this HttpContext context)
|
||||
{
|
||||
var ip = context.Request.Headers["Cdn-Src-Ip"].FirstOrDefault();
|
||||
if (!string.IsNullOrEmpty(ip))
|
||||
return IpReplace(ip);
|
||||
|
||||
ip = context.Request.Headers["X-Forwarded-For"].FirstOrDefault();
|
||||
if (!string.IsNullOrEmpty(ip))
|
||||
return IpReplace(ip);
|
||||
|
||||
ip = context.Connection.RemoteIpAddress.ToString();
|
||||
|
||||
return IpReplace(ip);
|
||||
}
|
||||
|
||||
static string IpReplace(string inip)
|
||||
{
|
||||
//::ffff:
|
||||
//::ffff:192.168.2.131 这种IP处理
|
||||
if (inip.Contains("::ffff:"))
|
||||
{
|
||||
inip = inip.Replace("::ffff:", "");
|
||||
}
|
||||
return inip;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -249,10 +249,6 @@ namespace IRaCIS.Core.Infra.EFCore.Common
|
|||
dicValueList = await _dbContext.Dictionary.Where(t => dicIdList.Contains(t.Id)).Select(t => t.Value).ToListAsync();
|
||||
}
|
||||
|
||||
// 附加评估
|
||||
|
||||
var addtionalAssesementList = await _dbContext.TrialCriterionAdditionalAssessmentType.Where(t => t.TrialReadingCriterionId == entity.Id && t.IsSelected != null)
|
||||
.Select(t => new { t.AdditionalAssessmentType, t.IsSelected }).ToListAsync();
|
||||
|
||||
|
||||
await InsertInspection<ReadingQuestionCriterionTrial>(entity, type, x => new InspectionConvertDTO()
|
||||
|
@ -268,7 +264,7 @@ namespace IRaCIS.Core.Infra.EFCore.Common
|
|||
}, new
|
||||
{
|
||||
EvaluationResultTypes = dicValueList.Count > 0 ? string.Join(",", dicValueList) : string.Empty,
|
||||
AdditionalAssessmentTypeList = addtionalAssesementList
|
||||
|
||||
});
|
||||
}
|
||||
|
||||
|
|
|
@ -122,14 +122,15 @@ namespace IRaCIS.Core.Infra.EFCore
|
|||
|
||||
|
||||
modelBuilder.Entity<Dictionary>().HasMany(t => t.ChildList).WithOne(t => t.Parent);
|
||||
if (_userInfo.IsEn_Us)
|
||||
{
|
||||
modelBuilder.Entity<Dictionary>().Property(t => t.MappedValue).HasColumnName(nameof(Domain.Models.Dictionary.Value));
|
||||
}
|
||||
else
|
||||
{
|
||||
modelBuilder.Entity<Dictionary>().Property(t => t.MappedValue).HasColumnName(nameof(Domain.Models.Dictionary.ValueCN));
|
||||
}
|
||||
|
||||
//if (_userInfo.IsEn_Us)
|
||||
//{
|
||||
// modelBuilder.Entity<Dictionary>().Property(t => t.MappedValue).HasColumnName(nameof(Domain.Models.Dictionary.Value));
|
||||
//}
|
||||
//else
|
||||
//{
|
||||
// modelBuilder.Entity<Dictionary>().Property(t => t.MappedValue).HasColumnName(nameof(Domain.Models.Dictionary.ValueCN));
|
||||
//}
|
||||
|
||||
|
||||
//遍历实体模型手动配置
|
||||
|
@ -260,10 +261,8 @@ namespace IRaCIS.Core.Infra.EFCore
|
|||
|
||||
public virtual DbSet<TrialClinicalDataSetCriterion> TrialClinicalDataSetCriterion { get; set; }
|
||||
|
||||
public virtual DbSet<TrialCriterionAdditionalAssessmentType> TrialCriterionAdditionalAssessmentType { get; set; }
|
||||
|
||||
|
||||
public virtual DbSet<SubjectAdditionalEvaluationResult> SubjectAdditionalEvaluationResult { get; set; }
|
||||
|
||||
|
||||
|
||||
|
@ -513,54 +512,60 @@ namespace IRaCIS.Core.Infra.EFCore
|
|||
}
|
||||
catch (UniqueConstraintException ex)
|
||||
{
|
||||
_logger.LogError(ex.Message);
|
||||
_logger.LogError(ex.InnerException is null? ex.Message :ex.InnerException?.Message);
|
||||
|
||||
throw new DBSaveFailedException("该唯一键已经存在于数据库中。");
|
||||
|
||||
}
|
||||
catch (TimeoutException ex)
|
||||
{
|
||||
_logger.LogError(ex.Message);
|
||||
_logger.LogError(ex.InnerException is null ? ex.Message : ex.InnerException?.Message);
|
||||
|
||||
throw new DBSaveFailedException("数据库操作已经超时,请稍后重试。");
|
||||
|
||||
}
|
||||
catch (CannotInsertNullException ex)
|
||||
{
|
||||
_logger.LogError(ex.Message);
|
||||
_logger.LogError(ex.InnerException is null ? ex.Message : ex.InnerException?.Message);
|
||||
|
||||
throw new DBSaveFailedException("无法在非空列上插入空值。");
|
||||
}
|
||||
catch (MaxLengthExceededException ex)
|
||||
{
|
||||
_logger.LogError(ex.Message);
|
||||
_logger.LogError(ex.InnerException is null ? ex.Message : ex.InnerException?.Message);
|
||||
|
||||
throw new DBSaveFailedException("字符串超过了数据库列的最大长度。");
|
||||
}
|
||||
catch (NumericOverflowException ex)
|
||||
{
|
||||
_logger.LogError(ex.Message);
|
||||
|
||||
_logger.LogError(ex.InnerException is null ? ex.Message : ex.InnerException?.Message);
|
||||
throw new DBSaveFailedException("数值超过了数据类型的范围。");
|
||||
}
|
||||
catch (SyntaxErrorException ex)
|
||||
{
|
||||
_logger.LogError(ex.Message);
|
||||
_logger.LogError(ex.InnerException is null ? ex.Message : ex.InnerException?.Message);
|
||||
|
||||
throw new DBSaveFailedException("SQL 查询中存在语法错误。");
|
||||
}
|
||||
catch (ReferenceConstraintException ex)
|
||||
{
|
||||
_logger.LogError(ex.Message);
|
||||
_logger.LogError(ex.InnerException is null ? ex.Message : ex.InnerException?.Message);
|
||||
throw new DBSaveFailedException("无法进行当前操作,当前数据不符合外键约束。");
|
||||
}
|
||||
catch (DbUpdateConcurrencyException ex)
|
||||
{
|
||||
_logger.LogError(ex.Message);
|
||||
_logger.LogError(ex.InnerException is null ? ex.Message : ex.InnerException?.Message);
|
||||
|
||||
throw new DBSaveFailedException("SQL 事务失败,请检查环境。");
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex.InnerException is null ? ex.Message : ex.InnerException?.Message);
|
||||
|
||||
throw new DBSaveFailedException("数据保存异常。");
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
public async Task AddAudit()
|
||||
|
|
|
@ -36,8 +36,7 @@ namespace IRaCIS.Core.Infra.EFCore.EntityConfigration
|
|||
|
||||
public void Configure(EntityTypeBuilder<Dictionary> builder)
|
||||
{
|
||||
builder.Property(e => e.MappedValue).Metadata.SetBeforeSaveBehavior(PropertySaveBehavior.Ignore);
|
||||
builder.Property(e => e.MappedValue).Metadata.SetAfterSaveBehavior(PropertySaveBehavior.Ignore);
|
||||
|
||||
|
||||
}
|
||||
}
|
||||
|
|
|
@ -8,7 +8,9 @@
|
|||
<OutputPath>..\bin</OutputPath>
|
||||
</PropertyGroup>
|
||||
|
||||
|
||||
<ItemGroup>
|
||||
<FrameworkReference Include="Microsoft.AspNetCore.App" />
|
||||
</ItemGroup>
|
||||
|
||||
|
||||
<ItemGroup>
|
||||
|
@ -17,15 +19,13 @@
|
|||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="EFCore.BulkExtensions" Version="6.5.6" />
|
||||
<PackageReference Include="AutoMapper" Version="12.0.0" />
|
||||
<PackageReference Include="EntityFrameworkCore.Exceptions.SqlServer" Version="6.0.3.1" />
|
||||
<PackageReference Include="Microsoft.AspNetCore.Mvc.Abstractions" Version="2.2.0" />
|
||||
<PackageReference Include="Microsoft.AspNetCore.Mvc.Core" Version="2.2.5" />
|
||||
<PackageReference Include="Microsoft.Extensions.Localization.Abstractions" Version="7.0.2" />
|
||||
<PackageReference Include="Microsoft.Extensions.Logging.Debug" Version="6.0.0" />
|
||||
<PackageReference Include="EntityFrameworkCore.Projectables" Version="2.3.0" />
|
||||
<PackageReference Include="NewId" Version="3.0.3" />
|
||||
<PackageReference Include="EFCore.BulkExtensions" Version="7.1.6" />
|
||||
<PackageReference Include="EntityFrameworkCore.Triggered" Version="3.2.2" />
|
||||
<PackageReference Include="EntityFrameworkCore.Projectables" Version="2.3.0" />
|
||||
<PackageReference Include="EntityFrameworkCore.Exceptions.SqlServer" Version="6.0.3.2" />
|
||||
<PackageReference Include="Microsoft.Extensions.Localization.Abstractions" Version="7.0.12" />
|
||||
<PackageReference Include="Microsoft.Extensions.Logging.Debug" Version="7.0.0" />
|
||||
<PackageReference Include="NewId" Version="4.0.1" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
@ -1,18 +0,0 @@
|
|||
|
||||
namespace IRaCIS.Core.Infra.Common.Cache
|
||||
{
|
||||
/// <summary>
|
||||
/// 缓存类型
|
||||
/// </summary>
|
||||
public enum CacheType
|
||||
{
|
||||
/// <summary>
|
||||
/// 内存缓存
|
||||
/// </summary>
|
||||
Memory,
|
||||
/// <summary>
|
||||
/// Redis缓存
|
||||
/// </summary>
|
||||
Redis
|
||||
}
|
||||
}
|
|
@ -1,107 +0,0 @@
|
|||
using System;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace IRaCIS.Core.Infra.Common.Cache
|
||||
{
|
||||
/// <summary>
|
||||
/// 缓存接口
|
||||
/// </summary>
|
||||
public interface ICache
|
||||
{
|
||||
/// <summary>
|
||||
/// 用于在 key 存在时删除 key
|
||||
/// </summary>
|
||||
/// <param name="key">键</param>
|
||||
long Del(params string[] key);
|
||||
|
||||
/// <summary>
|
||||
/// 用于在 key 存在时删除 key
|
||||
/// </summary>
|
||||
/// <param name="key">键</param>
|
||||
/// <returns></returns>
|
||||
Task<long> DelAsync(params string[] key);
|
||||
|
||||
/// <summary>
|
||||
/// 用于在 key 模板存在时删除
|
||||
/// </summary>
|
||||
/// <param name="pattern">key模板</param>
|
||||
/// <returns></returns>
|
||||
Task<long> DelByPatternAsync(string pattern);
|
||||
|
||||
/// <summary>
|
||||
/// 检查给定 key 是否存在
|
||||
/// </summary>
|
||||
/// <param name="key">键</param>
|
||||
/// <returns></returns>
|
||||
bool Exists(string key);
|
||||
|
||||
/// <summary>
|
||||
/// 检查给定 key 是否存在
|
||||
/// </summary>
|
||||
/// <param name="key">键</param>
|
||||
/// <returns></returns>
|
||||
Task<bool> ExistsAsync(string key);
|
||||
|
||||
/// <summary>
|
||||
/// 获取指定 key 的值
|
||||
/// </summary>
|
||||
/// <param name="key">键</param>
|
||||
/// <returns></returns>
|
||||
string Get(string key);
|
||||
|
||||
/// <summary>
|
||||
/// 获取指定 key 的值
|
||||
/// </summary>
|
||||
/// <typeparam name="T">byte[] 或其他类型</typeparam>
|
||||
/// <param name="key">键</param>
|
||||
/// <returns></returns>
|
||||
T Get<T>(string key);
|
||||
|
||||
/// <summary>
|
||||
/// 获取指定 key 的值
|
||||
/// </summary>
|
||||
/// <param name="key">键</param>
|
||||
/// <returns></returns>
|
||||
Task<string> GetAsync(string key);
|
||||
|
||||
/// <summary>
|
||||
/// 获取指定 key 的值
|
||||
/// </summary>
|
||||
/// <typeparam name="T">byte[] 或其他类型</typeparam>
|
||||
/// <param name="key">键</param>
|
||||
/// <returns></returns>
|
||||
Task<T> GetAsync<T>(string key);
|
||||
|
||||
/// <summary>
|
||||
/// 设置指定 key 的值,所有写入参数object都支持string | byte[] | 数值 | 对象
|
||||
/// </summary>
|
||||
/// <param name="key">键</param>
|
||||
/// <param name="value">值</param>
|
||||
bool Set(string key, object value);
|
||||
|
||||
/// <summary>
|
||||
/// 设置指定 key 的值,所有写入参数object都支持string | byte[] | 数值 | 对象
|
||||
/// </summary>
|
||||
/// <param name="key">键</param>
|
||||
/// <param name="value">值</param>
|
||||
/// <param name="expire">有效期</param>
|
||||
bool Set(string key, object value, TimeSpan expire);
|
||||
|
||||
/// <summary>
|
||||
/// 设置指定 key 的值,所有写入参数object都支持string | byte[] | 数值 | 对象
|
||||
/// </summary>
|
||||
/// <param name="key">键</param>
|
||||
/// <param name="value">值</param>
|
||||
/// <returns></returns>
|
||||
Task<bool> SetAsync(string key, object value);
|
||||
|
||||
/// <summary>
|
||||
/// 设置指定 key 的值,所有写入参数object都支持string | byte[] | 数值 | 对象
|
||||
/// </summary>
|
||||
/// <param name="key">键</param>
|
||||
/// <param name="value">值</param>
|
||||
/// <param name="expire">有效期</param>
|
||||
/// <returns></returns>
|
||||
Task<bool> SetAsync(string key, object value, TimeSpan expire);
|
||||
}
|
||||
}
|
|
@ -1,127 +0,0 @@
|
|||
using System;
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Reflection;
|
||||
using System.Text.RegularExpressions;
|
||||
using System.Threading.Tasks;
|
||||
using Microsoft.Extensions.Caching.Memory;
|
||||
|
||||
namespace IRaCIS.Core.Infra.Common.Cache
|
||||
{
|
||||
/// <summary>
|
||||
/// 内存缓存
|
||||
/// </summary>
|
||||
public class MemoryCache : ICache
|
||||
{
|
||||
private readonly IMemoryCache _memoryCache;
|
||||
public MemoryCache(IMemoryCache memoryCache)
|
||||
{
|
||||
_memoryCache = memoryCache;
|
||||
}
|
||||
|
||||
public long Del(params string[] key)
|
||||
{
|
||||
foreach(var k in key)
|
||||
{
|
||||
_memoryCache.Remove(k);
|
||||
}
|
||||
return key.Length;
|
||||
}
|
||||
|
||||
public Task<long> DelAsync(params string[] key)
|
||||
{
|
||||
foreach (var k in key)
|
||||
{
|
||||
_memoryCache.Remove(k);
|
||||
}
|
||||
|
||||
return Task.FromResult((long)key.Length);
|
||||
}
|
||||
|
||||
public async Task<long> DelByPatternAsync(string pattern)
|
||||
{
|
||||
if (string.IsNullOrEmpty(pattern))
|
||||
return default;
|
||||
|
||||
pattern = Regex.Replace(pattern, @"\{.*\}", "(.*)");
|
||||
|
||||
var keys = GetAllKeys().Where(k => Regex.IsMatch(k, pattern));
|
||||
|
||||
if(keys != null && keys.Count() > 0)
|
||||
{
|
||||
return await DelAsync(keys.ToArray());
|
||||
}
|
||||
|
||||
return default;
|
||||
}
|
||||
|
||||
public bool Exists(string key)
|
||||
{
|
||||
return _memoryCache.TryGetValue(key, out _);
|
||||
}
|
||||
|
||||
public Task<bool> ExistsAsync(string key)
|
||||
{
|
||||
return Task.FromResult(_memoryCache.TryGetValue(key, out _));
|
||||
}
|
||||
|
||||
public string Get(string key)
|
||||
{
|
||||
return _memoryCache.Get(key)?.ToString();
|
||||
}
|
||||
|
||||
public T Get<T>(string key)
|
||||
{
|
||||
return _memoryCache.Get<T>(key);
|
||||
}
|
||||
|
||||
public Task<string> GetAsync(string key)
|
||||
{
|
||||
return Task.FromResult(Get(key));
|
||||
}
|
||||
|
||||
public Task<T> GetAsync<T>(string key)
|
||||
{
|
||||
return Task.FromResult(Get<T>(key));
|
||||
}
|
||||
|
||||
public bool Set(string key, object value)
|
||||
{
|
||||
_memoryCache.Set(key, value);
|
||||
return true;
|
||||
}
|
||||
|
||||
public bool Set(string key, object value, TimeSpan expire)
|
||||
{
|
||||
_memoryCache.Set(key, value, expire);
|
||||
return true;
|
||||
}
|
||||
|
||||
public Task<bool> SetAsync(string key, object value)
|
||||
{
|
||||
Set(key, value);
|
||||
return Task.FromResult(true);
|
||||
}
|
||||
|
||||
public Task<bool> SetAsync(string key, object value, TimeSpan expire)
|
||||
{
|
||||
Set(key, value, expire);
|
||||
return Task.FromResult(true);
|
||||
}
|
||||
|
||||
private List<string> GetAllKeys()
|
||||
{
|
||||
const BindingFlags flags = BindingFlags.Instance | BindingFlags.NonPublic;
|
||||
var entries = _memoryCache.GetType().GetField("_entries", flags).GetValue(_memoryCache);
|
||||
var cacheItems = entries as IDictionary;
|
||||
var keys = new List<string>();
|
||||
if (cacheItems == null) return keys;
|
||||
foreach (DictionaryEntry cacheItem in cacheItems)
|
||||
{
|
||||
keys.Add(cacheItem.Key.ToString());
|
||||
}
|
||||
return keys;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,88 +0,0 @@
|
|||
using System;
|
||||
using System.Text.RegularExpressions;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace IRaCIS.Core.Infra.Common.Cache
|
||||
{
|
||||
/// <summary>
|
||||
/// Redis缓存
|
||||
/// </summary>
|
||||
public class RedisCache : ICache
|
||||
{
|
||||
public long Del(params string[] key)
|
||||
{
|
||||
return RedisHelper.Del(key);
|
||||
}
|
||||
|
||||
public Task<long> DelAsync(params string[] key)
|
||||
{
|
||||
return RedisHelper.DelAsync(key);
|
||||
}
|
||||
|
||||
public async Task<long> DelByPatternAsync(string pattern)
|
||||
{
|
||||
if (string.IsNullOrEmpty(pattern))
|
||||
return default;
|
||||
|
||||
pattern = Regex.Replace(pattern, @"\{.*\}", "*");
|
||||
|
||||
var keys = (await RedisHelper.KeysAsync(pattern));
|
||||
if(keys != null && keys.Length > 0)
|
||||
{
|
||||
return await RedisHelper.DelAsync(keys);
|
||||
}
|
||||
|
||||
return default;
|
||||
}
|
||||
|
||||
public bool Exists(string key)
|
||||
{
|
||||
return RedisHelper.Exists(key);
|
||||
}
|
||||
|
||||
public Task<bool> ExistsAsync(string key)
|
||||
{
|
||||
return RedisHelper.ExistsAsync(key);
|
||||
}
|
||||
|
||||
public string Get(string key)
|
||||
{
|
||||
return RedisHelper.Get(key);
|
||||
}
|
||||
|
||||
public T Get<T>(string key)
|
||||
{
|
||||
return RedisHelper.Get<T>(key);
|
||||
}
|
||||
|
||||
public Task<string> GetAsync(string key)
|
||||
{
|
||||
return RedisHelper.GetAsync(key);
|
||||
}
|
||||
|
||||
public Task<T> GetAsync<T>(string key)
|
||||
{
|
||||
return RedisHelper.GetAsync<T>(key);
|
||||
}
|
||||
|
||||
public bool Set(string key, object value)
|
||||
{
|
||||
return RedisHelper.Set(key, value);
|
||||
}
|
||||
|
||||
public bool Set(string key, object value, TimeSpan expire)
|
||||
{
|
||||
return RedisHelper.Set(key, value, expire);
|
||||
}
|
||||
|
||||
public Task<bool> SetAsync(string key, object value)
|
||||
{
|
||||
return RedisHelper.SetAsync(key, value);
|
||||
}
|
||||
|
||||
public Task<bool> SetAsync(string key, object value, TimeSpan expire)
|
||||
{
|
||||
return RedisHelper.SetAsync(key, value, expire);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,158 +0,0 @@
|
|||
using Microsoft.AspNetCore.Http;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Text;
|
||||
|
||||
namespace IRaCIS.Core.Infrastructure.Extention
|
||||
{
|
||||
public static class HttpContextExtension
|
||||
{
|
||||
|
||||
public static T GetService<T>(this HttpContext context) where T : class
|
||||
{
|
||||
return context.RequestServices.GetService(typeof(T)) as T;
|
||||
}
|
||||
|
||||
|
||||
public static string GetUserIp(this HttpContext context)
|
||||
{
|
||||
string realIP = null;
|
||||
string forwarded = null;
|
||||
string remoteIpAddress = context.Connection.RemoteIpAddress.ToString();
|
||||
if (context.Request.Headers.ContainsKey("X-Real-IP"))
|
||||
{
|
||||
realIP = context.Request.Headers["X-Real-IP"].ToString();
|
||||
if (realIP != remoteIpAddress)
|
||||
{
|
||||
remoteIpAddress = realIP;
|
||||
}
|
||||
}
|
||||
if (context.Request.Headers.ContainsKey("X-Forwarded-For"))
|
||||
{
|
||||
forwarded = context.Request.Headers["X-Forwarded-For"].ToString();
|
||||
if (forwarded != remoteIpAddress)
|
||||
{
|
||||
remoteIpAddress = forwarded;
|
||||
}
|
||||
}
|
||||
return remoteIpAddress;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// 获取Request值
|
||||
/// </summary>
|
||||
/// <param name="context"></param>
|
||||
/// <param name="parameter"></param>
|
||||
/// <returns></returns>
|
||||
public static string Request(this HttpContext context, string parameter)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (context == null)
|
||||
return null;
|
||||
if (context.Request.Method == "POST")
|
||||
return context.Request.Form[parameter].ToString();
|
||||
else
|
||||
return context.Request.Query[parameter].ToString();
|
||||
}
|
||||
catch (System.Exception ex)
|
||||
{
|
||||
Console.Write(ex.Message + ex.InnerException);
|
||||
return context.RequestString(parameter);
|
||||
}
|
||||
}
|
||||
|
||||
public static T Request<T>(this HttpContext context, string parameter) where T : class
|
||||
{
|
||||
return context.RequestString(parameter)?.DeserializeObject<T>();
|
||||
}
|
||||
public static string RequestString(this HttpContext context, string parameter)
|
||||
{
|
||||
string requestParam = context.GetRequestParameters();
|
||||
if (string.IsNullOrEmpty(requestParam)) return null;
|
||||
Dictionary<string, object> keyValues = requestParam.DeserializeObject<Dictionary<string, object>>();
|
||||
if (keyValues == null || keyValues.Count == 0) return null;
|
||||
if (keyValues.TryGetValue(parameter, out object value))
|
||||
{
|
||||
if (value == null) return null;
|
||||
if (value.GetType() == typeof(string))
|
||||
{
|
||||
return value?.ToString();
|
||||
}
|
||||
return value.Serialize();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
/// <summary>
|
||||
/// 是否为ajax请求
|
||||
/// </summary>
|
||||
/// <param name="request"></param>
|
||||
/// <returns></returns>
|
||||
public static bool IsAjaxRequest(this HttpContext context)
|
||||
{
|
||||
return context.Request("X-Requested-With") == "XMLHttpRequest"
|
||||
|| (context.Request.Headers != null
|
||||
&& context.Request.Headers["X-Requested-With"] == "XMLHttpRequest");
|
||||
}
|
||||
|
||||
public static UserAgent GetAgentType(this HttpContext context)
|
||||
{
|
||||
string agent = context.Request.Headers["User-Agent"].ToString().ToLower();
|
||||
|
||||
if (agent.Contains("ios") || agent.Contains("ipod") || agent.Contains("ipad"))
|
||||
{
|
||||
return UserAgent.IOS;
|
||||
}
|
||||
if (agent.Contains("windows"))
|
||||
{
|
||||
return UserAgent.Windows;
|
||||
}
|
||||
return UserAgent.Android;
|
||||
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 获取请求的参数
|
||||
/// net core 2.0已增加回读方法 context.Request.EnableRewind();
|
||||
///
|
||||
/// </summary>
|
||||
/// <param name="context"></param>
|
||||
/// <returns></returns>
|
||||
|
||||
public static string GetRequestParameters(this HttpContext context)
|
||||
{
|
||||
if (context.Request.Body == null || !context.Request.Body.CanRead || !context.Request.Body.CanSeek)
|
||||
return null;
|
||||
if (context.Request.Body.Length == 0)
|
||||
return null;
|
||||
if (context.Request.Body.Position > 0)
|
||||
context.Request.Body.Position = 0;
|
||||
|
||||
string prarameters = null;
|
||||
var bodyStream = context.Request.Body;
|
||||
|
||||
using (var buffer = new MemoryStream())
|
||||
{
|
||||
bodyStream.CopyToAsync(buffer);
|
||||
buffer.Position = 0L;
|
||||
bodyStream.Position = 0L;
|
||||
using (var reader = new StreamReader(buffer, Encoding.UTF8))
|
||||
{
|
||||
buffer.Seek(0, SeekOrigin.Begin);
|
||||
prarameters = reader.ReadToEnd();
|
||||
}
|
||||
}
|
||||
return prarameters;
|
||||
}
|
||||
}
|
||||
public enum UserAgent
|
||||
{
|
||||
IOS = 0,
|
||||
Android = 1,
|
||||
Windows = 2,
|
||||
Linux
|
||||
}
|
||||
}
|
|
@ -1,43 +0,0 @@
|
|||
using System.Linq;
|
||||
using System.Text.RegularExpressions;
|
||||
using Microsoft.AspNetCore.Http;
|
||||
|
||||
namespace IRaCIS.Core.Infrastructure
|
||||
{
|
||||
public class IPHelper
|
||||
{
|
||||
/// <summary>
|
||||
/// 是否为ip
|
||||
/// </summary>
|
||||
/// <param name="ip"></param>
|
||||
/// <returns></returns>
|
||||
public static bool IsIP(string ip)
|
||||
{
|
||||
return Regex.IsMatch(ip, @"^((2[0-4]\d|25[0-5]|[01]?\d\d?)\.){3}(2[0-4]\d|25[0-5]|[01]?\d\d?)$");
|
||||
}
|
||||
|
||||
public static string GetIP(HttpRequest request)
|
||||
{
|
||||
if (request == null)
|
||||
{
|
||||
return "";
|
||||
}
|
||||
|
||||
string ip = request.Headers["X-Real-IP"].FirstOrDefault();
|
||||
if (string.IsNullOrEmpty(ip))
|
||||
{
|
||||
ip = request.Headers["X-Forwarded-For"].FirstOrDefault();
|
||||
}
|
||||
if (string.IsNullOrEmpty(ip))
|
||||
{
|
||||
ip = request.HttpContext?.Connection?.RemoteIpAddress?.ToString();
|
||||
}
|
||||
if (string.IsNullOrEmpty(ip) || !IsIP(ip))
|
||||
{
|
||||
ip = "127.0.0.1";
|
||||
}
|
||||
|
||||
return ip;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,27 +1,29 @@
|
|||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFramework>net6.0</TargetFramework>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup>
|
||||
<TargetFramework>net6.0</TargetFramework>
|
||||
</PropertyGroup>
|
||||
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|AnyCPU'">
|
||||
<OutputPath>..\bin</OutputPath>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|AnyCPU'">
|
||||
<OutputPath>..\bin</OutputPath>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="CSRedisCore" Version="3.8.669" />
|
||||
<PackageReference Include="Microsoft.AspNetCore.Http.Abstractions" Version="2.2.0" />
|
||||
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="6.0.10" />
|
||||
<PackageReference Include="SharpCompress" Version="0.32.2" />
|
||||
<PackageReference Include="SharpZipLib" Version="1.4.0" />
|
||||
<PackageReference Include="System.Linq.Dynamic.Core" Version="1.2.20" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<PackageReference Include="AutoMapper" Version="12.0.1" />
|
||||
<PackageReference Include="AutoMapper.Collection.EntityFrameworkCore" Version="9.0.0" />
|
||||
<PackageReference Include="Newtonsoft.Json" Version="13.0.3" />
|
||||
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="7.0.12" />
|
||||
<PackageReference Include="SharpCompress" Version="0.34.1" />
|
||||
<PackageReference Include="SharpZipLib" Version="1.4.2" />
|
||||
<PackageReference Include="System.Linq.Dynamic.Core" Version="1.3.5" />
|
||||
|
||||
</ItemGroup>
|
||||
|
||||
|
||||
|
||||
<ItemGroup>
|
||||
<Service Include="{508349b6-6b84-4df5-91f0-309beebad82d}" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Service Include="{508349b6-6b84-4df5-91f0-309beebad82d}" />
|
||||
</ItemGroup>
|
||||
|
||||
|
||||
|
||||
|
|
|
@ -3,11 +3,50 @@ using System.Threading;
|
|||
using System.Threading.Tasks;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
using System.Linq.Dynamic.Core;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace IRaCIS.Core.Infrastructure.Extention
|
||||
{
|
||||
public static class QueryablePageListExtensions
|
||||
{
|
||||
//内存排序 后期删除
|
||||
public static PageOutput<T> ToPagedList<T>(this IList<T> source, int pageIndex, int pageSize, string defaultSortFiled = "Id", bool isAsc = true)
|
||||
{
|
||||
if (pageIndex <= 0)
|
||||
{
|
||||
pageIndex = 1;
|
||||
}
|
||||
if (pageSize <= 0)
|
||||
{
|
||||
pageSize = 10;
|
||||
}
|
||||
var count = source.Count();
|
||||
|
||||
if (count == 0)
|
||||
{
|
||||
return new PageOutput<T>() { CurrentPageData = new List<T>() };
|
||||
}
|
||||
|
||||
var propName = string.IsNullOrWhiteSpace(defaultSortFiled) ? "Id" : defaultSortFiled;
|
||||
|
||||
IQueryable<T> sourceQuery = isAsc ? source.AsQueryable().OrderBy(propName) : source.AsQueryable().OrderBy(propName + " desc");
|
||||
|
||||
sourceQuery = sourceQuery.Skip((pageIndex - 1) * pageSize);
|
||||
|
||||
var items = sourceQuery
|
||||
.Take(pageSize)
|
||||
.ToArray();
|
||||
|
||||
var pagedList = new PageOutput<T>()
|
||||
{
|
||||
PageIndex = pageIndex,
|
||||
PageSize = pageSize,
|
||||
TotalCount = count,
|
||||
CurrentPageData = items
|
||||
};
|
||||
|
||||
return pagedList;
|
||||
}
|
||||
//单字段排序
|
||||
public static PageOutput<T> ToPagedList<T>(this IQueryable<T> source, int pageIndex, int pageSize, string defaultSortFiled = "Id", bool isAsc = true)
|
||||
{
|
||||
|
|
|
@ -13,10 +13,9 @@
|
|||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="6.0.8" />
|
||||
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.0.0" />
|
||||
<PackageReference Include="NUnit3TestAdapter" Version="4.1.0" />
|
||||
<PackageReference Include="coverlet.collector" Version="3.1.0">
|
||||
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.7.2" />
|
||||
<PackageReference Include="NUnit3TestAdapter" Version="4.5.0" />
|
||||
<PackageReference Include="coverlet.collector" Version="6.0.0">
|
||||
<PrivateAssets>all</PrivateAssets>
|
||||
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
|
||||
</PackageReference>
|
||||
|
|
|
@ -1,43 +0,0 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
|
||||
#region AuditContext
|
||||
public class AuditContext : DbContext
|
||||
{
|
||||
private readonly string _connectionString;
|
||||
|
||||
public AuditContext(string connectionString)
|
||||
{
|
||||
_connectionString = connectionString;
|
||||
}
|
||||
|
||||
//protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
|
||||
// => optionsBuilder.Usesq(_connectionString);
|
||||
|
||||
public DbSet<SaveChangesAudit> SaveChangesAudits { get; set; }
|
||||
}
|
||||
|
||||
|
||||
public class SaveChangesAudit
|
||||
{
|
||||
public int Id { get; set; }
|
||||
public Guid AuditId { get; set; }
|
||||
public DateTime StartTime { get; set; }
|
||||
public DateTime EndTime { get; set; }
|
||||
public bool Succeeded { get; set; }
|
||||
public string ErrorMessage { get; set; }
|
||||
|
||||
public ICollection<EntityAudit> Entities { get; } = new List<EntityAudit>();
|
||||
}
|
||||
|
||||
public class EntityAudit
|
||||
{
|
||||
public int Id { get; set; }
|
||||
public EntityState State { get; set; }
|
||||
public string AuditMessage { get; set; }
|
||||
|
||||
public SaveChangesAudit SaveChangesAudit { get; set; }
|
||||
}
|
||||
|
||||
#endregion
|
Loading…
Reference in New Issue