This commit is contained in:
parent
9736b41f1a
commit
556fdcbca0
@ -14,9 +14,9 @@ namespace DD.Persistence.API.Controllers;
|
|||||||
[Route("api/[controller]")]
|
[Route("api/[controller]")]
|
||||||
public class DataSourceSystemController : ControllerBase
|
public class DataSourceSystemController : ControllerBase
|
||||||
{
|
{
|
||||||
private readonly IDataSourceSystemRepository dataSourceSystemRepository;
|
private readonly IRelatedDataRepository<DataSourceSystemDto> dataSourceSystemRepository;
|
||||||
|
|
||||||
public DataSourceSystemController(IDataSourceSystemRepository dataSourceSystemRepository)
|
public DataSourceSystemController(IRelatedDataRepository<DataSourceSystemDto> dataSourceSystemRepository)
|
||||||
{
|
{
|
||||||
this.dataSourceSystemRepository = dataSourceSystemRepository;
|
this.dataSourceSystemRepository = dataSourceSystemRepository;
|
||||||
}
|
}
|
||||||
|
@ -15,9 +15,9 @@ namespace DD.Persistence.API.Controllers;
|
|||||||
[Route("api/[controller]/{discriminatorId}")]
|
[Route("api/[controller]/{discriminatorId}")]
|
||||||
public class TimestampedValuesController : ControllerBase
|
public class TimestampedValuesController : ControllerBase
|
||||||
{
|
{
|
||||||
private readonly ITimestampedValuesRepository<TimestampedValuesDto> repository;
|
private readonly ITimestampedValuesRepository repository;
|
||||||
|
|
||||||
public TimestampedValuesController(ITimestampedValuesRepository<TimestampedValuesDto> repository)
|
public TimestampedValuesController(ITimestampedValuesRepository repository)
|
||||||
{
|
{
|
||||||
this.repository = repository;
|
this.repository = repository;
|
||||||
}
|
}
|
||||||
|
@ -4,7 +4,7 @@
|
|||||||
"Port": 5432,
|
"Port": 5432,
|
||||||
"Database": "persistence",
|
"Database": "persistence",
|
||||||
"Username": "postgres",
|
"Username": "postgres",
|
||||||
"Password": "q"
|
"Password": "postgres"
|
||||||
},
|
},
|
||||||
"NeedUseKeyCloak": false,
|
"NeedUseKeyCloak": false,
|
||||||
"AuthUser": {
|
"AuthUser": {
|
||||||
|
@ -12,7 +12,7 @@ using Npgsql.EntityFrameworkCore.PostgreSQL.Metadata;
|
|||||||
namespace DD.Persistence.Database.Postgres.Migrations
|
namespace DD.Persistence.Database.Postgres.Migrations
|
||||||
{
|
{
|
||||||
[DbContext(typeof(PersistencePostgresContext))]
|
[DbContext(typeof(PersistencePostgresContext))]
|
||||||
[Migration("20250114100429_Init")]
|
[Migration("20250116093615_Init")]
|
||||||
partial class Init
|
partial class Init
|
||||||
{
|
{
|
||||||
/// <inheritdoc />
|
/// <inheritdoc />
|
||||||
@ -122,7 +122,24 @@ namespace DD.Persistence.Database.Postgres.Migrations
|
|||||||
|
|
||||||
b.HasKey("DiscriminatorId", "Timestamp");
|
b.HasKey("DiscriminatorId", "Timestamp");
|
||||||
|
|
||||||
b.ToTable("TimestampedSets");
|
b.ToTable("TimestampedValues");
|
||||||
|
});
|
||||||
|
|
||||||
|
modelBuilder.Entity("DD.Persistence.Database.Entity.ValuesIdentity", b =>
|
||||||
|
{
|
||||||
|
b.Property<Guid>("DiscriminatorId")
|
||||||
|
.ValueGeneratedOnAdd()
|
||||||
|
.HasColumnType("uuid")
|
||||||
|
.HasComment("Дискриминатор системы");
|
||||||
|
|
||||||
|
b.Property<string[]>("Identity")
|
||||||
|
.IsRequired()
|
||||||
|
.HasColumnType("jsonb")
|
||||||
|
.HasComment("Идентификаторы");
|
||||||
|
|
||||||
|
b.HasKey("DiscriminatorId");
|
||||||
|
|
||||||
|
b.ToTable("ValuesIdentities");
|
||||||
});
|
});
|
||||||
|
|
||||||
modelBuilder.Entity("DD.Persistence.Database.Model.ChangeLog", b =>
|
modelBuilder.Entity("DD.Persistence.Database.Model.ChangeLog", b =>
|
||||||
@ -212,6 +229,17 @@ namespace DD.Persistence.Database.Postgres.Migrations
|
|||||||
|
|
||||||
b.Navigation("System");
|
b.Navigation("System");
|
||||||
});
|
});
|
||||||
|
|
||||||
|
modelBuilder.Entity("DD.Persistence.Database.Entity.TimestampedValues", b =>
|
||||||
|
{
|
||||||
|
b.HasOne("DD.Persistence.Database.Entity.ValuesIdentity", "ValuesIdentity")
|
||||||
|
.WithMany()
|
||||||
|
.HasForeignKey("DiscriminatorId")
|
||||||
|
.OnDelete(DeleteBehavior.Cascade)
|
||||||
|
.IsRequired();
|
||||||
|
|
||||||
|
b.Navigation("ValuesIdentity");
|
||||||
|
});
|
||||||
#pragma warning restore 612, 618
|
#pragma warning restore 612, 618
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -74,16 +74,15 @@ namespace DD.Persistence.Database.Postgres.Migrations
|
|||||||
});
|
});
|
||||||
|
|
||||||
migrationBuilder.CreateTable(
|
migrationBuilder.CreateTable(
|
||||||
name: "TimestampedSets",
|
name: "ValuesIdentities",
|
||||||
columns: table => new
|
columns: table => new
|
||||||
{
|
{
|
||||||
Timestamp = table.Column<DateTimeOffset>(type: "timestamp with time zone", nullable: false, comment: "Временная отметка"),
|
|
||||||
DiscriminatorId = table.Column<Guid>(type: "uuid", nullable: false, comment: "Дискриминатор системы"),
|
DiscriminatorId = table.Column<Guid>(type: "uuid", nullable: false, comment: "Дискриминатор системы"),
|
||||||
Values = table.Column<string>(type: "jsonb", nullable: false, comment: "Данные")
|
Identity = table.Column<string[]>(type: "jsonb", nullable: false, comment: "Идентификаторы")
|
||||||
},
|
},
|
||||||
constraints: table =>
|
constraints: table =>
|
||||||
{
|
{
|
||||||
table.PrimaryKey("PK_TimestampedSets", x => new { x.DiscriminatorId, x.Timestamp });
|
table.PrimaryKey("PK_ValuesIdentities", x => x.DiscriminatorId);
|
||||||
});
|
});
|
||||||
|
|
||||||
migrationBuilder.CreateTable(
|
migrationBuilder.CreateTable(
|
||||||
@ -108,6 +107,25 @@ namespace DD.Persistence.Database.Postgres.Migrations
|
|||||||
onDelete: ReferentialAction.Cascade);
|
onDelete: ReferentialAction.Cascade);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
migrationBuilder.CreateTable(
|
||||||
|
name: "TimestampedValues",
|
||||||
|
columns: table => new
|
||||||
|
{
|
||||||
|
Timestamp = table.Column<DateTimeOffset>(type: "timestamp with time zone", nullable: false, comment: "Временная отметка"),
|
||||||
|
DiscriminatorId = table.Column<Guid>(type: "uuid", nullable: false, comment: "Дискриминатор системы"),
|
||||||
|
Values = table.Column<string>(type: "jsonb", nullable: false, comment: "Данные")
|
||||||
|
},
|
||||||
|
constraints: table =>
|
||||||
|
{
|
||||||
|
table.PrimaryKey("PK_TimestampedValues", x => new { x.DiscriminatorId, x.Timestamp });
|
||||||
|
table.ForeignKey(
|
||||||
|
name: "FK_TimestampedValues_ValuesIdentities_DiscriminatorId",
|
||||||
|
column: x => x.DiscriminatorId,
|
||||||
|
principalTable: "ValuesIdentities",
|
||||||
|
principalColumn: "DiscriminatorId",
|
||||||
|
onDelete: ReferentialAction.Cascade);
|
||||||
|
});
|
||||||
|
|
||||||
migrationBuilder.CreateIndex(
|
migrationBuilder.CreateIndex(
|
||||||
name: "IX_TechMessage_SystemId",
|
name: "IX_TechMessage_SystemId",
|
||||||
table: "TechMessage",
|
table: "TechMessage",
|
||||||
@ -130,10 +148,13 @@ namespace DD.Persistence.Database.Postgres.Migrations
|
|||||||
name: "TechMessage");
|
name: "TechMessage");
|
||||||
|
|
||||||
migrationBuilder.DropTable(
|
migrationBuilder.DropTable(
|
||||||
name: "TimestampedSets");
|
name: "TimestampedValues");
|
||||||
|
|
||||||
migrationBuilder.DropTable(
|
migrationBuilder.DropTable(
|
||||||
name: "DataSourceSystem");
|
name: "DataSourceSystem");
|
||||||
|
|
||||||
|
migrationBuilder.DropTable(
|
||||||
|
name: "ValuesIdentities");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -119,7 +119,24 @@ namespace DD.Persistence.Database.Postgres.Migrations
|
|||||||
|
|
||||||
b.HasKey("DiscriminatorId", "Timestamp");
|
b.HasKey("DiscriminatorId", "Timestamp");
|
||||||
|
|
||||||
b.ToTable("TimestampedSets");
|
b.ToTable("TimestampedValues");
|
||||||
|
});
|
||||||
|
|
||||||
|
modelBuilder.Entity("DD.Persistence.Database.Entity.ValuesIdentity", b =>
|
||||||
|
{
|
||||||
|
b.Property<Guid>("DiscriminatorId")
|
||||||
|
.ValueGeneratedOnAdd()
|
||||||
|
.HasColumnType("uuid")
|
||||||
|
.HasComment("Дискриминатор системы");
|
||||||
|
|
||||||
|
b.Property<string[]>("Identity")
|
||||||
|
.IsRequired()
|
||||||
|
.HasColumnType("jsonb")
|
||||||
|
.HasComment("Идентификаторы");
|
||||||
|
|
||||||
|
b.HasKey("DiscriminatorId");
|
||||||
|
|
||||||
|
b.ToTable("ValuesIdentities");
|
||||||
});
|
});
|
||||||
|
|
||||||
modelBuilder.Entity("DD.Persistence.Database.Model.ChangeLog", b =>
|
modelBuilder.Entity("DD.Persistence.Database.Model.ChangeLog", b =>
|
||||||
@ -209,6 +226,17 @@ namespace DD.Persistence.Database.Postgres.Migrations
|
|||||||
|
|
||||||
b.Navigation("System");
|
b.Navigation("System");
|
||||||
});
|
});
|
||||||
|
|
||||||
|
modelBuilder.Entity("DD.Persistence.Database.Entity.TimestampedValues", b =>
|
||||||
|
{
|
||||||
|
b.HasOne("DD.Persistence.Database.Entity.ValuesIdentity", "ValuesIdentity")
|
||||||
|
.WithMany()
|
||||||
|
.HasForeignKey("DiscriminatorId")
|
||||||
|
.OnDelete(DeleteBehavior.Cascade)
|
||||||
|
.IsRequired();
|
||||||
|
|
||||||
|
b.Navigation("ValuesIdentity");
|
||||||
|
});
|
||||||
#pragma warning restore 612, 618
|
#pragma warning restore 612, 618
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -9,7 +9,7 @@ public class DataSourceSystem
|
|||||||
public Guid SystemId { get; set; }
|
public Guid SystemId { get; set; }
|
||||||
|
|
||||||
[Required, Column(TypeName = "varchar(256)"), Comment("Наименование системы - источника данных")]
|
[Required, Column(TypeName = "varchar(256)"), Comment("Наименование системы - источника данных")]
|
||||||
public required string Name { get; set; }
|
public string Name { get; set; } = string.Empty;
|
||||||
|
|
||||||
[Comment("Описание системы - источника данных")]
|
[Comment("Описание системы - источника данных")]
|
||||||
public string? Description { get; set; }
|
public string? Description { get; set; }
|
||||||
|
@ -16,4 +16,7 @@ public class TimestampedValues : ITimestampedItem
|
|||||||
|
|
||||||
[Comment("Данные"), Column(TypeName = "jsonb")]
|
[Comment("Данные"), Column(TypeName = "jsonb")]
|
||||||
public required object[] Values { get; set; }
|
public required object[] Values { get; set; }
|
||||||
|
|
||||||
|
[Required, ForeignKey(nameof(DiscriminatorId)), Comment("Идентификаторы")]
|
||||||
|
public virtual ValuesIdentity? ValuesIdentity { get; set; }
|
||||||
}
|
}
|
||||||
|
14
DD.Persistence.Database/Entity/ValuesIdentity.cs
Normal file
14
DD.Persistence.Database/Entity/ValuesIdentity.cs
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
using Microsoft.EntityFrameworkCore;
|
||||||
|
using System.ComponentModel.DataAnnotations;
|
||||||
|
using System.ComponentModel.DataAnnotations.Schema;
|
||||||
|
|
||||||
|
namespace DD.Persistence.Database.Entity;
|
||||||
|
|
||||||
|
public class ValuesIdentity
|
||||||
|
{
|
||||||
|
[Key, Comment("Дискриминатор системы"),]
|
||||||
|
public Guid DiscriminatorId { get; set; }
|
||||||
|
|
||||||
|
[Comment("Идентификаторы"), Column(TypeName = "jsonb")]
|
||||||
|
public string[] Identity { get; set; } = [];
|
||||||
|
}
|
@ -11,7 +11,9 @@ public class PersistenceDbContext : DbContext
|
|||||||
{
|
{
|
||||||
public DbSet<Setpoint> Setpoint => Set<Setpoint>();
|
public DbSet<Setpoint> Setpoint => Set<Setpoint>();
|
||||||
|
|
||||||
public DbSet<TimestampedValues> TimestampedSets => Set<TimestampedValues>();
|
public DbSet<ValuesIdentity> ValuesIdentities => Set<ValuesIdentity>();
|
||||||
|
|
||||||
|
public DbSet<TimestampedValues> TimestampedValues => Set<TimestampedValues>();
|
||||||
|
|
||||||
public DbSet<ChangeLog> ChangeLog => Set<ChangeLog>();
|
public DbSet<ChangeLog> ChangeLog => Set<ChangeLog>();
|
||||||
|
|
||||||
@ -29,6 +31,10 @@ public class PersistenceDbContext : DbContext
|
|||||||
|
|
||||||
protected override void OnModelCreating(ModelBuilder modelBuilder)
|
protected override void OnModelCreating(ModelBuilder modelBuilder)
|
||||||
{
|
{
|
||||||
|
modelBuilder.Entity<ValuesIdentity>()
|
||||||
|
.Property(e => e.Identity)
|
||||||
|
.HasJsonConversion();
|
||||||
|
|
||||||
modelBuilder.Entity<TimestampedValues>()
|
modelBuilder.Entity<TimestampedValues>()
|
||||||
.Property(e => e.Values)
|
.Property(e => e.Values)
|
||||||
.HasJsonConversion();
|
.HasJsonConversion();
|
||||||
|
@ -212,11 +212,7 @@ public class TimestampedSetControllerTest : BaseIntegrationTest
|
|||||||
};
|
};
|
||||||
string jsonString = JsonSerializer.Serialize(t);
|
string jsonString = JsonSerializer.Serialize(t);
|
||||||
var values = JsonSerializer.Deserialize<object[]>(jsonString);
|
var values = JsonSerializer.Deserialize<object[]>(jsonString);
|
||||||
//// Создание динамического объекта
|
|
||||||
//dynamic obj = new ExpandoObject();
|
|
||||||
|
|
||||||
//// Добавляем поле с именем "FieldName" и значением 123
|
|
||||||
//obj.FieldName = 123;
|
|
||||||
|
|
||||||
yield return new TimestampedValuesDto()
|
yield return new TimestampedValuesDto()
|
||||||
{
|
{
|
||||||
|
@ -38,11 +38,14 @@ public static class DependencyInjection
|
|||||||
|
|
||||||
services.AddTransient<ISetpointRepository, SetpointRepository>();
|
services.AddTransient<ISetpointRepository, SetpointRepository>();
|
||||||
services.AddTransient<IChangeLogRepository, ChangeLogRepository>();
|
services.AddTransient<IChangeLogRepository, ChangeLogRepository>();
|
||||||
services.AddTransient<ITimestampedValuesRepository<TimestampedValuesDto>, TimestampedValuesRepository<TimestampedValuesDto>>();
|
services.AddTransient<ITimestampedValuesRepository, TimestampedValuesRepository>();
|
||||||
services.AddTransient<ITechMessagesRepository, TechMessagesRepository>();
|
services.AddTransient<ITechMessagesRepository, TechMessagesRepository>();
|
||||||
services.AddTransient<IParameterRepository, ParameterRepository>();
|
services.AddTransient<IParameterRepository, ParameterRepository>();
|
||||||
services.AddTransient<IDataSourceSystemRepository, DataSourceSystemCachedRepository>();
|
services.AddTransient<IRelatedDataRepository<DataSourceSystemDto>,
|
||||||
|
RelatedDataCachedRepository<DataSourceSystemDto, DataSourceSystem>>();
|
||||||
|
services.AddTransient<IRelatedDataRepository<ValuesIdentityDto>,
|
||||||
|
RelatedDataCachedRepository<ValuesIdentityDto, ValuesIdentity>>();
|
||||||
|
|
||||||
return services;
|
return services;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,33 +0,0 @@
|
|||||||
using DD.Persistence.Database.Entity;
|
|
||||||
using DD.Persistence.Models;
|
|
||||||
using DD.Persistence.Repositories;
|
|
||||||
using Mapster;
|
|
||||||
using Microsoft.EntityFrameworkCore;
|
|
||||||
|
|
||||||
namespace DD.Persistence.Repository.Repositories;
|
|
||||||
public class DataSourceSystemRepository : IDataSourceSystemRepository
|
|
||||||
{
|
|
||||||
protected DbContext db;
|
|
||||||
public DataSourceSystemRepository(DbContext db)
|
|
||||||
{
|
|
||||||
this.db = db;
|
|
||||||
}
|
|
||||||
protected virtual IQueryable<DataSourceSystem> GetQueryReadOnly() => db.Set<DataSourceSystem>();
|
|
||||||
|
|
||||||
public virtual async Task Add(DataSourceSystemDto dataSourceSystemDto, CancellationToken token)
|
|
||||||
{
|
|
||||||
var entity = dataSourceSystemDto.Adapt<DataSourceSystem>();
|
|
||||||
|
|
||||||
await db.Set<DataSourceSystem>().AddAsync(entity, token);
|
|
||||||
await db.SaveChangesAsync(token);
|
|
||||||
}
|
|
||||||
|
|
||||||
public virtual async Task<IEnumerable<DataSourceSystemDto>> Get(CancellationToken token)
|
|
||||||
{
|
|
||||||
var query = GetQueryReadOnly();
|
|
||||||
var entities = await query.ToArrayAsync(token);
|
|
||||||
var dtos = entities.Select(e => e.Adapt<DataSourceSystemDto>());
|
|
||||||
|
|
||||||
return dtos;
|
|
||||||
}
|
|
||||||
}
|
|
@ -0,0 +1,33 @@
|
|||||||
|
using DD.Persistence.Repositories;
|
||||||
|
using Mapster;
|
||||||
|
using Microsoft.EntityFrameworkCore;
|
||||||
|
|
||||||
|
namespace DD.Persistence.Repository.Repositories;
|
||||||
|
public class RelatedDataRepository<TDto, TEntity> : IRelatedDataRepository<TDto>
|
||||||
|
where TDto : class, new()
|
||||||
|
where TEntity : class, new()
|
||||||
|
{
|
||||||
|
protected DbContext db;
|
||||||
|
public RelatedDataRepository(DbContext db)
|
||||||
|
{
|
||||||
|
this.db = db;
|
||||||
|
}
|
||||||
|
protected virtual IQueryable<TEntity> GetQueryReadOnly() => db.Set<TEntity>();
|
||||||
|
|
||||||
|
public virtual async Task Add(TDto dataSourceSystemDto, CancellationToken token)
|
||||||
|
{
|
||||||
|
var entity = dataSourceSystemDto.Adapt<TEntity>();
|
||||||
|
|
||||||
|
await db.Set<TEntity>().AddAsync(entity, token);
|
||||||
|
await db.SaveChangesAsync(token);
|
||||||
|
}
|
||||||
|
|
||||||
|
public virtual async Task<IEnumerable<TDto>> Get(CancellationToken token)
|
||||||
|
{
|
||||||
|
var query = GetQueryReadOnly();
|
||||||
|
var entities = await query.ToArrayAsync(token);
|
||||||
|
var dtos = entities.Select(e => e.Adapt<TDto>());
|
||||||
|
|
||||||
|
return dtos;
|
||||||
|
}
|
||||||
|
}
|
@ -1,22 +1,19 @@
|
|||||||
using Mapster;
|
|
||||||
using Microsoft.EntityFrameworkCore;
|
|
||||||
using Microsoft.Extensions.Caching.Memory;
|
|
||||||
using Newtonsoft.Json.Linq;
|
|
||||||
using DD.Persistence.Database.Entity;
|
using DD.Persistence.Database.Entity;
|
||||||
using DD.Persistence.Models;
|
using DD.Persistence.Models;
|
||||||
|
using DD.Persistence.Models.Common;
|
||||||
using DD.Persistence.Models.Requests;
|
using DD.Persistence.Models.Requests;
|
||||||
using DD.Persistence.Repositories;
|
using DD.Persistence.Repositories;
|
||||||
using UuidExtensions;
|
using Mapster;
|
||||||
using DD.Persistence.Models.Common;
|
using Microsoft.EntityFrameworkCore;
|
||||||
|
|
||||||
namespace DD.Persistence.Repository.Repositories
|
namespace DD.Persistence.Repository.Repositories
|
||||||
{
|
{
|
||||||
public class TechMessagesRepository : ITechMessagesRepository
|
public class TechMessagesRepository : ITechMessagesRepository
|
||||||
{
|
{
|
||||||
private readonly IDataSourceSystemRepository sourceSystemRepository;
|
private readonly IRelatedDataRepository<DataSourceSystemDto> sourceSystemRepository;
|
||||||
private DbContext db;
|
private DbContext db;
|
||||||
|
|
||||||
public TechMessagesRepository(DbContext db, IDataSourceSystemRepository sourceSystemRepository)
|
public TechMessagesRepository(DbContext db, IRelatedDataRepository<DataSourceSystemDto> sourceSystemRepository)
|
||||||
{
|
{
|
||||||
this.db = db;
|
this.db = db;
|
||||||
this.sourceSystemRepository = sourceSystemRepository;
|
this.sourceSystemRepository = sourceSystemRepository;
|
||||||
|
@ -1,122 +0,0 @@
|
|||||||
//using Microsoft.EntityFrameworkCore;
|
|
||||||
//using DD.Persistence.Database.Entity;
|
|
||||||
//using DD.Persistence.Models;
|
|
||||||
//using DD.Persistence.Repositories;
|
|
||||||
//using DD.Persistence.Models.Common;
|
|
||||||
|
|
||||||
//namespace DD.Persistence.Repository.Repositories;
|
|
||||||
|
|
||||||
///// <summary>
|
|
||||||
///// Репозиторий для хранения разных наборов данных временных рядов.
|
|
||||||
///// idDiscriminator - идентифицирует конкретный набор данных, прим.: циклы измерения АСИБР, или отчет о DrillTest.
|
|
||||||
///// idDiscriminator формируют клиенты и только им известно что они обозначают.
|
|
||||||
///// Так как данные приходят редко, то их прореживания для построения графиков не предусмотрено.
|
|
||||||
///// </summary>
|
|
||||||
//public class TimestampedSetRepository : ITimestampedSetRepository
|
|
||||||
//{
|
|
||||||
// private readonly DbContext db;
|
|
||||||
|
|
||||||
// public TimestampedSetRepository(DbContext db)
|
|
||||||
// {
|
|
||||||
// this.db = db;
|
|
||||||
// }
|
|
||||||
|
|
||||||
// public Task<int> AddRange(Guid idDiscriminator, IEnumerable<TimestampedSetDto> sets, CancellationToken token)
|
|
||||||
// {
|
|
||||||
// var entities = sets.Select(set => new TimestampedSet(idDiscriminator, set.Timestamp.ToUniversalTime(), set.Set));
|
|
||||||
// var dbSet = db.Set<TimestampedSet>();
|
|
||||||
// dbSet.AddRange(entities);
|
|
||||||
// return db.SaveChangesAsync(token);
|
|
||||||
// }
|
|
||||||
|
|
||||||
// public async Task<IEnumerable<TimestampedSetDto>> Get(Guid idDiscriminator, DateTimeOffset? geTimestamp, IEnumerable<string>? columnNames, int skip, int take, CancellationToken token)
|
|
||||||
// {
|
|
||||||
// var dbSet = db.Set<TimestampedSet>();
|
|
||||||
// var query = dbSet.Where(entity => entity.IdDiscriminator == idDiscriminator);
|
|
||||||
|
|
||||||
// if (geTimestamp.HasValue)
|
|
||||||
// query = ApplyGeTimestamp(query, geTimestamp.Value);
|
|
||||||
|
|
||||||
// query = query
|
|
||||||
// .OrderBy(item => item.Timestamp)
|
|
||||||
// .Skip(skip)
|
|
||||||
// .Take(take);
|
|
||||||
|
|
||||||
// var data = await Materialize(query, token);
|
|
||||||
|
|
||||||
// if (columnNames is not null && columnNames.Any())
|
|
||||||
// data = ReduceSetColumnsByNames(data, columnNames);
|
|
||||||
|
|
||||||
// return data;
|
|
||||||
// }
|
|
||||||
|
|
||||||
// public async Task<IEnumerable<TimestampedSetDto>> GetLast(Guid idDiscriminator, IEnumerable<string>? columnNames, int take, CancellationToken token)
|
|
||||||
// {
|
|
||||||
// var dbSet = db.Set<TimestampedSet>();
|
|
||||||
// var query = dbSet.Where(entity => entity.IdDiscriminator == idDiscriminator);
|
|
||||||
|
|
||||||
// query = query.OrderByDescending(entity => entity.Timestamp)
|
|
||||||
// .Take(take)
|
|
||||||
// .OrderBy(entity => entity.Timestamp);
|
|
||||||
|
|
||||||
// var data = await Materialize(query, token);
|
|
||||||
|
|
||||||
// if (columnNames is not null && columnNames.Any())
|
|
||||||
// data = ReduceSetColumnsByNames(data, columnNames);
|
|
||||||
|
|
||||||
// return data;
|
|
||||||
// }
|
|
||||||
|
|
||||||
// public Task<int> Count(Guid idDiscriminator, CancellationToken token)
|
|
||||||
// {
|
|
||||||
// var dbSet = db.Set<TimestampedSet>();
|
|
||||||
// var query = dbSet.Where(entity => entity.IdDiscriminator == idDiscriminator);
|
|
||||||
// return query.CountAsync(token);
|
|
||||||
// }
|
|
||||||
|
|
||||||
// public async Task<DatesRangeDto?> GetDatesRange(Guid idDiscriminator, CancellationToken token)
|
|
||||||
// {
|
|
||||||
// var query = db.Set<TimestampedSet>()
|
|
||||||
// .GroupBy(entity => entity.IdDiscriminator)
|
|
||||||
// .Select(group => new
|
|
||||||
// {
|
|
||||||
// Min = group.Min(entity => entity.Timestamp),
|
|
||||||
// Max = group.Max(entity => entity.Timestamp),
|
|
||||||
// });
|
|
||||||
|
|
||||||
// var item = await query.FirstOrDefaultAsync(token);
|
|
||||||
// if (item is null)
|
|
||||||
// return null;
|
|
||||||
|
|
||||||
// return new DatesRangeDto
|
|
||||||
// {
|
|
||||||
// From = item.Min,
|
|
||||||
// To = item.Max,
|
|
||||||
// };
|
|
||||||
// }
|
|
||||||
|
|
||||||
// private static async Task<IEnumerable<TimestampedSetDto>> Materialize(IQueryable<TimestampedSet> query, CancellationToken token)
|
|
||||||
// {
|
|
||||||
// var dtoQuery = query.Select(entity => new TimestampedSetDto(entity.Timestamp, entity.Set));
|
|
||||||
// var dtos = await dtoQuery.ToArrayAsync(token);
|
|
||||||
// return dtos;
|
|
||||||
// }
|
|
||||||
|
|
||||||
// private static IQueryable<TimestampedSet> ApplyGeTimestamp(IQueryable<TimestampedSet> query, DateTimeOffset geTimestamp)
|
|
||||||
// {
|
|
||||||
// var geTimestampUtc = geTimestamp.ToUniversalTime();
|
|
||||||
// return query.Where(entity => entity.Timestamp >= geTimestampUtc);
|
|
||||||
// }
|
|
||||||
|
|
||||||
// private static IEnumerable<TimestampedSetDto> ReduceSetColumnsByNames(IEnumerable<TimestampedSetDto> query, IEnumerable<string> columnNames)
|
|
||||||
// {
|
|
||||||
// var newQuery = query
|
|
||||||
// .Select(entity => new TimestampedSetDto(
|
|
||||||
// entity.Timestamp,
|
|
||||||
// entity.Set
|
|
||||||
// .Where(prop => columnNames.Contains(prop.Key))
|
|
||||||
// .ToDictionary(prop => prop.Key, prop => prop.Value)
|
|
||||||
// ));
|
|
||||||
// return newQuery;
|
|
||||||
// }
|
|
||||||
//}
|
|
@ -1,24 +1,29 @@
|
|||||||
using DD.Persistence.Database.Entity;
|
using DD.Persistence.Database.Entity;
|
||||||
using DD.Persistence.Models;
|
using DD.Persistence.Models;
|
||||||
using DD.Persistence.Models.Common;
|
using DD.Persistence.Models.Common;
|
||||||
using DD.Persistence.ModelsAbstractions;
|
|
||||||
using DD.Persistence.Repositories;
|
using DD.Persistence.Repositories;
|
||||||
|
using DD.Persistence.Repository.Extensions;
|
||||||
using Mapster;
|
using Mapster;
|
||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
|
using Newtonsoft.Json.Linq;
|
||||||
|
using System.Linq;
|
||||||
using System.Text.Json;
|
using System.Text.Json;
|
||||||
|
using System.Text.Json.Nodes;
|
||||||
|
|
||||||
namespace DD.Persistence.Repository.Repositories;
|
namespace DD.Persistence.Repository.Repositories;
|
||||||
public class TimestampedValuesRepository<TDto> : ITimestampedValuesRepository<TDto>
|
public class TimestampedValuesRepository : ITimestampedValuesRepository
|
||||||
where TDto : class, ITimestampAbstractDto, new()
|
|
||||||
{
|
{
|
||||||
private readonly DbContext db;
|
private readonly DbContext db;
|
||||||
|
private readonly IRelatedDataRepository<ValuesIdentityDto> relatedDataRepository;
|
||||||
|
|
||||||
public TimestampedValuesRepository(DbContext db)
|
public TimestampedValuesRepository(DbContext db, IRelatedDataRepository<ValuesIdentityDto> relatedDataRepository)
|
||||||
{
|
{
|
||||||
this.db = db;
|
this.db = db;
|
||||||
|
this.relatedDataRepository = relatedDataRepository;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected virtual IQueryable<TimestampedValues> GetQueryReadOnly() => this.db.Set<TimestampedValues>();
|
protected virtual IQueryable<TimestampedValues> GetQueryReadOnly() => this.db.Set<TimestampedValues>()
|
||||||
|
.Include(e => e.ValuesIdentity);
|
||||||
|
|
||||||
public virtual async Task<DatesRangeDto?> GetDatesRange(Guid discriminatorId, CancellationToken token)
|
public virtual async Task<DatesRangeDto?> GetDatesRange(Guid discriminatorId, CancellationToken token)
|
||||||
{
|
{
|
||||||
@ -41,47 +46,57 @@ public class TimestampedValuesRepository<TDto> : ITimestampedValuesRepository<TD
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
public virtual async Task<IEnumerable<TDto>> GetGtDate(Guid discriminatorId, DateTimeOffset date, CancellationToken token)
|
public virtual async Task<IEnumerable<TimestampedValuesDto>> GetGtDate(Guid discriminatorId, DateTimeOffset date, CancellationToken token)
|
||||||
{
|
{
|
||||||
var query = GetQueryReadOnly().Where(e => e.Timestamp > date);
|
var query = GetQueryReadOnly().Where(e => e.Timestamp > date);
|
||||||
var entities = await query.ToArrayAsync(token);
|
var entities = await query.ToArrayAsync(token);
|
||||||
|
|
||||||
var dtos = entities.Select(e => e.Adapt<TDto>());
|
var dtos = entities.Select(e => e.Adapt<TimestampedValuesDto>());
|
||||||
|
|
||||||
return dtos;
|
return dtos;
|
||||||
}
|
}
|
||||||
|
|
||||||
public virtual async Task<int> AddRange(Guid discriminatorId, IEnumerable<TDto> dtos, CancellationToken token)
|
public virtual async Task<int> AddRange(Guid discriminatorId, IEnumerable<TimestampedValuesDto> dtos, CancellationToken token)
|
||||||
{
|
{
|
||||||
var entities = dtos
|
var timestampedValuesEntities = new List<TimestampedValues>();
|
||||||
.Select(d => d.Adapt<TimestampedValues>())
|
foreach (var dto in dtos)
|
||||||
.ToList();
|
|
||||||
|
|
||||||
entities.ForEach(d =>
|
|
||||||
{
|
{
|
||||||
d.DiscriminatorId = discriminatorId;
|
var values = dto.Values
|
||||||
d.Timestamp = d.Timestamp.ToUniversalTime();
|
.SelectMany(v => JsonSerializer.Deserialize<Dictionary<string, object>>(v.ToString()!)!)
|
||||||
});
|
.ToDictionary();
|
||||||
|
|
||||||
|
var keys = values.Keys.ToArray();
|
||||||
|
await CreateValuesIdentityIfNotExist(discriminatorId, keys, token);
|
||||||
|
|
||||||
|
var timestampedValuesEntity = new TimestampedValues()
|
||||||
|
{
|
||||||
|
DiscriminatorId = discriminatorId,
|
||||||
|
Timestamp = dto.Timestamp.ToUniversalTime(),
|
||||||
|
Values = values.Values.ToArray()
|
||||||
|
};
|
||||||
|
timestampedValuesEntities.Add(timestampedValuesEntity);
|
||||||
|
}
|
||||||
|
|
||||||
|
await db.Set<TimestampedValues>().AddRangeAsync(timestampedValuesEntities, token);
|
||||||
|
|
||||||
await db.Set<TimestampedValues>().AddRangeAsync(entities, token);
|
|
||||||
var result = await db.SaveChangesAsync(token);
|
var result = await db.SaveChangesAsync(token);
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected async Task<IEnumerable<TDto>> GetLastAsync(int takeCount, CancellationToken token)
|
protected async Task<IEnumerable<TimestampedValuesDto>> GetLastAsync(int takeCount, CancellationToken token)
|
||||||
{
|
{
|
||||||
var query = GetQueryReadOnly()
|
var query = GetQueryReadOnly()
|
||||||
.OrderByDescending(e => e.Timestamp)
|
.OrderByDescending(e => e.Timestamp)
|
||||||
.Take(takeCount);
|
.Take(takeCount);
|
||||||
|
|
||||||
var entities = await query.ToArrayAsync(token);
|
var entities = await query.ToArrayAsync(token);
|
||||||
var dtos = entities.Select(e => e.Adapt<TDto>());
|
var dtos = entities.Select(e => e.Adapt<TimestampedValuesDto>());
|
||||||
|
|
||||||
return dtos;
|
return dtos;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected async Task<TDto?> GetFirstAsync(CancellationToken token)
|
protected async Task<TimestampedValuesDto?> GetFirstAsync(CancellationToken token)
|
||||||
{
|
{
|
||||||
var query = GetQueryReadOnly()
|
var query = GetQueryReadOnly()
|
||||||
.OrderBy(e => e.Timestamp);
|
.OrderBy(e => e.Timestamp);
|
||||||
@ -91,11 +106,11 @@ public class TimestampedValuesRepository<TDto> : ITimestampedValuesRepository<TD
|
|||||||
if (entity == null)
|
if (entity == null)
|
||||||
return null;
|
return null;
|
||||||
|
|
||||||
var dto = entity.Adapt<TDto>();
|
var dto = entity.Adapt<TimestampedValuesDto>();
|
||||||
return dto;
|
return dto;
|
||||||
}
|
}
|
||||||
|
|
||||||
public async virtual Task<IEnumerable<TDto>> GetResampledData(
|
public async virtual Task<IEnumerable<TimestampedValuesDto>> GetResampledData(
|
||||||
Guid discriminatorId,
|
Guid discriminatorId,
|
||||||
DateTimeOffset dateBegin,
|
DateTimeOffset dateBegin,
|
||||||
double intervalSec = 600d,
|
double intervalSec = 600d,
|
||||||
@ -116,10 +131,10 @@ public class TimestampedValuesRepository<TDto> : ITimestampedValuesRepository<TD
|
|||||||
return dtos;
|
return dtos;
|
||||||
}
|
}
|
||||||
|
|
||||||
public async Task<IEnumerable<TimestampedValuesDto>> Get(Guid idDiscriminator, DateTimeOffset? geTimestamp, IEnumerable<string>? columnNames, int skip, int take, CancellationToken token)
|
public async Task<IEnumerable<TimestampedValuesDto>> Get(Guid discriminatorId, DateTimeOffset? geTimestamp, IEnumerable<string>? columnNames, int skip, int take, CancellationToken token)
|
||||||
{
|
{
|
||||||
var dbSet = db.Set<TimestampedValues>();
|
var dbSet = db.Set<TimestampedValues>();
|
||||||
var query = dbSet.Where(entity => entity.DiscriminatorId == idDiscriminator);
|
var query = dbSet.Where(entity => entity.DiscriminatorId == discriminatorId);
|
||||||
|
|
||||||
if (geTimestamp.HasValue)
|
if (geTimestamp.HasValue)
|
||||||
query = ApplyGeTimestamp(query, geTimestamp.Value);
|
query = ApplyGeTimestamp(query, geTimestamp.Value);
|
||||||
@ -129,7 +144,7 @@ public class TimestampedValuesRepository<TDto> : ITimestampedValuesRepository<TD
|
|||||||
.Skip(skip)
|
.Skip(skip)
|
||||||
.Take(take);
|
.Take(take);
|
||||||
|
|
||||||
var data = await Materialize(query, token);
|
var data = await Materialize(discriminatorId, query, token);
|
||||||
|
|
||||||
if (columnNames is not null && columnNames.Any())
|
if (columnNames is not null && columnNames.Any())
|
||||||
data = ReduceSetColumnsByNames(data, columnNames);
|
data = ReduceSetColumnsByNames(data, columnNames);
|
||||||
@ -137,16 +152,16 @@ public class TimestampedValuesRepository<TDto> : ITimestampedValuesRepository<TD
|
|||||||
return data;
|
return data;
|
||||||
}
|
}
|
||||||
|
|
||||||
public async Task<IEnumerable<TimestampedValuesDto>> GetLast(Guid idDiscriminator, IEnumerable<string>? columnNames, int take, CancellationToken token)
|
public async Task<IEnumerable<TimestampedValuesDto>> GetLast(Guid discriminatorId, IEnumerable<string>? columnNames, int take, CancellationToken token)
|
||||||
{
|
{
|
||||||
var dbSet = db.Set<TimestampedValues>();
|
var dbSet = db.Set<TimestampedValues>();
|
||||||
var query = dbSet.Where(entity => entity.DiscriminatorId == idDiscriminator);
|
var query = dbSet.Where(entity => entity.DiscriminatorId == discriminatorId);
|
||||||
|
|
||||||
query = query.OrderByDescending(entity => entity.Timestamp)
|
query = query.OrderByDescending(entity => entity.Timestamp)
|
||||||
.Take(take)
|
.Take(take)
|
||||||
.OrderBy(entity => entity.Timestamp);
|
.OrderBy(entity => entity.Timestamp);
|
||||||
|
|
||||||
var data = await Materialize(query, token);
|
var data = await Materialize(discriminatorId, query, token);
|
||||||
|
|
||||||
if (columnNames is not null && columnNames.Any())
|
if (columnNames is not null && columnNames.Any())
|
||||||
data = ReduceSetColumnsByNames(data, columnNames);
|
data = ReduceSetColumnsByNames(data, columnNames);
|
||||||
@ -154,21 +169,43 @@ public class TimestampedValuesRepository<TDto> : ITimestampedValuesRepository<TD
|
|||||||
return data;
|
return data;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Task<int> Count(Guid idDiscriminator, CancellationToken token)
|
public Task<int> Count(Guid discriminatorId, CancellationToken token)
|
||||||
{
|
{
|
||||||
var dbSet = db.Set<TimestampedValues>();
|
var dbSet = db.Set<TimestampedValues>();
|
||||||
var query = dbSet.Where(entity => entity.DiscriminatorId == idDiscriminator);
|
var query = dbSet.Where(entity => entity.DiscriminatorId == discriminatorId);
|
||||||
return query.CountAsync(token);
|
return query.CountAsync(token);
|
||||||
}
|
}
|
||||||
|
|
||||||
private static async Task<IEnumerable<TimestampedValuesDto>> Materialize(IQueryable<TimestampedValues> query, CancellationToken token)
|
private async Task<IEnumerable<TimestampedValuesDto>> Materialize(Guid discriminatorId, IQueryable<TimestampedValues> query, CancellationToken token)
|
||||||
{
|
{
|
||||||
var dtoQuery = query.Select(entity => new TimestampedValuesDto() { Timestamp = entity.Timestamp, Values = entity.Values });
|
var dtoQuery = query.Select(entity => new TimestampedValuesDto()
|
||||||
|
{
|
||||||
|
Timestamp = entity.Timestamp,
|
||||||
|
Values = entity.Values
|
||||||
|
});
|
||||||
|
|
||||||
var dtos = await dtoQuery.ToArrayAsync(token);
|
var dtos = await dtoQuery.ToArrayAsync(token);
|
||||||
|
foreach(var dto in dtos)
|
||||||
|
{
|
||||||
|
var valuesIdentities = await relatedDataRepository.Get(token);
|
||||||
|
var valuesIdentity = valuesIdentities?
|
||||||
|
.FirstOrDefault(e => e.DiscriminatorId == discriminatorId);
|
||||||
|
if (valuesIdentity == null)
|
||||||
|
return []; // ToDo: какая логика должна быть?
|
||||||
|
|
||||||
|
for (var i = 0; i < valuesIdentity.Identity.Count(); i++)
|
||||||
|
{
|
||||||
|
var key = valuesIdentity.Identity[i];
|
||||||
|
var value = dto.Values[i];
|
||||||
|
|
||||||
|
dto.Values[i] = new { key = value }; // ToDo: вывод?
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return dtos;
|
return dtos;
|
||||||
}
|
}
|
||||||
|
|
||||||
private static IQueryable<TimestampedValues> ApplyGeTimestamp(IQueryable<TimestampedValues> query, DateTimeOffset geTimestamp)
|
private IQueryable<TimestampedValues> ApplyGeTimestamp(IQueryable<TimestampedValues> query, DateTimeOffset geTimestamp)
|
||||||
{
|
{
|
||||||
var geTimestampUtc = geTimestamp.ToUniversalTime();
|
var geTimestampUtc = geTimestamp.ToUniversalTime();
|
||||||
return query.Where(entity => entity.Timestamp >= geTimestampUtc);
|
return query.Where(entity => entity.Timestamp >= geTimestampUtc);
|
||||||
@ -176,16 +213,43 @@ public class TimestampedValuesRepository<TDto> : ITimestampedValuesRepository<TD
|
|||||||
|
|
||||||
private static IEnumerable<TimestampedValuesDto> ReduceSetColumnsByNames(IEnumerable<TimestampedValuesDto> query, IEnumerable<string> columnNames)
|
private static IEnumerable<TimestampedValuesDto> ReduceSetColumnsByNames(IEnumerable<TimestampedValuesDto> query, IEnumerable<string> columnNames)
|
||||||
{
|
{
|
||||||
var newQuery = query
|
var newQuery = query;
|
||||||
.Select(entity => new TimestampedValuesDto()
|
//.Select(entity => new TimestampedValuesDto()
|
||||||
{
|
//{
|
||||||
Timestamp = entity.Timestamp,
|
// Timestamp = entity.Timestamp,
|
||||||
Values = entity.Values?
|
// Values = entity.Values?
|
||||||
.Where(prop => columnNames.Contains(
|
// .Where(prop => columnNames.Contains(
|
||||||
JsonSerializer.Deserialize<Dictionary<string, object>>(prop.ToString()!)?
|
// JsonSerializer.Deserialize<Dictionary<string, object>>(prop.ToString()!)?
|
||||||
.FirstOrDefault().Key
|
// .FirstOrDefault().Key
|
||||||
)).ToArray()
|
// )).ToArray()
|
||||||
});
|
//});
|
||||||
return newQuery;
|
return newQuery;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private async Task CreateValuesIdentityIfNotExist(Guid discriminatorId, string[] keys, CancellationToken token)
|
||||||
|
{
|
||||||
|
var valuesIdentities = await relatedDataRepository.Get(token);
|
||||||
|
var valuesIdentity = valuesIdentities?
|
||||||
|
.FirstOrDefault(e => e.DiscriminatorId == discriminatorId);
|
||||||
|
|
||||||
|
if (valuesIdentity == null)
|
||||||
|
{
|
||||||
|
valuesIdentity = new ValuesIdentityDto()
|
||||||
|
{
|
||||||
|
DiscriminatorId = discriminatorId,
|
||||||
|
Identity = keys
|
||||||
|
};
|
||||||
|
await relatedDataRepository.Add(valuesIdentity, token);
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!valuesIdentity.Identity.SequenceEqual(keys))
|
||||||
|
{
|
||||||
|
var expectedIdentity = string.Join(", ", valuesIdentity.Identity);
|
||||||
|
var actualIdentity = string.Join(", ", keys);
|
||||||
|
throw new InvalidOperationException($"Для системы {discriminatorId.ToString()} " +
|
||||||
|
$"характерен набор данных: [{expectedIdentity}], однако был передан набор: [{actualIdentity}]");
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -4,24 +4,26 @@ using DD.Persistence.Models;
|
|||||||
using DD.Persistence.Repository.Repositories;
|
using DD.Persistence.Repository.Repositories;
|
||||||
|
|
||||||
namespace DD.Persistence.Repository.RepositoriesCached;
|
namespace DD.Persistence.Repository.RepositoriesCached;
|
||||||
public class DataSourceSystemCachedRepository : DataSourceSystemRepository
|
public class RelatedDataCachedRepository<TDto, TEntity> : RelatedDataRepository<TDto, TEntity>
|
||||||
|
where TEntity : class, new()
|
||||||
|
where TDto : class, new()
|
||||||
{
|
{
|
||||||
private static readonly string SystemCacheKey = $"{typeof(Database.Entity.DataSourceSystem).FullName}CacheKey";
|
private static readonly string SystemCacheKey = $"{typeof(Database.Entity.DataSourceSystem).FullName}CacheKey";
|
||||||
private readonly IMemoryCache memoryCache;
|
private readonly IMemoryCache memoryCache;
|
||||||
private const int CacheExpirationInMinutes = 60;
|
private const int CacheExpirationInMinutes = 60;
|
||||||
private readonly TimeSpan? AbsoluteExpirationRelativeToNow = TimeSpan.FromMinutes(60);
|
private readonly TimeSpan? AbsoluteExpirationRelativeToNow = TimeSpan.FromMinutes(60);
|
||||||
|
|
||||||
public DataSourceSystemCachedRepository(DbContext db, IMemoryCache memoryCache) : base(db)
|
public RelatedDataCachedRepository(DbContext db, IMemoryCache memoryCache) : base(db)
|
||||||
{
|
{
|
||||||
this.memoryCache = memoryCache;
|
this.memoryCache = memoryCache;
|
||||||
}
|
}
|
||||||
public override async Task Add(DataSourceSystemDto dataSourceSystemDto, CancellationToken token)
|
public override async Task Add(TDto dataSourceSystemDto, CancellationToken token)
|
||||||
{
|
{
|
||||||
await base.Add(dataSourceSystemDto, token);
|
await base.Add(dataSourceSystemDto, token);
|
||||||
|
|
||||||
memoryCache.Remove(SystemCacheKey);
|
memoryCache.Remove(SystemCacheKey);
|
||||||
}
|
}
|
||||||
public override async Task<IEnumerable<DataSourceSystemDto>> Get(CancellationToken token)
|
public override async Task<IEnumerable<TDto>> Get(CancellationToken token)
|
||||||
{
|
{
|
||||||
var systems = await memoryCache.GetOrCreateAsync(SystemCacheKey, async (cacheEntry) =>
|
var systems = await memoryCache.GetOrCreateAsync(SystemCacheKey, async (cacheEntry) =>
|
||||||
{
|
{
|
@ -13,7 +13,7 @@ public class DataSourceSystemDto
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Наименование
|
/// Наименование
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public required string Name { get; set; } = string.Empty;
|
public string Name { get; set; } = string.Empty;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Описание
|
/// Описание
|
||||||
|
@ -15,5 +15,5 @@ public class TimestampedValuesDto : ITimestampAbstractDto
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Набор данных
|
/// Набор данных
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public object[]? Values { get; set; }
|
public object[] Values { get; set; } = [];
|
||||||
}
|
}
|
||||||
|
17
DD.Persistence/Models/ValuesIdentityDto.cs
Normal file
17
DD.Persistence/Models/ValuesIdentityDto.cs
Normal file
@ -0,0 +1,17 @@
|
|||||||
|
namespace DD.Persistence.Models;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Набор идентификаторов для набора данных
|
||||||
|
/// </summary>
|
||||||
|
public class ValuesIdentityDto
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Дискриминатор системы
|
||||||
|
/// </summary>
|
||||||
|
public Guid DiscriminatorId { get; set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Идентификаторы
|
||||||
|
/// </summary>
|
||||||
|
public string[] Identity { get; set; } = [];
|
||||||
|
}
|
@ -1,22 +0,0 @@
|
|||||||
using DD.Persistence.Models;
|
|
||||||
|
|
||||||
namespace DD.Persistence.Repositories;
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// Интерфейс по работе с системами - источниками данных
|
|
||||||
/// </summary>
|
|
||||||
public interface IDataSourceSystemRepository
|
|
||||||
{
|
|
||||||
/// <summary>
|
|
||||||
/// Добавить систему
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="dataSourceSystemDto"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
public Task Add(DataSourceSystemDto dataSourceSystemDto, CancellationToken token);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// Получить список систем
|
|
||||||
/// </summary>
|
|
||||||
/// <returns></returns>
|
|
||||||
public Task<IEnumerable<DataSourceSystemDto>> Get(CancellationToken token);
|
|
||||||
}
|
|
23
DD.Persistence/Repositories/IRelatedDataRepository.cs
Normal file
23
DD.Persistence/Repositories/IRelatedDataRepository.cs
Normal file
@ -0,0 +1,23 @@
|
|||||||
|
using DD.Persistence.Models;
|
||||||
|
|
||||||
|
namespace DD.Persistence.Repositories;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Интерфейс по работе с системами - источниками данных
|
||||||
|
/// </summary>
|
||||||
|
public interface IRelatedDataRepository<TDto>
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Добавить систему
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="dataSourceSystemDto"></param>
|
||||||
|
/// <param name="token"></param>
|
||||||
|
/// <returns></returns>
|
||||||
|
public Task Add(TDto dataSourceSystemDto, CancellationToken token);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Получить список систем
|
||||||
|
/// </summary>
|
||||||
|
/// <returns></returns>
|
||||||
|
public Task<IEnumerable<TDto>> Get(CancellationToken token);
|
||||||
|
}
|
@ -7,9 +7,7 @@ namespace DD.Persistence.Repositories;
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Интерфейс по работе с временными данными
|
/// Интерфейс по работе с временными данными
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <typeparam name="TDto"></typeparam>
|
public interface ITimestampedValuesRepository : ISyncRepository, ITimeSeriesBaseRepository
|
||||||
public interface ITimestampedValuesRepository<TDto> : ISyncRepository<TDto>, ITimeSeriesBaseRepository<TDto>
|
|
||||||
where TDto : class, ITimestampAbstractDto, new()
|
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Добавление записей
|
/// Добавление записей
|
||||||
@ -18,7 +16,7 @@ public interface ITimestampedValuesRepository<TDto> : ISyncRepository<TDto>, ITi
|
|||||||
/// <param name="dtos"></param>
|
/// <param name="dtos"></param>
|
||||||
/// <param name="token"></param>
|
/// <param name="token"></param>
|
||||||
/// <returns></returns>
|
/// <returns></returns>
|
||||||
Task<int> AddRange(Guid idDiscriminator, IEnumerable<TDto> dtos, CancellationToken token);
|
Task<int> AddRange(Guid idDiscriminator, IEnumerable<TimestampedValuesDto> dtos, CancellationToken token);
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Количество записей по указанному набору в БД. Для пагинации.
|
/// Количество записей по указанному набору в БД. Для пагинации.
|
||||||
|
@ -1,12 +1,12 @@
|
|||||||
using DD.Persistence.Models.Common;
|
using DD.Persistence.Models;
|
||||||
|
using DD.Persistence.Models.Common;
|
||||||
|
|
||||||
namespace DD.Persistence.RepositoriesAbstractions;
|
namespace DD.Persistence.RepositoriesAbstractions;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Интерфейс по работе с данными
|
/// Интерфейс по работе с данными
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <typeparam name="TDto"></typeparam>
|
public interface ISyncRepository
|
||||||
public interface ISyncRepository<TDto>
|
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Получить данные, начиная с определенной даты
|
/// Получить данные, начиная с определенной даты
|
||||||
@ -15,7 +15,7 @@ public interface ISyncRepository<TDto>
|
|||||||
/// <param name="dateBegin">дата начала</param>
|
/// <param name="dateBegin">дата начала</param>
|
||||||
/// <param name="token"></param>
|
/// <param name="token"></param>
|
||||||
/// <returns></returns>
|
/// <returns></returns>
|
||||||
Task<IEnumerable<TDto>> GetGtDate(Guid discriminatorId, DateTimeOffset dateBegin, CancellationToken token);
|
Task<IEnumerable<TimestampedValuesDto>> GetGtDate(Guid discriminatorId, DateTimeOffset dateBegin, CancellationToken token);
|
||||||
|
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
@ -5,7 +5,7 @@ namespace DD.Persistence.RepositoriesAbstractions;
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Интерфейс по работе с прореженными данными
|
/// Интерфейс по работе с прореженными данными
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public interface ITimeSeriesBaseRepository<TDto>
|
public interface ITimeSeriesBaseRepository
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Получить список объектов с прореживанием
|
/// Получить список объектов с прореживанием
|
||||||
@ -16,7 +16,7 @@ public interface ITimeSeriesBaseRepository<TDto>
|
|||||||
/// <param name="approxPointsCount"></param>
|
/// <param name="approxPointsCount"></param>
|
||||||
/// <param name="token"></param>
|
/// <param name="token"></param>
|
||||||
/// <returns></returns>
|
/// <returns></returns>
|
||||||
Task<IEnumerable<TDto>> GetResampledData(
|
Task<IEnumerable<TimestampedValuesDto>> GetResampledData(
|
||||||
Guid discriminatorId,
|
Guid discriminatorId,
|
||||||
DateTimeOffset dateBegin,
|
DateTimeOffset dateBegin,
|
||||||
double intervalSec = 600d,
|
double intervalSec = 600d,
|
||||||
|
Loading…
Reference in New Issue
Block a user