From f955aab2181f20a671de1b7a3435e4c0df2d29e7 Mon Sep 17 00:00:00 2001 From: Roman Efremov Date: Wed, 5 Feb 2025 09:16:28 +0500 Subject: [PATCH 1/7] =?UTF-8?q?=D0=9F=D0=B5=D1=80=D0=B5=D0=BD=D0=B5=D1=81?= =?UTF-8?q?=D1=82=D0=B8=20=D1=81=D0=BE=D0=B4=D0=B5=D1=80=D0=B6=D0=B8=D0=BC?= =?UTF-8?q?=D0=BE=D0=B5=20=D0=BF=D1=80=D0=BE=D0=B5=D0=BA=D1=82=D0=B0=20DD.?= =?UTF-8?q?Persistence.Repository=20=D0=B2=20DD.Persistence.Database.Postg?= =?UTF-8?q?res?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- DD.Persistence.API/DD.Persistence.API.csproj | 1 - DD.Persistence.API/Startup.cs | 1 - .../DD.Persistence.Database.Postgres.csproj | 2 + .../DependencyInjection.cs | 42 ++++++++++++++++- .../Extensions/EFExtensionsSortBy.cs | 2 +- .../Helpers}/CyclicArray.cs | 2 +- .../Helpers}/QueryBuilders.cs | 13 +++--- .../Repositories/ChangeLogRepository.cs | 3 +- .../Repositories/DataSchemeRepository.cs | 2 +- .../DataSourceSystemRepository.cs | 2 +- .../Repositories/ParameterRepository.cs | 2 +- .../Repositories/SetpointRepository.cs | 2 +- .../Repositories/TechMessagesRepository.cs | 2 +- .../TimestampedValuesRepository.cs | 14 +++++- .../DataSchemeCachedRepository.cs | 4 +- .../DataSourceSystemCachedRepository.cs | 4 +- .../TimestampedValuesCachedRepository.cs | 2 +- .../DD.Persistence.Repository.Test.csproj | 1 - .../SetpointRepositoryShould.cs | 7 +-- .../DD.Persistence.Repository.csproj | 19 -------- .../DependencyInjection.cs | 45 ------------------- DD.Persistence.sln | 6 --- 22 files changed, 76 insertions(+), 102 deletions(-) rename {DD.Persistence.Repository => DD.Persistence.Database.Postgres}/Extensions/EFExtensionsSortBy.cs (99%) rename {DD.Persistence.Repository => DD.Persistence.Database.Postgres/Helpers}/CyclicArray.cs (99%) rename {DD.Persistence.Repository => DD.Persistence.Database.Postgres/Helpers}/QueryBuilders.cs (90%) rename {DD.Persistence.Repository => DD.Persistence.Database.Postgres}/Repositories/ChangeLogRepository.cs (98%) rename {DD.Persistence.Repository => DD.Persistence.Database.Postgres}/Repositories/DataSchemeRepository.cs (94%) rename {DD.Persistence.Repository => DD.Persistence.Database.Postgres}/Repositories/DataSourceSystemRepository.cs (94%) rename {DD.Persistence.Repository => DD.Persistence.Database.Postgres}/Repositories/ParameterRepository.cs (98%) rename {DD.Persistence.Repository => DD.Persistence.Database.Postgres}/Repositories/SetpointRepository.cs (98%) rename {DD.Persistence.Repository => DD.Persistence.Database.Postgres}/Repositories/TechMessagesRepository.cs (98%) rename {DD.Persistence.Repository => DD.Persistence.Database.Postgres}/Repositories/TimestampedValuesRepository.cs (91%) rename {DD.Persistence.Repository => DD.Persistence.Database.Postgres}/RepositoriesCached/DataSchemeCachedRepository.cs (88%) rename {DD.Persistence.Repository => DD.Persistence.Database.Postgres}/RepositoriesCached/DataSourceSystemCachedRepository.cs (91%) rename {DD.Persistence.Repository => DD.Persistence.Database.Postgres}/RepositoriesCached/TimestampedValuesCachedRepository.cs (98%) delete mode 100644 DD.Persistence.Repository/DD.Persistence.Repository.csproj delete mode 100644 DD.Persistence.Repository/DependencyInjection.cs diff --git a/DD.Persistence.API/DD.Persistence.API.csproj b/DD.Persistence.API/DD.Persistence.API.csproj index 5ed1097..38dd298 100644 --- a/DD.Persistence.API/DD.Persistence.API.csproj +++ b/DD.Persistence.API/DD.Persistence.API.csproj @@ -25,7 +25,6 @@ - diff --git a/DD.Persistence.API/Startup.cs b/DD.Persistence.API/Startup.cs index 1a880c0..bc78548 100644 --- a/DD.Persistence.API/Startup.cs +++ b/DD.Persistence.API/Startup.cs @@ -1,6 +1,5 @@ using DD.Persistence.Database.Model; using DD.Persistence.Database.Postgres.Extensions; -using DD.Persistence.Repository; namespace DD.Persistence.API; diff --git a/DD.Persistence.Database.Postgres/DD.Persistence.Database.Postgres.csproj b/DD.Persistence.Database.Postgres/DD.Persistence.Database.Postgres.csproj index bf406a6..80b6736 100644 --- a/DD.Persistence.Database.Postgres/DD.Persistence.Database.Postgres.csproj +++ b/DD.Persistence.Database.Postgres/DD.Persistence.Database.Postgres.csproj @@ -7,11 +7,13 @@ + all runtime; build; native; contentfiles; analyzers; buildtransitive + diff --git a/DD.Persistence.Database.Postgres/DependencyInjection.cs b/DD.Persistence.Database.Postgres/DependencyInjection.cs index f0c8ff1..0509061 100644 --- a/DD.Persistence.Database.Postgres/DependencyInjection.cs +++ b/DD.Persistence.Database.Postgres/DependencyInjection.cs @@ -1,6 +1,13 @@ -using Microsoft.EntityFrameworkCore; +using DD.Persistence.Database.Entity; +using DD.Persistence.Database.Postgres.Repositories; +using DD.Persistence.Database.Postgres.RepositoriesCached; +using DD.Persistence.Models; +using DD.Persistence.Repositories; +using Mapster; +using Microsoft.EntityFrameworkCore; using Microsoft.Extensions.Configuration; using Microsoft.Extensions.DependencyInjection; +using System.Reflection; namespace DD.Persistence.Database.Model; @@ -17,4 +24,37 @@ public static class DependencyInjection return services; } + + public static void MapsterSetup() + { + TypeAdapterConfig.GlobalSettings.Default.Config + .ForType() + .Ignore(dest => dest.System, dest => dest.SystemId); + + TypeAdapterConfig.NewConfig() + .Map(dest => dest.Value, src => new ChangeLogValuesDto() + { + Value = src.Value, + Id = src.Id + }); + } + + public static IServiceCollection AddInfrastructure(this IServiceCollection services) + { + var typeAdapterConfig = TypeAdapterConfig.GlobalSettings; + typeAdapterConfig.RuleMap.Clear(); + typeAdapterConfig.Scan(Assembly.GetExecutingAssembly()); + + MapsterSetup(); + + services.AddTransient(); + services.AddTransient(); + services.AddTransient(); + services.AddTransient(); + services.AddTransient(); + services.AddTransient(); + services.AddTransient(); + + return services; + } } diff --git a/DD.Persistence.Repository/Extensions/EFExtensionsSortBy.cs b/DD.Persistence.Database.Postgres/Extensions/EFExtensionsSortBy.cs similarity index 99% rename from DD.Persistence.Repository/Extensions/EFExtensionsSortBy.cs rename to DD.Persistence.Database.Postgres/Extensions/EFExtensionsSortBy.cs index bed529e..3af7ae0 100644 --- a/DD.Persistence.Repository/Extensions/EFExtensionsSortBy.cs +++ b/DD.Persistence.Database.Postgres/Extensions/EFExtensionsSortBy.cs @@ -2,7 +2,7 @@ using System.Collections.Concurrent; using System.Linq.Expressions; using System.Reflection; -namespace DD.Persistence.Repository.Extensions; +namespace DD.Persistence.Database.Postgres.Extensions; public static class EFExtensionsSortBy { diff --git a/DD.Persistence.Repository/CyclicArray.cs b/DD.Persistence.Database.Postgres/Helpers/CyclicArray.cs similarity index 99% rename from DD.Persistence.Repository/CyclicArray.cs rename to DD.Persistence.Database.Postgres/Helpers/CyclicArray.cs index 7a7ea1d..fcb5793 100644 --- a/DD.Persistence.Repository/CyclicArray.cs +++ b/DD.Persistence.Database.Postgres/Helpers/CyclicArray.cs @@ -1,6 +1,6 @@ using System.Collections; -namespace DD.Persistence.Repository; +namespace DD.Persistence.Database.Postgres.Helpers; /// /// Цикличный массив /// diff --git a/DD.Persistence.Repository/QueryBuilders.cs b/DD.Persistence.Database.Postgres/Helpers/QueryBuilders.cs similarity index 90% rename from DD.Persistence.Repository/QueryBuilders.cs rename to DD.Persistence.Database.Postgres/Helpers/QueryBuilders.cs index 52b6429..8529230 100644 --- a/DD.Persistence.Repository/QueryBuilders.cs +++ b/DD.Persistence.Database.Postgres/Helpers/QueryBuilders.cs @@ -1,11 +1,10 @@ -using Microsoft.EntityFrameworkCore; -using DD.Persistence.Models.Requests; -using DD.Persistence.Models.Common; -using DD.Persistence.ModelsAbstractions; -using DD.Persistence.Database.EntityAbstractions; +using DD.Persistence.Database.EntityAbstractions; using DD.Persistence.Extensions; +using DD.Persistence.Models.Common; +using DD.Persistence.Models.Requests; +using Microsoft.EntityFrameworkCore; -namespace DD.Persistence.Repository; +namespace DD.Persistence.Database.Postgres.Helpers; /// /// класс с набором методов, необходимых для фильтрации записей @@ -55,4 +54,4 @@ public static class QueryBuilders return result; } -} +} \ No newline at end of file diff --git a/DD.Persistence.Repository/Repositories/ChangeLogRepository.cs b/DD.Persistence.Database.Postgres/Repositories/ChangeLogRepository.cs similarity index 98% rename from DD.Persistence.Repository/Repositories/ChangeLogRepository.cs rename to DD.Persistence.Database.Postgres/Repositories/ChangeLogRepository.cs index 2af06ce..c2502ef 100644 --- a/DD.Persistence.Repository/Repositories/ChangeLogRepository.cs +++ b/DD.Persistence.Database.Postgres/Repositories/ChangeLogRepository.cs @@ -1,4 +1,5 @@ using DD.Persistence.Database.Entity; +using DD.Persistence.Database.Postgres.Helpers; using DD.Persistence.Models; using DD.Persistence.Models.Common; using DD.Persistence.Models.Requests; @@ -7,7 +8,7 @@ using Mapster; using Microsoft.EntityFrameworkCore; using UuidExtensions; -namespace DD.Persistence.Repository.Repositories; +namespace DD.Persistence.Database.Postgres.Repositories; public class ChangeLogRepository : IChangeLogRepository { private readonly DbContext db; diff --git a/DD.Persistence.Repository/Repositories/DataSchemeRepository.cs b/DD.Persistence.Database.Postgres/Repositories/DataSchemeRepository.cs similarity index 94% rename from DD.Persistence.Repository/Repositories/DataSchemeRepository.cs rename to DD.Persistence.Database.Postgres/Repositories/DataSchemeRepository.cs index c30c8da..ba5ccd7 100644 --- a/DD.Persistence.Repository/Repositories/DataSchemeRepository.cs +++ b/DD.Persistence.Database.Postgres/Repositories/DataSchemeRepository.cs @@ -4,7 +4,7 @@ using DD.Persistence.Repositories; using Mapster; using Microsoft.EntityFrameworkCore; -namespace DD.Persistence.Repository.Repositories; +namespace DD.Persistence.Database.Postgres.Repositories; public class DataSchemeRepository : IDataSchemeRepository { protected DbContext db; diff --git a/DD.Persistence.Repository/Repositories/DataSourceSystemRepository.cs b/DD.Persistence.Database.Postgres/Repositories/DataSourceSystemRepository.cs similarity index 94% rename from DD.Persistence.Repository/Repositories/DataSourceSystemRepository.cs rename to DD.Persistence.Database.Postgres/Repositories/DataSourceSystemRepository.cs index d8b6c0a..d9e7fa7 100644 --- a/DD.Persistence.Repository/Repositories/DataSourceSystemRepository.cs +++ b/DD.Persistence.Database.Postgres/Repositories/DataSourceSystemRepository.cs @@ -4,7 +4,7 @@ using DD.Persistence.Repositories; using Mapster; using Microsoft.EntityFrameworkCore; -namespace DD.Persistence.Repository.Repositories; +namespace DD.Persistence.Database.Postgres.Repositories; public class DataSourceSystemRepository : IDataSourceSystemRepository { protected DbContext db; diff --git a/DD.Persistence.Repository/Repositories/ParameterRepository.cs b/DD.Persistence.Database.Postgres/Repositories/ParameterRepository.cs similarity index 98% rename from DD.Persistence.Repository/Repositories/ParameterRepository.cs rename to DD.Persistence.Database.Postgres/Repositories/ParameterRepository.cs index d241de7..c489cd7 100644 --- a/DD.Persistence.Repository/Repositories/ParameterRepository.cs +++ b/DD.Persistence.Database.Postgres/Repositories/ParameterRepository.cs @@ -5,7 +5,7 @@ using DD.Persistence.Models; using DD.Persistence.Repositories; using DD.Persistence.Models.Common; -namespace DD.Persistence.Repository.Repositories; +namespace DD.Persistence.Database.Postgres.Repositories; public class ParameterRepository : IParameterRepository { private DbContext db; diff --git a/DD.Persistence.Repository/Repositories/SetpointRepository.cs b/DD.Persistence.Database.Postgres/Repositories/SetpointRepository.cs similarity index 98% rename from DD.Persistence.Repository/Repositories/SetpointRepository.cs rename to DD.Persistence.Database.Postgres/Repositories/SetpointRepository.cs index 97c6098..3cfd9b1 100644 --- a/DD.Persistence.Repository/Repositories/SetpointRepository.cs +++ b/DD.Persistence.Database.Postgres/Repositories/SetpointRepository.cs @@ -6,7 +6,7 @@ using Mapster; using Microsoft.EntityFrameworkCore; using System.Text.Json; -namespace DD.Persistence.Repository.Repositories +namespace DD.Persistence.Database.Postgres.Repositories { public class SetpointRepository : ISetpointRepository { diff --git a/DD.Persistence.Repository/Repositories/TechMessagesRepository.cs b/DD.Persistence.Database.Postgres/Repositories/TechMessagesRepository.cs similarity index 98% rename from DD.Persistence.Repository/Repositories/TechMessagesRepository.cs rename to DD.Persistence.Database.Postgres/Repositories/TechMessagesRepository.cs index 1a84f25..15d8fe8 100644 --- a/DD.Persistence.Repository/Repositories/TechMessagesRepository.cs +++ b/DD.Persistence.Database.Postgres/Repositories/TechMessagesRepository.cs @@ -7,7 +7,7 @@ using DD.Persistence.Repositories; using Mapster; using Microsoft.EntityFrameworkCore; -namespace DD.Persistence.Repository.Repositories +namespace DD.Persistence.Database.Postgres.Repositories { public class TechMessagesRepository : ITechMessagesRepository { diff --git a/DD.Persistence.Repository/Repositories/TimestampedValuesRepository.cs b/DD.Persistence.Database.Postgres/Repositories/TimestampedValuesRepository.cs similarity index 91% rename from DD.Persistence.Repository/Repositories/TimestampedValuesRepository.cs rename to DD.Persistence.Database.Postgres/Repositories/TimestampedValuesRepository.cs index 2005a5a..149e411 100644 --- a/DD.Persistence.Repository/Repositories/TimestampedValuesRepository.cs +++ b/DD.Persistence.Database.Postgres/Repositories/TimestampedValuesRepository.cs @@ -4,7 +4,7 @@ using DD.Persistence.Models.Common; using DD.Persistence.Repositories; using Microsoft.EntityFrameworkCore; -namespace DD.Persistence.Repository.Repositories; +namespace DD.Persistence.Database.Postgres.Repositories; public class TimestampedValuesRepository : ITimestampedValuesRepository { private readonly DbContext db; @@ -14,7 +14,8 @@ public class TimestampedValuesRepository : ITimestampedValuesRepository this.db = db; } - protected virtual IQueryable GetQueryReadOnly() => this.db.Set(); + protected virtual IQueryable GetQueryReadOnly() => this.db.Set() + .Include(e => e.DataScheme); public async virtual Task AddRange(Guid discriminatorId, IEnumerable dtos, CancellationToken token) { @@ -54,6 +55,15 @@ public class TimestampedValuesRepository : ITimestampedValuesRepository .Select(g => KeyValuePair.Create(g.Key, g.OrderBy(i => i.Timestamp).Skip(skip).Take(take))); var entities = await groupQuery.ToArrayAsync(token); + //var root = new TVertex( + // OperationEnum.And, + // new TLeaf(OperationEnum.Equal, "A", 1), + // new TLeaf(OperationEnum.Equal, "B", 1) + //); + //var dataScheme = entities.First().Value.First().DataScheme; + //var specification = dataScheme.BuildFilter(root); + //var que = ApplySpecification(specification); + var result = entities.ToDictionary(k => k.Key, v => v.Value.Select(e => ( e.Timestamp, e.Values diff --git a/DD.Persistence.Repository/RepositoriesCached/DataSchemeCachedRepository.cs b/DD.Persistence.Database.Postgres/RepositoriesCached/DataSchemeCachedRepository.cs similarity index 88% rename from DD.Persistence.Repository/RepositoriesCached/DataSchemeCachedRepository.cs rename to DD.Persistence.Database.Postgres/RepositoriesCached/DataSchemeCachedRepository.cs index ea22196..f4cec62 100644 --- a/DD.Persistence.Repository/RepositoriesCached/DataSchemeCachedRepository.cs +++ b/DD.Persistence.Database.Postgres/RepositoriesCached/DataSchemeCachedRepository.cs @@ -1,9 +1,9 @@ using DD.Persistence.Models; -using DD.Persistence.Repository.Repositories; +using DD.Persistence.Database.Postgres.Repositories; using Microsoft.EntityFrameworkCore; using Microsoft.Extensions.Caching.Memory; -namespace DD.Persistence.Repository.RepositoriesCached; +namespace DD.Persistence.Database.Postgres.RepositoriesCached; public class DataSchemeCachedRepository : DataSchemeRepository { private readonly IMemoryCache memoryCache; diff --git a/DD.Persistence.Repository/RepositoriesCached/DataSourceSystemCachedRepository.cs b/DD.Persistence.Database.Postgres/RepositoriesCached/DataSourceSystemCachedRepository.cs similarity index 91% rename from DD.Persistence.Repository/RepositoriesCached/DataSourceSystemCachedRepository.cs rename to DD.Persistence.Database.Postgres/RepositoriesCached/DataSourceSystemCachedRepository.cs index 87e487e..919c3ba 100644 --- a/DD.Persistence.Repository/RepositoriesCached/DataSourceSystemCachedRepository.cs +++ b/DD.Persistence.Database.Postgres/RepositoriesCached/DataSourceSystemCachedRepository.cs @@ -1,10 +1,10 @@ using DD.Persistence.Database.Entity; using DD.Persistence.Models; -using DD.Persistence.Repository.Repositories; +using DD.Persistence.Database.Postgres.Repositories; using Microsoft.EntityFrameworkCore; using Microsoft.Extensions.Caching.Memory; -namespace DD.Persistence.Repository.RepositoriesCached; +namespace DD.Persistence.Database.Postgres.RepositoriesCached; public class DataSourceSystemCachedRepository : DataSourceSystemRepository { private static readonly string SystemCacheKey = $"{typeof(DataSourceSystem).FullName}CacheKey"; diff --git a/DD.Persistence.Repository/RepositoriesCached/TimestampedValuesCachedRepository.cs b/DD.Persistence.Database.Postgres/RepositoriesCached/TimestampedValuesCachedRepository.cs similarity index 98% rename from DD.Persistence.Repository/RepositoriesCached/TimestampedValuesCachedRepository.cs rename to DD.Persistence.Database.Postgres/RepositoriesCached/TimestampedValuesCachedRepository.cs index f81f7a0..2073126 100644 --- a/DD.Persistence.Repository/RepositoriesCached/TimestampedValuesCachedRepository.cs +++ b/DD.Persistence.Database.Postgres/RepositoriesCached/TimestampedValuesCachedRepository.cs @@ -3,7 +3,7 @@ //using DD.Persistence.Repositories; //using Microsoft.EntityFrameworkCore; -//namespace DD.Persistence.Repository.Repositories; +//namespace DD.Persistence.Database.Postgres.Repositories; //public class TimestampedValuesCachedRepository : TimestampedValuesRepository //{ diff --git a/DD.Persistence.Repository.Test/DD.Persistence.Repository.Test.csproj b/DD.Persistence.Repository.Test/DD.Persistence.Repository.Test.csproj index 4f29d86..63b4134 100644 --- a/DD.Persistence.Repository.Test/DD.Persistence.Repository.Test.csproj +++ b/DD.Persistence.Repository.Test/DD.Persistence.Repository.Test.csproj @@ -20,7 +20,6 @@ - diff --git a/DD.Persistence.Repository.Test/SetpointRepositoryShould.cs b/DD.Persistence.Repository.Test/SetpointRepositoryShould.cs index 6b05ff3..44c518a 100644 --- a/DD.Persistence.Repository.Test/SetpointRepositoryShould.cs +++ b/DD.Persistence.Repository.Test/SetpointRepositoryShould.cs @@ -1,12 +1,7 @@ using DD.Persistence.Database.Model; -using DD.Persistence.Repository.Repositories; +using DD.Persistence.Database.Postgres.Repositories; using Shouldly; -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; using System.Text.Json; -using System.Threading.Tasks; namespace DD.Persistence.Repository.Test; public class SetpointRepositoryShould : IClassFixture diff --git a/DD.Persistence.Repository/DD.Persistence.Repository.csproj b/DD.Persistence.Repository/DD.Persistence.Repository.csproj deleted file mode 100644 index 75803db..0000000 --- a/DD.Persistence.Repository/DD.Persistence.Repository.csproj +++ /dev/null @@ -1,19 +0,0 @@ - - - - net9.0 - enable - enable - - - - - - - - - - - - - diff --git a/DD.Persistence.Repository/DependencyInjection.cs b/DD.Persistence.Repository/DependencyInjection.cs deleted file mode 100644 index a6ae2af..0000000 --- a/DD.Persistence.Repository/DependencyInjection.cs +++ /dev/null @@ -1,45 +0,0 @@ -using DD.Persistence.Database.Entity; -using DD.Persistence.Models; -using DD.Persistence.Repositories; -using DD.Persistence.Repository.Repositories; -using DD.Persistence.Repository.RepositoriesCached; -using Mapster; -using Microsoft.Extensions.DependencyInjection; -using System.Reflection; - -namespace DD.Persistence.Repository; -public static class DependencyInjection -{ - public static void MapsterSetup() - { - TypeAdapterConfig.GlobalSettings.Default.Config - .ForType() - .Ignore(dest => dest.System, dest => dest.SystemId); - - TypeAdapterConfig.NewConfig() - .Map(dest => dest.Value, src => new ChangeLogValuesDto() - { - Value = src.Value, - Id = src.Id - }); - } - - public static IServiceCollection AddInfrastructure(this IServiceCollection services) - { - var typeAdapterConfig = TypeAdapterConfig.GlobalSettings; - typeAdapterConfig.RuleMap.Clear(); - typeAdapterConfig.Scan(Assembly.GetExecutingAssembly()); - - MapsterSetup(); - - services.AddTransient(); - services.AddTransient(); - services.AddTransient(); - services.AddTransient(); - services.AddTransient(); - services.AddTransient(); - services.AddTransient(); - - return services; - } -} diff --git a/DD.Persistence.sln b/DD.Persistence.sln index ca91e47..e42f411 100644 --- a/DD.Persistence.sln +++ b/DD.Persistence.sln @@ -7,8 +7,6 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "DD.Persistence", "DD.Persis EndProject Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "DD.Persistence.API", "DD.Persistence.API\DD.Persistence.API.csproj", "{8650A227-929E-45F0-AEF7-2C91F45FE884}" EndProject -Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "DD.Persistence.Repository", "DD.Persistence.Repository\DD.Persistence.Repository.csproj", "{493D6D92-231B-4CB6-831B-BE13884B0DE4}" -EndProject Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "DD.Persistence.Database", "DD.Persistence.Database\DD.Persistence.Database.csproj", "{F77475D1-D074-407A-9D69-2FADDDAE2056}" EndProject Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "DD.Persistence.IntegrationTests", "DD.Persistence.IntegrationTests\DD.Persistence.IntegrationTests.csproj", "{10752C25-3773-4081-A1F2-215A1D950126}" @@ -51,10 +49,6 @@ Global {8650A227-929E-45F0-AEF7-2C91F45FE884}.Debug|Any CPU.Build.0 = Debug|Any CPU {8650A227-929E-45F0-AEF7-2C91F45FE884}.Release|Any CPU.ActiveCfg = Release|Any CPU {8650A227-929E-45F0-AEF7-2C91F45FE884}.Release|Any CPU.Build.0 = Release|Any CPU - {493D6D92-231B-4CB6-831B-BE13884B0DE4}.Debug|Any CPU.ActiveCfg = Debug|Any CPU - {493D6D92-231B-4CB6-831B-BE13884B0DE4}.Debug|Any CPU.Build.0 = Debug|Any CPU - {493D6D92-231B-4CB6-831B-BE13884B0DE4}.Release|Any CPU.ActiveCfg = Release|Any CPU - {493D6D92-231B-4CB6-831B-BE13884B0DE4}.Release|Any CPU.Build.0 = Release|Any CPU {F77475D1-D074-407A-9D69-2FADDDAE2056}.Debug|Any CPU.ActiveCfg = Debug|Any CPU {F77475D1-D074-407A-9D69-2FADDDAE2056}.Debug|Any CPU.Build.0 = Debug|Any CPU {F77475D1-D074-407A-9D69-2FADDDAE2056}.Release|Any CPU.ActiveCfg = Release|Any CPU From 1d0921c3e86b0af37907fb659568252698fd180b Mon Sep 17 00:00:00 2001 From: Roman Efremov Date: Wed, 5 Feb 2025 09:56:49 +0500 Subject: [PATCH 2/7] =?UTF-8?q?=D0=94=D0=BE=D1=80=D0=B0=D0=B1=D0=BE=D1=82?= =?UTF-8?q?=D0=B0=D1=82=D1=8C=20=D1=81=D1=85=D0=B5=D0=BC=D1=83=20=D0=B4?= =?UTF-8?q?=D0=B0=D0=BD=D0=BD=D1=8B=D1=85=20=D0=BF=D0=BE=20=D1=87=D0=B0?= =?UTF-8?q?=D1=81=D1=82=D0=B8=20=D1=85=D1=80=D0=B0=D0=BD=D0=B5=D0=BD=D0=B8?= =?UTF-8?q?=D1=8F=20=D1=82=D0=B8=D0=BF=D0=BE=D0=B2=20=D0=BF=D0=BE=D0=BB?= =?UTF-8?q?=D0=B5=D0=B9=20=D0=B2=20=D1=81=D0=BE=D0=BE=D1=82=D0=B2=D0=B5?= =?UTF-8?q?=D1=82=D1=81=D1=82=D0=B2=D0=B8=D0=B8=20=D1=81=20=D0=B8=D0=BD?= =?UTF-8?q?=D0=B4=D0=B5=D0=BA=D1=81=D0=B0=D1=86=D0=B8=D0=B5=D0=B9?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- ...ner.cs => 20250204044050_Init.Designer.cs} | 7 ++- ...3061429_Init.cs => 20250204044050_Init.cs} | 3 +- ...PersistencePostgresContextModelSnapshot.cs | 5 ++ DD.Persistence.Database/Entity/DataScheme.cs | 6 +- .../TimestampedValuesControllerTest.cs | 3 +- DD.Persistence.Models/DataSchemeDto.cs | 5 ++ .../Enumerations/PropTypeEnum.cs | 14 +++++ .../Services/TimestampedValuesService.cs | 62 ++++++++++++++----- 8 files changed, 84 insertions(+), 21 deletions(-) rename DD.Persistence.Database.Postgres/Migrations/{20250203061429_Init.Designer.cs => 20250204044050_Init.Designer.cs} (97%) rename DD.Persistence.Database.Postgres/Migrations/{20250203061429_Init.cs => 20250204044050_Init.cs} (97%) create mode 100644 DD.Persistence.Models/Enumerations/PropTypeEnum.cs diff --git a/DD.Persistence.Database.Postgres/Migrations/20250203061429_Init.Designer.cs b/DD.Persistence.Database.Postgres/Migrations/20250204044050_Init.Designer.cs similarity index 97% rename from DD.Persistence.Database.Postgres/Migrations/20250203061429_Init.Designer.cs rename to DD.Persistence.Database.Postgres/Migrations/20250204044050_Init.Designer.cs index bdeaf87..60e6e92 100644 --- a/DD.Persistence.Database.Postgres/Migrations/20250203061429_Init.Designer.cs +++ b/DD.Persistence.Database.Postgres/Migrations/20250204044050_Init.Designer.cs @@ -13,7 +13,7 @@ using Npgsql.EntityFrameworkCore.PostgreSQL.Metadata; namespace DD.Persistence.Database.Postgres.Migrations { [DbContext(typeof(PersistencePostgresContext))] - [Migration("20250203061429_Init")] + [Migration("20250204044050_Init")] partial class Init { /// @@ -79,6 +79,11 @@ namespace DD.Persistence.Database.Postgres.Migrations .HasColumnType("jsonb") .HasComment("Наименования полей в порядке индексации"); + b.PrimitiveCollection("PropTypes") + .IsRequired() + .HasColumnType("integer[]") + .HasComment("Типы полей в порядке индексации"); + b.HasKey("DiscriminatorId"); b.ToTable("data_scheme"); diff --git a/DD.Persistence.Database.Postgres/Migrations/20250203061429_Init.cs b/DD.Persistence.Database.Postgres/Migrations/20250204044050_Init.cs similarity index 97% rename from DD.Persistence.Database.Postgres/Migrations/20250203061429_Init.cs rename to DD.Persistence.Database.Postgres/Migrations/20250204044050_Init.cs index df996bc..24a310d 100644 --- a/DD.Persistence.Database.Postgres/Migrations/20250203061429_Init.cs +++ b/DD.Persistence.Database.Postgres/Migrations/20250204044050_Init.cs @@ -35,7 +35,8 @@ namespace DD.Persistence.Database.Postgres.Migrations columns: table => new { DiscriminatorId = table.Column(type: "uuid", nullable: false, comment: "Идентификатор схемы данных"), - PropNames = table.Column(type: "jsonb", nullable: false, comment: "Наименования полей в порядке индексации") + PropNames = table.Column(type: "jsonb", nullable: false, comment: "Наименования полей в порядке индексации"), + PropTypes = table.Column(type: "integer[]", nullable: false, comment: "Типы полей в порядке индексации") }, constraints: table => { diff --git a/DD.Persistence.Database.Postgres/Migrations/PersistencePostgresContextModelSnapshot.cs b/DD.Persistence.Database.Postgres/Migrations/PersistencePostgresContextModelSnapshot.cs index 5c5ad2e..ca319a5 100644 --- a/DD.Persistence.Database.Postgres/Migrations/PersistencePostgresContextModelSnapshot.cs +++ b/DD.Persistence.Database.Postgres/Migrations/PersistencePostgresContextModelSnapshot.cs @@ -76,6 +76,11 @@ namespace DD.Persistence.Database.Postgres.Migrations .HasColumnType("jsonb") .HasComment("Наименования полей в порядке индексации"); + b.PrimitiveCollection("PropTypes") + .IsRequired() + .HasColumnType("integer[]") + .HasComment("Типы полей в порядке индексации"); + b.HasKey("DiscriminatorId"); b.ToTable("data_scheme"); diff --git a/DD.Persistence.Database/Entity/DataScheme.cs b/DD.Persistence.Database/Entity/DataScheme.cs index 75794c0..a231580 100644 --- a/DD.Persistence.Database/Entity/DataScheme.cs +++ b/DD.Persistence.Database/Entity/DataScheme.cs @@ -1,4 +1,5 @@ -using Microsoft.EntityFrameworkCore; +using DD.Persistence.Models; +using Microsoft.EntityFrameworkCore; using System.ComponentModel.DataAnnotations; using System.ComponentModel.DataAnnotations.Schema; @@ -12,4 +13,7 @@ public class DataScheme [Comment("Наименования полей в порядке индексации"), Column(TypeName = "jsonb")] public string[] PropNames { get; set; } = []; + + [Comment("Типы полей в порядке индексации")] + public PropTypeEnum[] PropTypes { get; set; } = []; } diff --git a/DD.Persistence.IntegrationTests/Controllers/TimestampedValuesControllerTest.cs b/DD.Persistence.IntegrationTests/Controllers/TimestampedValuesControllerTest.cs index c6642a5..526b372 100644 --- a/DD.Persistence.IntegrationTests/Controllers/TimestampedValuesControllerTest.cs +++ b/DD.Persistence.IntegrationTests/Controllers/TimestampedValuesControllerTest.cs @@ -3,7 +3,6 @@ using DD.Persistence.Client.Clients; using DD.Persistence.Client.Clients.Interfaces; using DD.Persistence.Client.Clients.Interfaces.Refit; using DD.Persistence.Database.Entity; -using DD.Persistence.Extensions; using DD.Persistence.Models; using Microsoft.Extensions.Caching.Memory; using Microsoft.Extensions.DependencyInjection; @@ -267,7 +266,7 @@ public class TimestampedValuesControllerTest : BaseIntegrationTest var count = 2048; var timestampBegin = DateTimeOffset.UtcNow; var dtos = await AddRange(discriminatorId, count); - + //act var response = await timestampedValuesClient.GetResampledData(discriminatorId, timestampBegin, count); diff --git a/DD.Persistence.Models/DataSchemeDto.cs b/DD.Persistence.Models/DataSchemeDto.cs index d1efdd5..7f238aa 100644 --- a/DD.Persistence.Models/DataSchemeDto.cs +++ b/DD.Persistence.Models/DataSchemeDto.cs @@ -14,4 +14,9 @@ public class DataSchemeDto /// Наименования полей /// public string[] PropNames { get; set; } = []; + + /// + /// Типы полей + /// + public PropTypeEnum[] PropTypes { get; set; } = []; } diff --git a/DD.Persistence.Models/Enumerations/PropTypeEnum.cs b/DD.Persistence.Models/Enumerations/PropTypeEnum.cs new file mode 100644 index 0000000..5379929 --- /dev/null +++ b/DD.Persistence.Models/Enumerations/PropTypeEnum.cs @@ -0,0 +1,14 @@ +namespace DD.Persistence.Models; + +/// +/// Типы для набора данных +/// +public enum PropTypeEnum +{ + /// + String = 0, + /// + Double = 1, + /// + DateTime = 2 +} diff --git a/DD.Persistence/Services/TimestampedValuesService.cs b/DD.Persistence/Services/TimestampedValuesService.cs index cbcb73c..fc17777 100644 --- a/DD.Persistence/Services/TimestampedValuesService.cs +++ b/DD.Persistence/Services/TimestampedValuesService.cs @@ -1,6 +1,5 @@ using DD.Persistence.Extensions; using DD.Persistence.Models; -using DD.Persistence.Models.Common; using DD.Persistence.Repositories; using DD.Persistence.Services.Interfaces; @@ -25,8 +24,7 @@ public class TimestampedValuesService : ITimestampedValuesService // ToDo: реализовать без foreach foreach (var dto in dtos) { - var keys = dto.Values.Keys.ToArray(); - await CreateSystemSpecificationIfNotExist(discriminatorId, keys, token); + await CreateDataSchemeIfNotExist(discriminatorId, dto, token); } var result = await timestampedValuesRepository.AddRange(discriminatorId, dtos, token); @@ -94,7 +92,7 @@ public class TimestampedValuesService : ITimestampedValuesService public async Task> GetGtDate(Guid discriminatorId, DateTimeOffset beginTimestamp, CancellationToken token) { var result = await timestampedValuesRepository.GetGtDate(discriminatorId, beginTimestamp, token); - + var resultToMaterialize = new[] { KeyValuePair.Create(discriminatorId, result) } .ToDictionary(); var dtos = await Materialize(resultToMaterialize, token); @@ -140,37 +138,69 @@ public class TimestampedValuesService : ITimestampedValuesService } /// - /// Создать спецификацию, при отсутствии таковой + /// Создать схему данных, при отсутствии таковой /// - /// Дискриминатор системы - /// Набор наименований полей + /// Дискриминатор схемы + /// Набор данных, по образу которого будет создана соответствующая схема /// /// /// Некорректный набор наименований полей - private async Task CreateSystemSpecificationIfNotExist(Guid discriminatorId, string[] fieldNames, CancellationToken token) + private async Task CreateDataSchemeIfNotExist(Guid discriminatorId, TimestampedValuesDto dto, CancellationToken token) { - var systemSpecification = await dataSchemeRepository.Get(discriminatorId, token); - if (systemSpecification is null) + var propNames = dto.Values.Keys.ToArray(); + var propTypes = GetPropTypes(dto); + + var dataScheme = await dataSchemeRepository.Get(discriminatorId, token); + if (dataScheme is null) { - systemSpecification = new DataSchemeDto() + dataScheme = new DataSchemeDto() { DiscriminatorId = discriminatorId, - PropNames = fieldNames + PropNames = propNames, + PropTypes = propTypes }; - await dataSchemeRepository.Add(systemSpecification, token); + await dataSchemeRepository.Add(dataScheme, token); return; } - if (!systemSpecification.PropNames.SequenceEqual(fieldNames)) + if (!dataScheme.PropNames.SequenceEqual(propNames)) { - var expectedFieldNames = string.Join(", ", systemSpecification.PropNames); - var actualFieldNames = string.Join(", ", fieldNames); + var expectedFieldNames = string.Join(", ", dataScheme.PropNames); + var actualFieldNames = string.Join(", ", propNames); throw new InvalidOperationException($"Для системы {discriminatorId.ToString()} " + $"характерен набор данных: [{expectedFieldNames}], однако был передан набор: [{actualFieldNames}]"); } } + /// + /// Получить типы для набора данных в соответствии с индексацией + /// + /// + /// + /// + private PropTypeEnum[] GetPropTypes(TimestampedValuesDto dto) + { + var types = dto.Values.Select(e => + { + var valueString = e.Value.ToString(); + + if (valueString is null) + throw new ArgumentNullException("Переданный набор данных содержит null, в следствии чего не удаётся определить типы полей"); + + if (DateTimeOffset.TryParse(valueString, out _)) + return PropTypeEnum.DateTime; + + var doubleString = valueString.Replace('.', ','); + if (double.TryParse(doubleString, out _)) + return PropTypeEnum.Double; + + return PropTypeEnum.String; + }); + + return types.ToArray(); + } + /// /// Отсеить лишние поля в соответствии с заданным фильтром /// From 4513de06fa1d532aef0a6d0cd9403aab8dd2aed3 Mon Sep 17 00:00:00 2001 From: Roman Efremov Date: Wed, 5 Feb 2025 12:19:45 +0500 Subject: [PATCH 3/7] =?UTF-8?q?=D0=9F=D0=B5=D1=80=D0=B5=D0=BD=D0=B5=D1=81?= =?UTF-8?q?=D1=82=D0=B8=20=D1=81=D0=BE=D0=B4=D0=B5=D1=80=D0=B6=D0=B8=D0=BC?= =?UTF-8?q?=D0=BE=D0=B5=20=D0=BF=D1=80=D0=BE=D0=B5=D0=BA=D1=82=D0=B0=20DD.?= =?UTF-8?q?Persistence.Repository=20=D0=B2=20DD.Persistence.Database?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- DD.Persistence.API/Startup.cs | 3 +- .../DD.Persistence.Database.Postgres.csproj | 2 - .../DependencyInjection.cs | 33 ------------- .../DD.Persistence.Database.csproj | 2 + .../DependencyInjection.cs | 47 +++++++++++++++++++ .../Extensions/EFExtensionsSortBy.cs | 2 +- .../Helpers/CyclicArray.cs | 0 .../Helpers/QueryBuilders.cs | 0 .../Repositories/ChangeLogRepository.cs | 8 ++-- .../Repositories/DataSchemeRepository.cs | 0 .../DataSourceSystemRepository.cs | 0 .../Repositories/ParameterRepository.cs | 0 .../Repositories/SetpointRepository.cs | 0 .../Repositories/TechMessagesRepository.cs | 0 .../TimestampedValuesRepository.cs | 0 .../DataSchemeCachedRepository.cs | 0 .../DataSourceSystemCachedRepository.cs | 0 .../TimestampedValuesCachedRepository.cs | 0 18 files changed, 56 insertions(+), 41 deletions(-) create mode 100644 DD.Persistence.Database/DependencyInjection.cs rename {DD.Persistence.Database.Postgres => DD.Persistence.Database}/Extensions/EFExtensionsSortBy.cs (99%) rename {DD.Persistence.Database.Postgres => DD.Persistence.Database}/Helpers/CyclicArray.cs (100%) rename {DD.Persistence.Database.Postgres => DD.Persistence.Database}/Helpers/QueryBuilders.cs (100%) rename {DD.Persistence.Database.Postgres => DD.Persistence.Database}/Repositories/ChangeLogRepository.cs (96%) rename {DD.Persistence.Database.Postgres => DD.Persistence.Database}/Repositories/DataSchemeRepository.cs (100%) rename {DD.Persistence.Database.Postgres => DD.Persistence.Database}/Repositories/DataSourceSystemRepository.cs (100%) rename {DD.Persistence.Database.Postgres => DD.Persistence.Database}/Repositories/ParameterRepository.cs (100%) rename {DD.Persistence.Database.Postgres => DD.Persistence.Database}/Repositories/SetpointRepository.cs (100%) rename {DD.Persistence.Database.Postgres => DD.Persistence.Database}/Repositories/TechMessagesRepository.cs (100%) rename {DD.Persistence.Database.Postgres => DD.Persistence.Database}/Repositories/TimestampedValuesRepository.cs (100%) rename {DD.Persistence.Database.Postgres => DD.Persistence.Database}/RepositoriesCached/DataSchemeCachedRepository.cs (100%) rename {DD.Persistence.Database.Postgres => DD.Persistence.Database}/RepositoriesCached/DataSourceSystemCachedRepository.cs (100%) rename {DD.Persistence.Database.Postgres => DD.Persistence.Database}/RepositoriesCached/TimestampedValuesCachedRepository.cs (100%) diff --git a/DD.Persistence.API/Startup.cs b/DD.Persistence.API/Startup.cs index bc78548..a3c3efe 100644 --- a/DD.Persistence.API/Startup.cs +++ b/DD.Persistence.API/Startup.cs @@ -1,4 +1,5 @@ -using DD.Persistence.Database.Model; +using DD.Persistence.Database; +using DD.Persistence.Database.Model; using DD.Persistence.Database.Postgres.Extensions; namespace DD.Persistence.API; diff --git a/DD.Persistence.Database.Postgres/DD.Persistence.Database.Postgres.csproj b/DD.Persistence.Database.Postgres/DD.Persistence.Database.Postgres.csproj index 80b6736..bf406a6 100644 --- a/DD.Persistence.Database.Postgres/DD.Persistence.Database.Postgres.csproj +++ b/DD.Persistence.Database.Postgres/DD.Persistence.Database.Postgres.csproj @@ -7,13 +7,11 @@ - all runtime; build; native; contentfiles; analyzers; buildtransitive - diff --git a/DD.Persistence.Database.Postgres/DependencyInjection.cs b/DD.Persistence.Database.Postgres/DependencyInjection.cs index 0509061..df84bb3 100644 --- a/DD.Persistence.Database.Postgres/DependencyInjection.cs +++ b/DD.Persistence.Database.Postgres/DependencyInjection.cs @@ -24,37 +24,4 @@ public static class DependencyInjection return services; } - - public static void MapsterSetup() - { - TypeAdapterConfig.GlobalSettings.Default.Config - .ForType() - .Ignore(dest => dest.System, dest => dest.SystemId); - - TypeAdapterConfig.NewConfig() - .Map(dest => dest.Value, src => new ChangeLogValuesDto() - { - Value = src.Value, - Id = src.Id - }); - } - - public static IServiceCollection AddInfrastructure(this IServiceCollection services) - { - var typeAdapterConfig = TypeAdapterConfig.GlobalSettings; - typeAdapterConfig.RuleMap.Clear(); - typeAdapterConfig.Scan(Assembly.GetExecutingAssembly()); - - MapsterSetup(); - - services.AddTransient(); - services.AddTransient(); - services.AddTransient(); - services.AddTransient(); - services.AddTransient(); - services.AddTransient(); - services.AddTransient(); - - return services; - } } diff --git a/DD.Persistence.Database/DD.Persistence.Database.csproj b/DD.Persistence.Database/DD.Persistence.Database.csproj index 9303e6a..65f8d54 100644 --- a/DD.Persistence.Database/DD.Persistence.Database.csproj +++ b/DD.Persistence.Database/DD.Persistence.Database.csproj @@ -7,11 +7,13 @@ + all runtime; build; native; contentfiles; analyzers; buildtransitive + diff --git a/DD.Persistence.Database/DependencyInjection.cs b/DD.Persistence.Database/DependencyInjection.cs new file mode 100644 index 0000000..c04d9e5 --- /dev/null +++ b/DD.Persistence.Database/DependencyInjection.cs @@ -0,0 +1,47 @@ +using DD.Persistence.Database.Entity; +using DD.Persistence.Database.Postgres.Repositories; +using DD.Persistence.Database.Postgres.RepositoriesCached; +using DD.Persistence.Database.Repositories; +using DD.Persistence.Models; +using DD.Persistence.Repositories; +using Mapster; +using Microsoft.Extensions.DependencyInjection; +using System.Reflection; + +namespace DD.Persistence.Database; + +public static class DependencyInjection +{ + public static void MapsterSetup() + { + TypeAdapterConfig.GlobalSettings.Default.Config + .ForType() + .Ignore(dest => dest.System, dest => dest.SystemId); + + TypeAdapterConfig.NewConfig() + .Map(dest => dest.Value, src => new ChangeLogValuesDto() + { + Value = src.Value, + Id = src.Id + }); + } + + public static IServiceCollection AddInfrastructure(this IServiceCollection services) + { + var typeAdapterConfig = TypeAdapterConfig.GlobalSettings; + typeAdapterConfig.RuleMap.Clear(); + typeAdapterConfig.Scan(Assembly.GetExecutingAssembly()); + + MapsterSetup(); + + services.AddTransient(); + services.AddTransient(); + services.AddTransient(); + services.AddTransient(); + services.AddTransient(); + services.AddTransient(); + services.AddTransient(); + + return services; + } +} diff --git a/DD.Persistence.Database.Postgres/Extensions/EFExtensionsSortBy.cs b/DD.Persistence.Database/Extensions/EFExtensionsSortBy.cs similarity index 99% rename from DD.Persistence.Database.Postgres/Extensions/EFExtensionsSortBy.cs rename to DD.Persistence.Database/Extensions/EFExtensionsSortBy.cs index 3af7ae0..10818a4 100644 --- a/DD.Persistence.Database.Postgres/Extensions/EFExtensionsSortBy.cs +++ b/DD.Persistence.Database/Extensions/EFExtensionsSortBy.cs @@ -2,7 +2,7 @@ using System.Collections.Concurrent; using System.Linq.Expressions; using System.Reflection; -namespace DD.Persistence.Database.Postgres.Extensions; +namespace DD.Persistence.Database.Extensions; public static class EFExtensionsSortBy { diff --git a/DD.Persistence.Database.Postgres/Helpers/CyclicArray.cs b/DD.Persistence.Database/Helpers/CyclicArray.cs similarity index 100% rename from DD.Persistence.Database.Postgres/Helpers/CyclicArray.cs rename to DD.Persistence.Database/Helpers/CyclicArray.cs diff --git a/DD.Persistence.Database.Postgres/Helpers/QueryBuilders.cs b/DD.Persistence.Database/Helpers/QueryBuilders.cs similarity index 100% rename from DD.Persistence.Database.Postgres/Helpers/QueryBuilders.cs rename to DD.Persistence.Database/Helpers/QueryBuilders.cs diff --git a/DD.Persistence.Database.Postgres/Repositories/ChangeLogRepository.cs b/DD.Persistence.Database/Repositories/ChangeLogRepository.cs similarity index 96% rename from DD.Persistence.Database.Postgres/Repositories/ChangeLogRepository.cs rename to DD.Persistence.Database/Repositories/ChangeLogRepository.cs index c2502ef..61e907d 100644 --- a/DD.Persistence.Database.Postgres/Repositories/ChangeLogRepository.cs +++ b/DD.Persistence.Database/Repositories/ChangeLogRepository.cs @@ -8,7 +8,7 @@ using Mapster; using Microsoft.EntityFrameworkCore; using UuidExtensions; -namespace DD.Persistence.Database.Postgres.Repositories; +namespace DD.Persistence.Database.Repositories; public class ChangeLogRepository : IChangeLogRepository { private readonly DbContext db; @@ -186,7 +186,7 @@ public class ChangeLogRepository : IChangeLogRepository var datesUpdate = await datesUpdateQuery.ToArrayAsync(token); - var dates = Enumerable.Concat(datesCreate, datesUpdate); + var dates = datesCreate.Concat(datesUpdate); var datesOnly = dates .Select(d => new DateOnly(d.Year, d.Month, d.Day)) .Distinct() @@ -214,7 +214,7 @@ public class ChangeLogRepository : IChangeLogRepository public async Task> GetGtDate(Guid idDiscriminator, DateTimeOffset dateBegin, CancellationToken token) { var date = dateBegin.ToUniversalTime(); - var query = this.db.Set() + var query = db.Set() .Where(e => e.IdDiscriminator == idDiscriminator) .Where(e => e.Creation >= date || e.Obsolete >= date); @@ -233,7 +233,7 @@ public class ChangeLogRepository : IChangeLogRepository .Select(group => new { Min = group.Min(e => e.Creation), - Max = group.Max(e => (e.Obsolete.HasValue && e.Obsolete > e.Creation) + Max = group.Max(e => e.Obsolete.HasValue && e.Obsolete > e.Creation ? e.Obsolete.Value : e.Creation), }); diff --git a/DD.Persistence.Database.Postgres/Repositories/DataSchemeRepository.cs b/DD.Persistence.Database/Repositories/DataSchemeRepository.cs similarity index 100% rename from DD.Persistence.Database.Postgres/Repositories/DataSchemeRepository.cs rename to DD.Persistence.Database/Repositories/DataSchemeRepository.cs diff --git a/DD.Persistence.Database.Postgres/Repositories/DataSourceSystemRepository.cs b/DD.Persistence.Database/Repositories/DataSourceSystemRepository.cs similarity index 100% rename from DD.Persistence.Database.Postgres/Repositories/DataSourceSystemRepository.cs rename to DD.Persistence.Database/Repositories/DataSourceSystemRepository.cs diff --git a/DD.Persistence.Database.Postgres/Repositories/ParameterRepository.cs b/DD.Persistence.Database/Repositories/ParameterRepository.cs similarity index 100% rename from DD.Persistence.Database.Postgres/Repositories/ParameterRepository.cs rename to DD.Persistence.Database/Repositories/ParameterRepository.cs diff --git a/DD.Persistence.Database.Postgres/Repositories/SetpointRepository.cs b/DD.Persistence.Database/Repositories/SetpointRepository.cs similarity index 100% rename from DD.Persistence.Database.Postgres/Repositories/SetpointRepository.cs rename to DD.Persistence.Database/Repositories/SetpointRepository.cs diff --git a/DD.Persistence.Database.Postgres/Repositories/TechMessagesRepository.cs b/DD.Persistence.Database/Repositories/TechMessagesRepository.cs similarity index 100% rename from DD.Persistence.Database.Postgres/Repositories/TechMessagesRepository.cs rename to DD.Persistence.Database/Repositories/TechMessagesRepository.cs diff --git a/DD.Persistence.Database.Postgres/Repositories/TimestampedValuesRepository.cs b/DD.Persistence.Database/Repositories/TimestampedValuesRepository.cs similarity index 100% rename from DD.Persistence.Database.Postgres/Repositories/TimestampedValuesRepository.cs rename to DD.Persistence.Database/Repositories/TimestampedValuesRepository.cs diff --git a/DD.Persistence.Database.Postgres/RepositoriesCached/DataSchemeCachedRepository.cs b/DD.Persistence.Database/RepositoriesCached/DataSchemeCachedRepository.cs similarity index 100% rename from DD.Persistence.Database.Postgres/RepositoriesCached/DataSchemeCachedRepository.cs rename to DD.Persistence.Database/RepositoriesCached/DataSchemeCachedRepository.cs diff --git a/DD.Persistence.Database.Postgres/RepositoriesCached/DataSourceSystemCachedRepository.cs b/DD.Persistence.Database/RepositoriesCached/DataSourceSystemCachedRepository.cs similarity index 100% rename from DD.Persistence.Database.Postgres/RepositoriesCached/DataSourceSystemCachedRepository.cs rename to DD.Persistence.Database/RepositoriesCached/DataSourceSystemCachedRepository.cs diff --git a/DD.Persistence.Database.Postgres/RepositoriesCached/TimestampedValuesCachedRepository.cs b/DD.Persistence.Database/RepositoriesCached/TimestampedValuesCachedRepository.cs similarity index 100% rename from DD.Persistence.Database.Postgres/RepositoriesCached/TimestampedValuesCachedRepository.cs rename to DD.Persistence.Database/RepositoriesCached/TimestampedValuesCachedRepository.cs From 431c7278cb7ff63c66c764739617515c47cbbda4 Mon Sep 17 00:00:00 2001 From: Roman Efremov Date: Wed, 5 Feb 2025 14:30:36 +0500 Subject: [PATCH 4/7] =?UTF-8?q?=D0=9F=D1=80=D0=B0=D0=B2=D0=BA=D0=B8=20?= =?UTF-8?q?=D0=BF=D0=BE=20=D1=80=D0=B5=D0=B2=D1=8C=D1=8E=20#1?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- DD.Persistence.Database/Entity/DataScheme.cs | 23 +++++++++++-------- .../TimestampedValuesRepository.cs | 9 -------- .../Services/TimestampedValuesService.cs | 3 +++ 3 files changed, 16 insertions(+), 19 deletions(-) diff --git a/DD.Persistence.Database/Entity/DataScheme.cs b/DD.Persistence.Database/Entity/DataScheme.cs index a231580..3ce46a2 100644 --- a/DD.Persistence.Database/Entity/DataScheme.cs +++ b/DD.Persistence.Database/Entity/DataScheme.cs @@ -1,19 +1,22 @@ -using DD.Persistence.Models; -using Microsoft.EntityFrameworkCore; -using System.ComponentModel.DataAnnotations; +using Microsoft.EntityFrameworkCore; using System.ComponentModel.DataAnnotations.Schema; +using System.Text.Json; namespace DD.Persistence.Database.Entity; -[Table("data_scheme")] -public class DataScheme +[Table("prop_scheme")] +[PrimaryKey(nameof(DiscriminatorId), nameof(Index))] +public class PropScheme { - [Key, Comment("Идентификатор схемы данных"),] + [Comment("Идентификатор схемы данных")] public Guid DiscriminatorId { get; set; } - [Comment("Наименования полей в порядке индексации"), Column(TypeName = "jsonb")] - public string[] PropNames { get; set; } = []; + [Comment("Индекс поля")] + public int Index { get; set; } - [Comment("Типы полей в порядке индексации")] - public PropTypeEnum[] PropTypes { get; set; } = []; + [Comment("Наименования индексируемого поля")] + public required string PropName { get; set; } + + [Comment("Тип индексируемого поля")] + public required JsonValueKind PropKind { get; set; } } diff --git a/DD.Persistence.Database/Repositories/TimestampedValuesRepository.cs b/DD.Persistence.Database/Repositories/TimestampedValuesRepository.cs index 149e411..1239b4a 100644 --- a/DD.Persistence.Database/Repositories/TimestampedValuesRepository.cs +++ b/DD.Persistence.Database/Repositories/TimestampedValuesRepository.cs @@ -55,15 +55,6 @@ public class TimestampedValuesRepository : ITimestampedValuesRepository .Select(g => KeyValuePair.Create(g.Key, g.OrderBy(i => i.Timestamp).Skip(skip).Take(take))); var entities = await groupQuery.ToArrayAsync(token); - //var root = new TVertex( - // OperationEnum.And, - // new TLeaf(OperationEnum.Equal, "A", 1), - // new TLeaf(OperationEnum.Equal, "B", 1) - //); - //var dataScheme = entities.First().Value.First().DataScheme; - //var specification = dataScheme.BuildFilter(root); - //var que = ApplySpecification(specification); - var result = entities.ToDictionary(k => k.Key, v => v.Value.Select(e => ( e.Timestamp, e.Values diff --git a/DD.Persistence/Services/TimestampedValuesService.cs b/DD.Persistence/Services/TimestampedValuesService.cs index fc17777..264fdc5 100644 --- a/DD.Persistence/Services/TimestampedValuesService.cs +++ b/DD.Persistence/Services/TimestampedValuesService.cs @@ -2,6 +2,7 @@ using DD.Persistence.Models; using DD.Persistence.Repositories; using DD.Persistence.Services.Interfaces; +using System.Text.Json; namespace DD.Persistence.Services; @@ -100,6 +101,7 @@ public class TimestampedValuesService : ITimestampedValuesService return dtos; } + // ToDo: рефакторинг, переименовать (текущее название не отражает суть) /// /// Преобразовать результат запроса в набор dto /// @@ -183,6 +185,7 @@ public class TimestampedValuesService : ITimestampedValuesService { var types = dto.Values.Select(e => { + var objectKind = ((JsonElement) e.Value).ValueKind; var valueString = e.Value.ToString(); if (valueString is null) From 9ca49cb1b517355b74d2d7fcece2bb227f60cb36 Mon Sep 17 00:00:00 2001 From: Roman Efremov Date: Wed, 5 Feb 2025 17:20:18 +0500 Subject: [PATCH 5/7] =?UTF-8?q?=D0=9F=D1=80=D0=B0=D0=B2=D0=BA=D0=B8=20?= =?UTF-8?q?=D0=BF=D0=BE=20=D1=80=D0=B5=D0=B2=D1=8C=D1=8E=20#2?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- DD.Persistence.API/Startup.cs | 2 +- ...ner.cs => 20250205114037_Init.Designer.cs} | 59 ++++++------- ...4044050_Init.cs => 20250205114037_Init.cs} | 39 ++++----- ...PersistencePostgresContextModelSnapshot.cs | 57 ++++++------ .../DependencyInjection.cs | 9 +- .../{DataScheme.cs => SchemeProperty.cs} | 9 +- .../Entity/TimestampedValues.cs | 3 - .../PersistenceDbContext.cs | 6 +- .../Repositories/DataSchemeRepository.cs | 34 -------- .../Repositories/SchemePropertyRepository.cs | 43 ++++++++++ .../TimestampedValuesRepository.cs | 3 +- ...y.cs => SchemePropertyCachedRepository.cs} | 12 +-- .../TimestampedValuesControllerTest.cs | 6 +- DD.Persistence.Models/DataSchemeDto.cs | 36 ++++++-- .../Enumerations/PropTypeEnum.cs | 14 --- DD.Persistence.Models/SchemePropertyDto.cs | 30 +++++++ .../TimestampedValuesServiceShould.cs | 2 +- ...sitory.cs => ISchemePropertyRepository.cs} | 4 +- .../Services/TimestampedValuesService.cs | 86 ++++++------------- 19 files changed, 221 insertions(+), 233 deletions(-) rename DD.Persistence.Database.Postgres/Migrations/{20250204044050_Init.Designer.cs => 20250205114037_Init.Designer.cs} (88%) rename DD.Persistence.Database.Postgres/Migrations/{20250204044050_Init.cs => 20250205114037_Init.cs} (90%) rename DD.Persistence.Database/Entity/{DataScheme.cs => SchemeProperty.cs} (71%) delete mode 100644 DD.Persistence.Database/Repositories/DataSchemeRepository.cs create mode 100644 DD.Persistence.Database/Repositories/SchemePropertyRepository.cs rename DD.Persistence.Database/RepositoriesCached/{DataSchemeCachedRepository.cs => SchemePropertyCachedRepository.cs} (57%) delete mode 100644 DD.Persistence.Models/Enumerations/PropTypeEnum.cs create mode 100644 DD.Persistence.Models/SchemePropertyDto.cs rename DD.Persistence/Repositories/{IDataSchemeRepository.cs => ISchemePropertyRepository.cs} (84%) diff --git a/DD.Persistence.API/Startup.cs b/DD.Persistence.API/Startup.cs index a3c3efe..f19e6cf 100644 --- a/DD.Persistence.API/Startup.cs +++ b/DD.Persistence.API/Startup.cs @@ -14,7 +14,7 @@ public class Startup public void ConfigureServices(IServiceCollection services) { - // Add services to the container. + // AddRange services to the container. services.AddControllers(); // Learn more about configuring Swagger/OpenAPI at https://aka.ms/aspnetcore/swashbuckle diff --git a/DD.Persistence.Database.Postgres/Migrations/20250204044050_Init.Designer.cs b/DD.Persistence.Database.Postgres/Migrations/20250205114037_Init.Designer.cs similarity index 88% rename from DD.Persistence.Database.Postgres/Migrations/20250204044050_Init.Designer.cs rename to DD.Persistence.Database.Postgres/Migrations/20250205114037_Init.Designer.cs index 60e6e92..b90d452 100644 --- a/DD.Persistence.Database.Postgres/Migrations/20250204044050_Init.Designer.cs +++ b/DD.Persistence.Database.Postgres/Migrations/20250205114037_Init.Designer.cs @@ -13,7 +13,7 @@ using Npgsql.EntityFrameworkCore.PostgreSQL.Metadata; namespace DD.Persistence.Database.Postgres.Migrations { [DbContext(typeof(PersistencePostgresContext))] - [Migration("20250204044050_Init")] + [Migration("20250205114037_Init")] partial class Init { /// @@ -67,28 +67,6 @@ namespace DD.Persistence.Database.Postgres.Migrations b.ToTable("change_log"); }); - modelBuilder.Entity("DD.Persistence.Database.Entity.DataScheme", b => - { - b.Property("DiscriminatorId") - .ValueGeneratedOnAdd() - .HasColumnType("uuid") - .HasComment("Идентификатор схемы данных"); - - b.Property("PropNames") - .IsRequired() - .HasColumnType("jsonb") - .HasComment("Наименования полей в порядке индексации"); - - b.PrimitiveCollection("PropTypes") - .IsRequired() - .HasColumnType("integer[]") - .HasComment("Типы полей в порядке индексации"); - - b.HasKey("DiscriminatorId"); - - b.ToTable("data_scheme"); - }); - modelBuilder.Entity("DD.Persistence.Database.Entity.DataSourceSystem", b => { b.Property("SystemId") @@ -134,6 +112,30 @@ namespace DD.Persistence.Database.Postgres.Migrations b.ToTable("parameter_data"); }); + modelBuilder.Entity("DD.Persistence.Database.Entity.SchemeProperty", b => + { + b.Property("DiscriminatorId") + .HasColumnType("uuid") + .HasComment("Идентификатор схемы данных"); + + b.Property("Index") + .HasColumnType("integer") + .HasComment("Индекс поля"); + + b.Property("PropertyKind") + .HasColumnType("smallint") + .HasComment("Тип индексируемого поля"); + + b.Property("PropertyName") + .IsRequired() + .HasColumnType("text") + .HasComment("Наименования индексируемого поля"); + + b.HasKey("DiscriminatorId", "Index"); + + b.ToTable("scheme_property"); + }); + modelBuilder.Entity("DD.Persistence.Database.Entity.Setpoint", b => { b.Property("Key") @@ -222,17 +224,6 @@ namespace DD.Persistence.Database.Postgres.Migrations b.Navigation("System"); }); - - modelBuilder.Entity("DD.Persistence.Database.Entity.TimestampedValues", b => - { - b.HasOne("DD.Persistence.Database.Entity.DataScheme", "DataScheme") - .WithMany() - .HasForeignKey("DiscriminatorId") - .OnDelete(DeleteBehavior.Cascade) - .IsRequired(); - - b.Navigation("DataScheme"); - }); #pragma warning restore 612, 618 } } diff --git a/DD.Persistence.Database.Postgres/Migrations/20250204044050_Init.cs b/DD.Persistence.Database.Postgres/Migrations/20250205114037_Init.cs similarity index 90% rename from DD.Persistence.Database.Postgres/Migrations/20250204044050_Init.cs rename to DD.Persistence.Database.Postgres/Migrations/20250205114037_Init.cs index 24a310d..c872547 100644 --- a/DD.Persistence.Database.Postgres/Migrations/20250204044050_Init.cs +++ b/DD.Persistence.Database.Postgres/Migrations/20250205114037_Init.cs @@ -30,19 +30,6 @@ namespace DD.Persistence.Database.Postgres.Migrations table.PrimaryKey("PK_change_log", x => x.Id); }); - migrationBuilder.CreateTable( - name: "data_scheme", - columns: table => new - { - DiscriminatorId = table.Column(type: "uuid", nullable: false, comment: "Идентификатор схемы данных"), - PropNames = table.Column(type: "jsonb", nullable: false, comment: "Наименования полей в порядке индексации"), - PropTypes = table.Column(type: "integer[]", nullable: false, comment: "Типы полей в порядке индексации") - }, - constraints: table => - { - table.PrimaryKey("PK_data_scheme", x => x.DiscriminatorId); - }); - migrationBuilder.CreateTable( name: "data_source_system", columns: table => new @@ -70,6 +57,20 @@ namespace DD.Persistence.Database.Postgres.Migrations table.PrimaryKey("PK_parameter_data", x => new { x.DiscriminatorId, x.ParameterId, x.Timestamp }); }); + migrationBuilder.CreateTable( + name: "scheme_property", + columns: table => new + { + DiscriminatorId = table.Column(type: "uuid", nullable: false, comment: "Идентификатор схемы данных"), + Index = table.Column(type: "integer", nullable: false, comment: "Индекс поля"), + PropertyName = table.Column(type: "text", nullable: false, comment: "Наименования индексируемого поля"), + PropertyKind = table.Column(type: "smallint", nullable: false, comment: "Тип индексируемого поля") + }, + constraints: table => + { + table.PrimaryKey("PK_scheme_property", x => new { x.DiscriminatorId, x.Index }); + }); + migrationBuilder.CreateTable( name: "setpoint", columns: table => new @@ -95,12 +96,6 @@ namespace DD.Persistence.Database.Postgres.Migrations constraints: table => { table.PrimaryKey("PK_timestamped_values", x => new { x.DiscriminatorId, x.Timestamp }); - table.ForeignKey( - name: "FK_timestamped_values_data_scheme_DiscriminatorId", - column: x => x.DiscriminatorId, - principalTable: "data_scheme", - principalColumn: "DiscriminatorId", - onDelete: ReferentialAction.Cascade); }); migrationBuilder.CreateTable( @@ -140,6 +135,9 @@ namespace DD.Persistence.Database.Postgres.Migrations migrationBuilder.DropTable( name: "parameter_data"); + migrationBuilder.DropTable( + name: "scheme_property"); + migrationBuilder.DropTable( name: "setpoint"); @@ -151,9 +149,6 @@ namespace DD.Persistence.Database.Postgres.Migrations migrationBuilder.DropTable( name: "data_source_system"); - - migrationBuilder.DropTable( - name: "data_scheme"); } } } diff --git a/DD.Persistence.Database.Postgres/Migrations/PersistencePostgresContextModelSnapshot.cs b/DD.Persistence.Database.Postgres/Migrations/PersistencePostgresContextModelSnapshot.cs index ca319a5..e2b0921 100644 --- a/DD.Persistence.Database.Postgres/Migrations/PersistencePostgresContextModelSnapshot.cs +++ b/DD.Persistence.Database.Postgres/Migrations/PersistencePostgresContextModelSnapshot.cs @@ -64,28 +64,6 @@ namespace DD.Persistence.Database.Postgres.Migrations b.ToTable("change_log"); }); - modelBuilder.Entity("DD.Persistence.Database.Entity.DataScheme", b => - { - b.Property("DiscriminatorId") - .ValueGeneratedOnAdd() - .HasColumnType("uuid") - .HasComment("Идентификатор схемы данных"); - - b.Property("PropNames") - .IsRequired() - .HasColumnType("jsonb") - .HasComment("Наименования полей в порядке индексации"); - - b.PrimitiveCollection("PropTypes") - .IsRequired() - .HasColumnType("integer[]") - .HasComment("Типы полей в порядке индексации"); - - b.HasKey("DiscriminatorId"); - - b.ToTable("data_scheme"); - }); - modelBuilder.Entity("DD.Persistence.Database.Entity.DataSourceSystem", b => { b.Property("SystemId") @@ -131,6 +109,30 @@ namespace DD.Persistence.Database.Postgres.Migrations b.ToTable("parameter_data"); }); + modelBuilder.Entity("DD.Persistence.Database.Entity.SchemeProperty", b => + { + b.Property("DiscriminatorId") + .HasColumnType("uuid") + .HasComment("Идентификатор схемы данных"); + + b.Property("Index") + .HasColumnType("integer") + .HasComment("Индекс поля"); + + b.Property("PropertyKind") + .HasColumnType("smallint") + .HasComment("Тип индексируемого поля"); + + b.Property("PropertyName") + .IsRequired() + .HasColumnType("text") + .HasComment("Наименования индексируемого поля"); + + b.HasKey("DiscriminatorId", "Index"); + + b.ToTable("scheme_property"); + }); + modelBuilder.Entity("DD.Persistence.Database.Entity.Setpoint", b => { b.Property("Key") @@ -219,17 +221,6 @@ namespace DD.Persistence.Database.Postgres.Migrations b.Navigation("System"); }); - - modelBuilder.Entity("DD.Persistence.Database.Entity.TimestampedValues", b => - { - b.HasOne("DD.Persistence.Database.Entity.DataScheme", "DataScheme") - .WithMany() - .HasForeignKey("DiscriminatorId") - .OnDelete(DeleteBehavior.Cascade) - .IsRequired(); - - b.Navigation("DataScheme"); - }); #pragma warning restore 612, 618 } } diff --git a/DD.Persistence.Database/DependencyInjection.cs b/DD.Persistence.Database/DependencyInjection.cs index c04d9e5..ca140d8 100644 --- a/DD.Persistence.Database/DependencyInjection.cs +++ b/DD.Persistence.Database/DependencyInjection.cs @@ -2,6 +2,7 @@ using DD.Persistence.Database.Postgres.Repositories; using DD.Persistence.Database.Postgres.RepositoriesCached; using DD.Persistence.Database.Repositories; +using DD.Persistence.Database.RepositoriesCached; using DD.Persistence.Models; using DD.Persistence.Repositories; using Mapster; @@ -24,6 +25,12 @@ public static class DependencyInjection Value = src.Value, Id = src.Id }); + + TypeAdapterConfig, SchemeProperty>.NewConfig() + .Map(dest => dest.DiscriminatorId, src => src.Key) + .Map(dest => dest.Index, src => src.Value.Index) + .Map(dest => dest.PropertyKind, src => src.Value.PropertyKind) + .Map(dest => dest.PropertyName, src => src.Value.PropertyName); } public static IServiceCollection AddInfrastructure(this IServiceCollection services) @@ -40,7 +47,7 @@ public static class DependencyInjection services.AddTransient(); services.AddTransient(); services.AddTransient(); - services.AddTransient(); + services.AddTransient(); return services; } diff --git a/DD.Persistence.Database/Entity/DataScheme.cs b/DD.Persistence.Database/Entity/SchemeProperty.cs similarity index 71% rename from DD.Persistence.Database/Entity/DataScheme.cs rename to DD.Persistence.Database/Entity/SchemeProperty.cs index 3ce46a2..6ef5bdb 100644 --- a/DD.Persistence.Database/Entity/DataScheme.cs +++ b/DD.Persistence.Database/Entity/SchemeProperty.cs @@ -1,12 +1,13 @@ using Microsoft.EntityFrameworkCore; +using System.ComponentModel.DataAnnotations; using System.ComponentModel.DataAnnotations.Schema; using System.Text.Json; namespace DD.Persistence.Database.Entity; -[Table("prop_scheme")] +[Table("scheme_property")] [PrimaryKey(nameof(DiscriminatorId), nameof(Index))] -public class PropScheme +public class SchemeProperty { [Comment("Идентификатор схемы данных")] public Guid DiscriminatorId { get; set; } @@ -15,8 +16,8 @@ public class PropScheme public int Index { get; set; } [Comment("Наименования индексируемого поля")] - public required string PropName { get; set; } + public required string PropertyName { get; set; } [Comment("Тип индексируемого поля")] - public required JsonValueKind PropKind { get; set; } + public required JsonValueKind PropertyKind { get; set; } } diff --git a/DD.Persistence.Database/Entity/TimestampedValues.cs b/DD.Persistence.Database/Entity/TimestampedValues.cs index a2835f7..d28e1cf 100644 --- a/DD.Persistence.Database/Entity/TimestampedValues.cs +++ b/DD.Persistence.Database/Entity/TimestampedValues.cs @@ -17,7 +17,4 @@ public class TimestampedValues : ITimestampedItem [Comment("Данные"), Column(TypeName = "jsonb")] public required object[] Values { get; set; } - - [Required, ForeignKey(nameof(DiscriminatorId)), Comment("Идентификаторы")] - public virtual DataScheme? DataScheme { get; set; } } diff --git a/DD.Persistence.Database/PersistenceDbContext.cs b/DD.Persistence.Database/PersistenceDbContext.cs index fbbc057..4b0a874 100644 --- a/DD.Persistence.Database/PersistenceDbContext.cs +++ b/DD.Persistence.Database/PersistenceDbContext.cs @@ -10,7 +10,7 @@ public class PersistenceDbContext : DbContext { public DbSet Setpoint => Set(); - public DbSet DataSchemes => Set(); + public DbSet SchemeProperty => Set(); public DbSet TimestampedValues => Set(); @@ -30,10 +30,6 @@ public class PersistenceDbContext : DbContext protected override void OnModelCreating(ModelBuilder modelBuilder) { - modelBuilder.Entity() - .Property(e => e.PropNames) - .HasJsonConversion(); - modelBuilder.Entity() .Property(e => e.Values) .HasJsonConversion(); diff --git a/DD.Persistence.Database/Repositories/DataSchemeRepository.cs b/DD.Persistence.Database/Repositories/DataSchemeRepository.cs deleted file mode 100644 index ba5ccd7..0000000 --- a/DD.Persistence.Database/Repositories/DataSchemeRepository.cs +++ /dev/null @@ -1,34 +0,0 @@ -using DD.Persistence.Database.Entity; -using DD.Persistence.Models; -using DD.Persistence.Repositories; -using Mapster; -using Microsoft.EntityFrameworkCore; - -namespace DD.Persistence.Database.Postgres.Repositories; -public class DataSchemeRepository : IDataSchemeRepository -{ - protected DbContext db; - public DataSchemeRepository(DbContext db) - { - this.db = db; - } - protected virtual IQueryable GetQueryReadOnly() => db.Set(); - - public virtual async Task Add(DataSchemeDto dataSourceSystemDto, CancellationToken token) - { - var entity = dataSourceSystemDto.Adapt(); - - await db.Set().AddAsync(entity, token); - await db.SaveChangesAsync(token); - } - - public virtual async Task Get(Guid dataSchemeId, CancellationToken token) - { - var query = GetQueryReadOnly() - .Where(e => e.DiscriminatorId == dataSchemeId); - var entity = await query.ToArrayAsync(); - var dto = entity.Select(e => e.Adapt()).FirstOrDefault(); - - return dto; - } -} diff --git a/DD.Persistence.Database/Repositories/SchemePropertyRepository.cs b/DD.Persistence.Database/Repositories/SchemePropertyRepository.cs new file mode 100644 index 0000000..26bb8aa --- /dev/null +++ b/DD.Persistence.Database/Repositories/SchemePropertyRepository.cs @@ -0,0 +1,43 @@ +using DD.Persistence.Database.Entity; +using DD.Persistence.Models; +using DD.Persistence.Repositories; +using Mapster; +using Microsoft.EntityFrameworkCore; + +namespace DD.Persistence.Database.Repositories; +public class SchemePropertyRepository : ISchemePropertyRepository +{ + protected DbContext db; + public SchemePropertyRepository(DbContext db) + { + this.db = db; + } + protected virtual IQueryable GetQueryReadOnly() => db.Set(); + + public virtual async Task AddRange(DataSchemeDto dataSchemeDto, CancellationToken token) + { + var entities = dataSchemeDto.Select(e => + KeyValuePair.Create(dataSchemeDto.DiscriminatorId, e) + .Adapt() + ); + + await db.Set().AddRangeAsync(entities, token); + await db.SaveChangesAsync(token); + } + + public virtual async Task Get(Guid dataSchemeId, CancellationToken token) + { + var query = GetQueryReadOnly() + .Where(e => e.DiscriminatorId == dataSchemeId); + var entities = await query.ToArrayAsync(token); + + DataSchemeDto? result = null; + if (entities.Length != 0) + { + var properties = entities.Select(e => e.Adapt()).ToArray(); + result = new DataSchemeDto(dataSchemeId, properties); + } + + return result; + } +} diff --git a/DD.Persistence.Database/Repositories/TimestampedValuesRepository.cs b/DD.Persistence.Database/Repositories/TimestampedValuesRepository.cs index 1239b4a..5f3f60e 100644 --- a/DD.Persistence.Database/Repositories/TimestampedValuesRepository.cs +++ b/DD.Persistence.Database/Repositories/TimestampedValuesRepository.cs @@ -14,8 +14,7 @@ public class TimestampedValuesRepository : ITimestampedValuesRepository this.db = db; } - protected virtual IQueryable GetQueryReadOnly() => this.db.Set() - .Include(e => e.DataScheme); + protected virtual IQueryable GetQueryReadOnly() => this.db.Set(); public async virtual Task AddRange(Guid discriminatorId, IEnumerable dtos, CancellationToken token) { diff --git a/DD.Persistence.Database/RepositoriesCached/DataSchemeCachedRepository.cs b/DD.Persistence.Database/RepositoriesCached/SchemePropertyCachedRepository.cs similarity index 57% rename from DD.Persistence.Database/RepositoriesCached/DataSchemeCachedRepository.cs rename to DD.Persistence.Database/RepositoriesCached/SchemePropertyCachedRepository.cs index f4cec62..64d9c01 100644 --- a/DD.Persistence.Database/RepositoriesCached/DataSchemeCachedRepository.cs +++ b/DD.Persistence.Database/RepositoriesCached/SchemePropertyCachedRepository.cs @@ -1,21 +1,21 @@ using DD.Persistence.Models; -using DD.Persistence.Database.Postgres.Repositories; using Microsoft.EntityFrameworkCore; using Microsoft.Extensions.Caching.Memory; +using DD.Persistence.Database.Repositories; -namespace DD.Persistence.Database.Postgres.RepositoriesCached; -public class DataSchemeCachedRepository : DataSchemeRepository +namespace DD.Persistence.Database.RepositoriesCached; +public class SchemePropertyCachedRepository : SchemePropertyRepository { private readonly IMemoryCache memoryCache; - public DataSchemeCachedRepository(DbContext db, IMemoryCache memoryCache) : base(db) + public SchemePropertyCachedRepository(DbContext db, IMemoryCache memoryCache) : base(db) { this.memoryCache = memoryCache; } - public override async Task Add(DataSchemeDto dataSourceSystemDto, CancellationToken token) + public override async Task AddRange(DataSchemeDto dataSourceSystemDto, CancellationToken token) { - await base.Add(dataSourceSystemDto, token); + await base.AddRange(dataSourceSystemDto, token); memoryCache.Set(dataSourceSystemDto.DiscriminatorId, dataSourceSystemDto); } diff --git a/DD.Persistence.IntegrationTests/Controllers/TimestampedValuesControllerTest.cs b/DD.Persistence.IntegrationTests/Controllers/TimestampedValuesControllerTest.cs index 526b372..9bb1d58 100644 --- a/DD.Persistence.IntegrationTests/Controllers/TimestampedValuesControllerTest.cs +++ b/DD.Persistence.IntegrationTests/Controllers/TimestampedValuesControllerTest.cs @@ -406,8 +406,12 @@ public class TimestampedValuesControllerTest : BaseIntegrationTest private void Cleanup() { + foreach (var item in discriminatorIds) + { + memoryCache.Remove(item); + } discriminatorIds = []; dbContext.CleanupDbSet(); - dbContext.CleanupDbSet(); + dbContext.CleanupDbSet(); } } diff --git a/DD.Persistence.Models/DataSchemeDto.cs b/DD.Persistence.Models/DataSchemeDto.cs index 7f238aa..d20ffaa 100644 --- a/DD.Persistence.Models/DataSchemeDto.cs +++ b/DD.Persistence.Models/DataSchemeDto.cs @@ -1,9 +1,11 @@ -namespace DD.Persistence.Models; +using System.Collections; + +namespace DD.Persistence.Models; /// /// Схема для набора данных /// -public class DataSchemeDto +public class DataSchemeDto : IEnumerable, IEquatable> { /// /// Дискриминатор @@ -11,12 +13,30 @@ public class DataSchemeDto public Guid DiscriminatorId { get; set; } /// - /// Наименования полей + /// Поля /// - public string[] PropNames { get; set; } = []; + private IEnumerable Properties { get; } = []; - /// - /// Типы полей - /// - public PropTypeEnum[] PropTypes { get; set; } = []; + /// + public DataSchemeDto(Guid discriminatorId, SchemePropertyDto[] Properties) + { + DiscriminatorId = discriminatorId; + this.Properties = Properties; + } + + /// + public IEnumerator GetEnumerator() + => Properties.GetEnumerator(); + + IEnumerator IEnumerable.GetEnumerator() + => GetEnumerator(); + + /// + public bool Equals(IEnumerable? otherProperties) + { + //if (otherProperties is null) + // return false; + + return Properties.SequenceEqual(otherProperties); + } } diff --git a/DD.Persistence.Models/Enumerations/PropTypeEnum.cs b/DD.Persistence.Models/Enumerations/PropTypeEnum.cs deleted file mode 100644 index 5379929..0000000 --- a/DD.Persistence.Models/Enumerations/PropTypeEnum.cs +++ /dev/null @@ -1,14 +0,0 @@ -namespace DD.Persistence.Models; - -/// -/// Типы для набора данных -/// -public enum PropTypeEnum -{ - /// - String = 0, - /// - Double = 1, - /// - DateTime = 2 -} diff --git a/DD.Persistence.Models/SchemePropertyDto.cs b/DD.Persistence.Models/SchemePropertyDto.cs new file mode 100644 index 0000000..0c34ba7 --- /dev/null +++ b/DD.Persistence.Models/SchemePropertyDto.cs @@ -0,0 +1,30 @@ +using System.Text.Json; + +namespace DD.Persistence.Models; + +/// +/// Индексируемого поле из схемы для набора данных +/// +public class SchemePropertyDto : IEquatable +{ + /// + /// Индекс поля + /// + public required int Index { get; set; } + + /// + /// Наименование индексируемого поля + /// + public required string PropertyName { get; set; } + + /// + /// Тип индексируемого поля + /// + public required JsonValueKind PropertyKind { get; set; } + + /// + public bool Equals(SchemePropertyDto? other) + { + return Index == other?.Index && PropertyName == other?.PropertyName && PropertyKind == other?.PropertyKind; + } +} diff --git a/DD.Persistence.Test/TimestampedValuesServiceShould.cs b/DD.Persistence.Test/TimestampedValuesServiceShould.cs index 0acb6de..ad26d14 100644 --- a/DD.Persistence.Test/TimestampedValuesServiceShould.cs +++ b/DD.Persistence.Test/TimestampedValuesServiceShould.cs @@ -7,7 +7,7 @@ namespace DD.Persistence.Repository.Test; public class TimestampedValuesServiceShould { private readonly ITimestampedValuesRepository timestampedValuesRepository = Substitute.For(); - private readonly IDataSchemeRepository dataSchemeRepository = Substitute.For(); + private readonly ISchemePropertyRepository dataSchemeRepository = Substitute.For(); private TimestampedValuesService timestampedValuesService; public TimestampedValuesServiceShould() diff --git a/DD.Persistence/Repositories/IDataSchemeRepository.cs b/DD.Persistence/Repositories/ISchemePropertyRepository.cs similarity index 84% rename from DD.Persistence/Repositories/IDataSchemeRepository.cs rename to DD.Persistence/Repositories/ISchemePropertyRepository.cs index c14a9cf..458f5cd 100644 --- a/DD.Persistence/Repositories/IDataSchemeRepository.cs +++ b/DD.Persistence/Repositories/ISchemePropertyRepository.cs @@ -5,7 +5,7 @@ namespace DD.Persistence.Repositories; /// /// Репозиторий для работы со схемами наборов данных /// -public interface IDataSchemeRepository +public interface ISchemePropertyRepository { /// /// Добавить схему @@ -13,7 +13,7 @@ public interface IDataSchemeRepository /// /// /// - Task Add(DataSchemeDto dataSourceSystemDto, CancellationToken token); + Task AddRange(DataSchemeDto dataSourceSystemDto, CancellationToken token); /// /// Вычитать схему diff --git a/DD.Persistence/Services/TimestampedValuesService.cs b/DD.Persistence/Services/TimestampedValuesService.cs index 264fdc5..5e6f9ed 100644 --- a/DD.Persistence/Services/TimestampedValuesService.cs +++ b/DD.Persistence/Services/TimestampedValuesService.cs @@ -10,10 +10,10 @@ namespace DD.Persistence.Services; public class TimestampedValuesService : ITimestampedValuesService { private readonly ITimestampedValuesRepository timestampedValuesRepository; - private readonly IDataSchemeRepository dataSchemeRepository; + private readonly ISchemePropertyRepository dataSchemeRepository; /// - public TimestampedValuesService(ITimestampedValuesRepository timestampedValuesRepository, IDataSchemeRepository relatedDataRepository) + public TimestampedValuesService(ITimestampedValuesRepository timestampedValuesRepository, ISchemePropertyRepository relatedDataRepository) { this.timestampedValuesRepository = timestampedValuesRepository; this.dataSchemeRepository = relatedDataRepository; @@ -38,7 +38,7 @@ public class TimestampedValuesService : ITimestampedValuesService { var result = await timestampedValuesRepository.Get(discriminatorIds, geTimestamp, columnNames, skip, take, token); - var dtos = await Materialize(result, token); + var dtos = await BindingToDataScheme(result, token); if (!columnNames.IsNullOrEmpty()) { @@ -53,9 +53,9 @@ public class TimestampedValuesService : ITimestampedValuesService { var result = await timestampedValuesRepository.GetFirst(discriminatorId, takeCount, token); - var resultToMaterialize = new[] { KeyValuePair.Create(discriminatorId, result) } + var resultBeforeBinding = new[] { KeyValuePair.Create(discriminatorId, result) } .ToDictionary(); - var dtos = await Materialize(resultToMaterialize, token); + var dtos = await BindingToDataScheme(resultBeforeBinding, token); return dtos; } @@ -65,9 +65,9 @@ public class TimestampedValuesService : ITimestampedValuesService { var result = await timestampedValuesRepository.GetLast(discriminatorId, takeCount, token); - var resultToMaterialize = new[] { KeyValuePair.Create(discriminatorId, result) } + var resultBeforeBinding = new[] { KeyValuePair.Create(discriminatorId, result) } .ToDictionary(); - var dtos = await Materialize(resultToMaterialize, token); + var dtos = await BindingToDataScheme(resultBeforeBinding, token); return dtos; } @@ -82,9 +82,9 @@ public class TimestampedValuesService : ITimestampedValuesService { var result = await timestampedValuesRepository.GetResampledData(discriminatorId, beginTimestamp, intervalSec, approxPointsCount, token); - var resultToMaterialize = new[] { KeyValuePair.Create(discriminatorId, result) } + var resultBeforeBinding = new[] { KeyValuePair.Create(discriminatorId, result) } .ToDictionary(); - var dtos = await Materialize(resultToMaterialize, token); + var dtos = await BindingToDataScheme(resultBeforeBinding, token); return dtos; } @@ -94,9 +94,9 @@ public class TimestampedValuesService : ITimestampedValuesService { var result = await timestampedValuesRepository.GetGtDate(discriminatorId, beginTimestamp, token); - var resultToMaterialize = new[] { KeyValuePair.Create(discriminatorId, result) } + var resultBeforeBinding = new[] { KeyValuePair.Create(discriminatorId, result) } .ToDictionary(); - var dtos = await Materialize(resultToMaterialize, token); + var dtos = await BindingToDataScheme(resultBeforeBinding, token); return dtos; } @@ -108,28 +108,22 @@ public class TimestampedValuesService : ITimestampedValuesService /// /// /// - private async Task> Materialize(IDictionary> queryResult, CancellationToken token) + private async Task> BindingToDataScheme(IDictionary> queryResult, CancellationToken token) { IEnumerable result = []; foreach (var keyValuePair in queryResult) { var dataScheme = await dataSchemeRepository.Get(keyValuePair.Key, token); if (dataScheme is null) - { continue; - } foreach (var tuple in keyValuePair.Value) { - var identity = dataScheme!.PropNames; - var indexedIdentity = identity - .Select((value, index) => new { index, value }); - var dto = new TimestampedValuesDto() { Timestamp = tuple.Timestamp.ToUniversalTime(), - Values = indexedIdentity - .ToDictionary(x => x.value, x => tuple.Values[x.index]) + Values = dataScheme + .ToDictionary(k => k.PropertyName, v => tuple.Values[v.Index]) }; result = result.Append(dto); @@ -149,61 +143,29 @@ public class TimestampedValuesService : ITimestampedValuesService /// Некорректный набор наименований полей private async Task CreateDataSchemeIfNotExist(Guid discriminatorId, TimestampedValuesDto dto, CancellationToken token) { - var propNames = dto.Values.Keys.ToArray(); - var propTypes = GetPropTypes(dto); + var valuesList = dto.Values.ToList(); + var properties = valuesList.ToList().Select(e => new SchemePropertyDto() { + Index = valuesList.IndexOf(e), + PropertyName = e.Key, + PropertyKind = ((JsonElement) e.Value).ValueKind + }).ToArray(); var dataScheme = await dataSchemeRepository.Get(discriminatorId, token); if (dataScheme is null) { - dataScheme = new DataSchemeDto() - { - DiscriminatorId = discriminatorId, - PropNames = propNames, - PropTypes = propTypes - }; - await dataSchemeRepository.Add(dataScheme, token); + dataScheme = new DataSchemeDto(discriminatorId, properties); + await dataSchemeRepository.AddRange(dataScheme, token); return; } - if (!dataScheme.PropNames.SequenceEqual(propNames)) + if (!dataScheme.Equals(properties)) { - var expectedFieldNames = string.Join(", ", dataScheme.PropNames); - var actualFieldNames = string.Join(", ", propNames); throw new InvalidOperationException($"Для системы {discriminatorId.ToString()} " + - $"характерен набор данных: [{expectedFieldNames}], однако был передан набор: [{actualFieldNames}]"); + $"был передан нехарактерный набор данных"); } } - /// - /// Получить типы для набора данных в соответствии с индексацией - /// - /// - /// - /// - private PropTypeEnum[] GetPropTypes(TimestampedValuesDto dto) - { - var types = dto.Values.Select(e => - { - var objectKind = ((JsonElement) e.Value).ValueKind; - var valueString = e.Value.ToString(); - - if (valueString is null) - throw new ArgumentNullException("Переданный набор данных содержит null, в следствии чего не удаётся определить типы полей"); - - if (DateTimeOffset.TryParse(valueString, out _)) - return PropTypeEnum.DateTime; - - var doubleString = valueString.Replace('.', ','); - if (double.TryParse(doubleString, out _)) - return PropTypeEnum.Double; - - return PropTypeEnum.String; - }); - - return types.ToArray(); - } - /// /// Отсеить лишние поля в соответствии с заданным фильтром /// From 7d973ba85926e163c76cda323e83701826f07dfa Mon Sep 17 00:00:00 2001 From: Roman Efremov Date: Thu, 6 Feb 2025 09:31:10 +0500 Subject: [PATCH 6/7] =?UTF-8?q?=D0=9F=D1=80=D0=B0=D0=B2=D0=BA=D0=B8=20?= =?UTF-8?q?=D0=BF=D0=BE=20=D1=80=D0=B5=D0=B2=D1=8C=D1=8E=20#3?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../DependencyInjection.cs | 1 + .../TimestampedValuesCachedRepository.cs | 103 ------------------ 2 files changed, 1 insertion(+), 103 deletions(-) delete mode 100644 DD.Persistence.Database/RepositoriesCached/TimestampedValuesCachedRepository.cs diff --git a/DD.Persistence.Database/DependencyInjection.cs b/DD.Persistence.Database/DependencyInjection.cs index ca140d8..a9291e2 100644 --- a/DD.Persistence.Database/DependencyInjection.cs +++ b/DD.Persistence.Database/DependencyInjection.cs @@ -13,6 +13,7 @@ namespace DD.Persistence.Database; public static class DependencyInjection { + // ToDo: перенести в другой файл public static void MapsterSetup() { TypeAdapterConfig.GlobalSettings.Default.Config diff --git a/DD.Persistence.Database/RepositoriesCached/TimestampedValuesCachedRepository.cs b/DD.Persistence.Database/RepositoriesCached/TimestampedValuesCachedRepository.cs deleted file mode 100644 index 2073126..0000000 --- a/DD.Persistence.Database/RepositoriesCached/TimestampedValuesCachedRepository.cs +++ /dev/null @@ -1,103 +0,0 @@ -//using DD.Persistence.Models; -//using DD.Persistence.Models.Common; -//using DD.Persistence.Repositories; -//using Microsoft.EntityFrameworkCore; - -//namespace DD.Persistence.Database.Postgres.Repositories; - -//public class TimestampedValuesCachedRepository : TimestampedValuesRepository -//{ -// public static TimestampedValuesDto? FirstByDate { get; private set; } -// public static CyclicArray LastData { get; } = new CyclicArray(CacheItemsCount); - -// private const int CacheItemsCount = 3600; - -// public TimestampedValuesCachedRepository(DbContext db, IDataSourceSystemRepository relatedDataRepository) : base(db, relatedDataRepository) -// { -// //Task.Run(async () => -// //{ -// // var firstDateItem = await base.GetFirst(CancellationToken.None); -// // if (firstDateItem == null) -// // { -// // return; -// // } - -// // FirstByDate = firstDateItem; - -// // var dtos = await base.GetLast(CacheItemsCount, CancellationToken.None); -// // dtos = dtos.OrderBy(d => d.Timestamp); -// // LastData.AddRange(dtos); -// //}).Wait(); -// } - -// public override async Task> GetGtDate(Guid discriminatorId, DateTimeOffset dateBegin, CancellationToken token) -// { - -// if (LastData.Count == 0 || LastData[0].Timestamp > dateBegin) -// { -// var dtos = await base.GetGtDate(discriminatorId, dateBegin, token); -// return dtos; -// } - -// var items = LastData -// .Where(i => i.Timestamp >= dateBegin); - -// return items; -// } - -// public override async Task AddRange(Guid discriminatorId, IEnumerable dtos, CancellationToken token) -// { -// var result = await base.AddRange(discriminatorId, dtos, token); -// if (result > 0) -// { - -// dtos = dtos.OrderBy(x => x.Timestamp); - -// FirstByDate = dtos.First(); -// LastData.AddRange(dtos); -// } - -// return result; -// } - -// public override async Task GetDatesRange(Guid discriminatorId, CancellationToken token) -// { -// if (FirstByDate == null) -// return null; - -// return await Task.Run(() => -// { -// return new DatesRangeDto -// { -// From = FirstByDate.Timestamp, -// To = LastData[^1].Timestamp -// }; -// }); -// } - -// public override async Task> GetResampledData( -// Guid discriminatorId, -// DateTimeOffset dateBegin, -// double intervalSec = 600d, -// int approxPointsCount = 1024, -// CancellationToken token = default) -// { -// var dtos = LastData.Where(i => i.Timestamp >= dateBegin); -// if (LastData.Count == 0 || LastData[0].Timestamp > dateBegin) -// { -// dtos = await base.GetGtDate(discriminatorId, dateBegin, token); -// } - -// var dateEnd = dateBegin.AddSeconds(intervalSec); -// dtos = dtos -// .Where(i => i.Timestamp <= dateEnd); - -// var ratio = dtos.Count() / approxPointsCount; -// if (ratio > 1) -// dtos = dtos -// .Where((_, index) => index % ratio == 0); - -// return dtos; -// } -//} - From c5da82c2105f4372739a3dd3e8b689eaef5c09ac Mon Sep 17 00:00:00 2001 From: Roman Efremov Date: Thu, 6 Feb 2025 12:39:40 +0500 Subject: [PATCH 7/7] =?UTF-8?q?=D0=9F=D1=80=D0=B0=D0=B2=D0=BA=D0=B8=20?= =?UTF-8?q?=D0=BF=D0=BE=20=D1=80=D0=B5=D0=B2=D1=8C=D1=8E=20#4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- DD.Persistence.Models/DataSchemeDto.cs | 6 +++--- .../TimestampedValuesServiceShould.cs | 16 ++++++++++++---- .../Services/TimestampedValuesService.cs | 17 +++++++++-------- 3 files changed, 24 insertions(+), 15 deletions(-) diff --git a/DD.Persistence.Models/DataSchemeDto.cs b/DD.Persistence.Models/DataSchemeDto.cs index d20ffaa..2b28176 100644 --- a/DD.Persistence.Models/DataSchemeDto.cs +++ b/DD.Persistence.Models/DataSchemeDto.cs @@ -18,7 +18,7 @@ public class DataSchemeDto : IEnumerable, IEquatable Properties { get; } = []; /// - public DataSchemeDto(Guid discriminatorId, SchemePropertyDto[] Properties) + public DataSchemeDto(Guid discriminatorId, IEnumerable Properties) { DiscriminatorId = discriminatorId; this.Properties = Properties; @@ -34,8 +34,8 @@ public class DataSchemeDto : IEnumerable, IEquatable public bool Equals(IEnumerable? otherProperties) { - //if (otherProperties is null) - // return false; + if (otherProperties is null) + return false; return Properties.SequenceEqual(otherProperties); } diff --git a/DD.Persistence.Test/TimestampedValuesServiceShould.cs b/DD.Persistence.Test/TimestampedValuesServiceShould.cs index ad26d14..0fe7769 100644 --- a/DD.Persistence.Test/TimestampedValuesServiceShould.cs +++ b/DD.Persistence.Test/TimestampedValuesServiceShould.cs @@ -2,6 +2,7 @@ using DD.Persistence.Repositories; using DD.Persistence.Services; using NSubstitute; +using System.Text.Json; namespace DD.Persistence.Repository.Test; public class TimestampedValuesServiceShould @@ -45,10 +46,10 @@ public class TimestampedValuesServiceShould { var values = new Dictionary() { - { "A", i }, - { "B", i * 1.1 }, - { "C", $"Any{i}" }, - { "D", DateTimeOffset.Now }, + { "A", GetJsonFromObject(i) }, + { "B", GetJsonFromObject(i * 1.1) }, + { "C", GetJsonFromObject($"Any{i}") }, + { "D", GetJsonFromObject(DateTimeOffset.Now) } }; yield return new TimestampedValuesDto() @@ -58,4 +59,11 @@ public class TimestampedValuesServiceShould }; } } + + private static JsonElement GetJsonFromObject(object value) + { + var jsonString = JsonSerializer.Serialize(value); + var doc = JsonDocument.Parse(jsonString); + return doc.RootElement; + } } diff --git a/DD.Persistence/Services/TimestampedValuesService.cs b/DD.Persistence/Services/TimestampedValuesService.cs index 5e6f9ed..cef700f 100644 --- a/DD.Persistence/Services/TimestampedValuesService.cs +++ b/DD.Persistence/Services/TimestampedValuesService.cs @@ -117,13 +117,13 @@ public class TimestampedValuesService : ITimestampedValuesService if (dataScheme is null) continue; - foreach (var tuple in keyValuePair.Value) + foreach (var (Timestamp, Values) in keyValuePair.Value) { var dto = new TimestampedValuesDto() { - Timestamp = tuple.Timestamp.ToUniversalTime(), + Timestamp = Timestamp.ToUniversalTime(), Values = dataScheme - .ToDictionary(k => k.PropertyName, v => tuple.Values[v.Index]) + .ToDictionary(k => k.PropertyName, v => Values[v.Index]) }; result = result.Append(dto); @@ -144,11 +144,12 @@ public class TimestampedValuesService : ITimestampedValuesService private async Task CreateDataSchemeIfNotExist(Guid discriminatorId, TimestampedValuesDto dto, CancellationToken token) { var valuesList = dto.Values.ToList(); - var properties = valuesList.ToList().Select(e => new SchemePropertyDto() { - Index = valuesList.IndexOf(e), + var properties = valuesList.Select((e, index) => new SchemePropertyDto() + { + Index = index, PropertyName = e.Key, - PropertyKind = ((JsonElement) e.Value).ValueKind - }).ToArray(); + PropertyKind = ((JsonElement)e.Value).ValueKind + }); var dataScheme = await dataSchemeRepository.Get(discriminatorId, token); if (dataScheme is null) @@ -172,7 +173,7 @@ public class TimestampedValuesService : ITimestampedValuesService /// /// Поля, которые необходимо оставить /// - private IEnumerable ReduceSetColumnsByNames(IEnumerable dtos, IEnumerable fieldNames) + private static IEnumerable ReduceSetColumnsByNames(IEnumerable dtos, IEnumerable fieldNames) { var result = dtos.Select(dto => {