diff --git a/AsbCloudApp/Requests/WellRequest.cs b/AsbCloudApp/Requests/WellRequest.cs new file mode 100644 index 00000000..feb7259a --- /dev/null +++ b/AsbCloudApp/Requests/WellRequest.cs @@ -0,0 +1,20 @@ +namespace AsbCloudApp.Requests +{ +#nullable enable + /// + /// Запрос на получение скважин + /// + public class WellRequest + { + /// + /// id компании + /// + public int? IdCompany { get; set; } + + /// + /// id состояния + /// + public int? IdState { get; set; } + } +#nullable disable +} diff --git a/AsbCloudApp/Services/IWellService.cs b/AsbCloudApp/Services/IWellService.cs index 7eef310e..6bd3da44 100644 --- a/AsbCloudApp/Services/IWellService.cs +++ b/AsbCloudApp/Services/IWellService.cs @@ -1,11 +1,14 @@ using AsbCloudApp.Data; +using AsbCloudApp.Requests; using System; using System.Collections.Generic; +using System.Net; using System.Threading; using System.Threading.Tasks; namespace AsbCloudApp.Services { +#nullable enable /// /// сервис скважин /// @@ -19,10 +22,10 @@ namespace AsbCloudApp.Services /// /// Список скважин доступных компании /// - /// + /// /// /// - Task> GetWellsByCompanyAsync(int idCompany, CancellationToken token); + Task> GetAsync(WellRequest request, CancellationToken token); /// /// проверяет доступ к скважине для компании @@ -33,14 +36,6 @@ namespace AsbCloudApp.Services /// Task IsCompanyInvolvedInWellAsync(int idCompany, int idWell, CancellationToken token); - /// - /// проверяет доступ к скважине для компании - /// - /// - /// - /// - bool IsCompanyInvolvedInWell(int idCompany, int idWell); - /// /// получить название скважины по id /// @@ -101,5 +96,15 @@ namespace AsbCloudApp.Services /// /// Task EnshureTimezonesIsSetAsync(CancellationToken token); + + /// + /// ВРЕМЕННЫЙ метод + /// + /// + /// + /// +#warning GetWellTreeAsync(..) is dummy. Remove it before pullrequest. + Task> GetWellTreeAsync(int idCompany, CancellationToken token); } +#nullable disable } diff --git a/AsbCloudInfrastructure/Repository/TelemetryWirelineRunOutRepository.cs b/AsbCloudInfrastructure/Repository/TelemetryWirelineRunOutRepository.cs index cc815d91..9662d342 100644 --- a/AsbCloudInfrastructure/Repository/TelemetryWirelineRunOutRepository.cs +++ b/AsbCloudInfrastructure/Repository/TelemetryWirelineRunOutRepository.cs @@ -75,7 +75,7 @@ namespace AsbCloudInfrastructure.Repository /// public async Task> GetAllAsync(int idCompany, CancellationToken token) { - var wells = await wellService.GetWellsByCompanyAsync(idCompany, token) + var wells = await wellService.GetAsync(new() { IdCompany = idCompany }, token) .ConfigureAwait(false); var result = new List(wells.Count()); diff --git a/AsbCloudInfrastructure/Services/Subsystems/SubsystemOperationTimeService.cs b/AsbCloudInfrastructure/Services/Subsystems/SubsystemOperationTimeService.cs index a5ed9e49..280b0d92 100644 --- a/AsbCloudInfrastructure/Services/Subsystems/SubsystemOperationTimeService.cs +++ b/AsbCloudInfrastructure/Services/Subsystems/SubsystemOperationTimeService.cs @@ -190,7 +190,7 @@ namespace AsbCloudInfrastructure.Services.Subsystems private async Task> GetActiveWellsByCompany(int idCompany, CancellationToken token) { - var listWell = await wellService.GetWellsByCompanyAsync(idCompany, token); + var listWell = await wellService.GetAsync(new() { IdCompany = idCompany }, token); var active = listWell.Where(w => w.IdState == 1); return active; } diff --git a/AsbCloudInfrastructure/Services/WellOperationService/OperationsStatService.cs b/AsbCloudInfrastructure/Services/WellOperationService/OperationsStatService.cs index b9daba10..343b225b 100644 --- a/AsbCloudInfrastructure/Services/WellOperationService/OperationsStatService.cs +++ b/AsbCloudInfrastructure/Services/WellOperationService/OperationsStatService.cs @@ -27,7 +27,7 @@ namespace AsbCloudInfrastructure.Services.WellOperationService public async Task GetStatClusterAsync(int idCluster, int idCompany, CancellationToken token = default) { - var allWellsByCompany = await wellService.GetWellsByCompanyAsync(idCompany, token).ConfigureAwait(false); + var allWellsByCompany = await wellService.GetAsync(new() { IdCompany = idCompany }, token).ConfigureAwait(false); var idWellsByCompany = allWellsByCompany.Select(w => w.Id).Distinct(); diff --git a/AsbCloudInfrastructure/Services/WellService.cs b/AsbCloudInfrastructure/Services/WellService.cs index 967c44ca..a29d1573 100644 --- a/AsbCloudInfrastructure/Services/WellService.cs +++ b/AsbCloudInfrastructure/Services/WellService.cs @@ -1,6 +1,7 @@ using AsbCloudApp.Data; using AsbCloudApp.Exceptions; using AsbCloudApp.Repositories; +using AsbCloudApp.Requests; using AsbCloudApp.Services; using AsbCloudDb.Model; using AsbCloudInfrastructure.EfCache; @@ -16,6 +17,7 @@ using System.Threading.Tasks; namespace AsbCloudInfrastructure.Services { +#nullable enable public class WellService : CrudCacheRepositoryBase, IWellService { private const string relationCompaniesWellsCacheTag = "RelationCompaniesWells"; @@ -47,12 +49,6 @@ namespace AsbCloudInfrastructure.Services companyTypesService = new CrudCacheRepositoryBase(dbContext, memoryCache); } - private IEnumerable GetCacheRelationCompanyWell() - => dbContext.RelationCompaniesWells - .Include(r => r.Company) - .Include(r => r.Well) - .FromCache(relationCompaniesWellsCacheTag, relationCompaniesWellsCacheObsolence); - private Task> GetCacheRelationCompanyWellAsync(CancellationToken token) => dbContext.RelationCompaniesWells .Include(r => r.Company) @@ -73,21 +69,67 @@ namespace AsbCloudInfrastructure.Services return lastTelemetryDate; } - public async Task> GetWellsByCompanyAsync(int idCompany, CancellationToken token) +#warning GetWellTreeAsync(..) is dummy. Remove it before pullrequest. + public async Task> GetWellTreeAsync(int idCompany, CancellationToken token) { - var relationsCache = await GetCacheRelationCompanyWellAsync(token); + var wells = await GetEntitiesAsync(new() { IdCompany = idCompany }, token); - var wellsIds = relationsCache - .Where(r => r.IdCompany == idCompany) - .Select(r => r.IdWell); + var groupedWells = wells + .GroupBy(w => w.Cluster) + .GroupBy(g => g.Key.Deposit); - var wellsDtos = (await GetCacheAsync(token)) - .Where(w => wellsIds.Contains(w.Id)) - .Select(Convert); + var depositTree = groupedWells.Select( + gDeposit => new DepositBranchDto + { + Id = gDeposit.Key.Id, + Caption = gDeposit.Key.Caption, + Latitude = gDeposit.Key.Latitude, + Longitude = gDeposit.Key.Longitude, + Clusters = gDeposit.Select(gCluster => new ClusterBranchDto + { + Id = gCluster.Key.Id, + Caption = gCluster.Key.Caption, + Latitude = gCluster.Key.Latitude ?? gDeposit.Key.Latitude, + Longitude = gCluster.Key.Longitude ?? gDeposit.Key.Longitude, + Wells = gCluster.Select(well => + { + var dto = well.Adapt(); + if (dto.Latitude is null) + dto.Latitude = gCluster.Key.Latitude ?? gDeposit.Key.Latitude; + if (dto.Longitude is null) + dto.Longitude = gCluster.Key.Longitude ?? gDeposit.Key.Longitude; + + if (well.IdTelemetry is not null) + dto.LastTelemetryDate = telemetryService.GetLastTelemetryDate(well.IdTelemetry.Value); + return dto; + }), + }), + }); + return depositTree; + } + + public async Task> GetAsync(WellRequest request, CancellationToken token) + { + var wells = await GetEntitiesAsync(request, token); + var wellsDtos = wells.Select(Convert); return wellsDtos; } + private async Task> GetEntitiesAsync(WellRequest request, CancellationToken token) + { + var wells = await GetCacheAsync(token); + + if (request.IdCompany.HasValue) + wells = wells.Where(well => well.RelationCompaniesWells.Any(r => r.IdCompany == request.IdCompany.Value)); + + + if (request.IdState.HasValue) + wells = wells.Where(well => well.IdState == request.IdState.Value); + + return wells; + } + public override async Task InsertAsync(WellDto dto, CancellationToken token = default) { if (dto.IdWellType is < 1 or > 2) @@ -146,10 +188,6 @@ namespace AsbCloudInfrastructure.Services return result; } - public bool IsCompanyInvolvedInWell(int idCompany, int idWell) - => GetCacheRelationCompanyWell() - .Any(r => r.IdWell == idWell && r.IdCompany == idCompany); - public async Task IsCompanyInvolvedInWellAsync(int idCompany, int idWell, CancellationToken token) => (await GetCacheRelationCompanyWellAsync(token)) .Any(r => r.IdWell == idWell && r.IdCompany == idCompany); @@ -183,7 +221,7 @@ namespace AsbCloudInfrastructure.Services var well = await GetOrDefaultAsync(idWell, token); if (well is null) - return null; + return Enumerable.Empty(); var cache = await GetCacheAsync(token); @@ -209,9 +247,6 @@ namespace AsbCloudInfrastructure.Services protected override WellDto Convert(Well entity) { - if (entity is null) - return null; - var dto = base.Convert(entity); if (entity.Timezone is null) @@ -233,7 +268,8 @@ namespace AsbCloudInfrastructure.Services { var dto = entity.Adapt(); dto.CompanyTypeCaption = entity.CompanyType?.Caption - ?? companyTypesService.GetOrDefault(entity.IdCompanyType).Caption; + ?? companyTypesService.GetOrDefault(entity.IdCompanyType)?.Caption + ?? string.Empty; return dto; } @@ -278,20 +314,24 @@ namespace AsbCloudInfrastructure.Services } var well = GetQuery().FirstOrDefault(w => w.Id == wellDto.Id); - var point = GetCoordinates(well); - if (point is not null) - { - if (point.Timezone is not null) - { - return point.Timezone.Adapt(); - } - if (point.Latitude is not null & point.Longitude is not null) + if (well is not null) + { + var point = GetCoordinates(well); + if (point is not null) { - var timezone = timezoneService.GetByCoordinates((double)point.Latitude, (double)point.Longitude); - if (timezone is not null) + if (point.Timezone is not null) { - return timezone; + return point.Timezone.Adapt(); + } + + if (point.Latitude is not null & point.Longitude is not null) + { + var timezone = timezoneService.GetByCoordinates(point.Latitude!.Value, point.Longitude!.Value); + if (timezone is not null) + { + return timezone; + } } } } @@ -338,4 +378,5 @@ namespace AsbCloudInfrastructure.Services return telemetryService.GetDatesRange((int)well.IdTelemetry); } } -} +#nullable disable +} \ No newline at end of file diff --git a/AsbCloudWebApi/Controllers/CrudWellRelatedController.cs b/AsbCloudWebApi/Controllers/CrudWellRelatedController.cs index 3e7d1508..cf1110b8 100644 --- a/AsbCloudWebApi/Controllers/CrudWellRelatedController.cs +++ b/AsbCloudWebApi/Controllers/CrudWellRelatedController.cs @@ -44,7 +44,7 @@ namespace AsbCloudWebApi.Controllers if (idCompany is null) return Forbid(); - var wells = await wellService.GetWellsByCompanyAsync((int)idCompany, token); + var wells = await wellService.GetAsync(new() { IdCompany = idCompany }, token); if (!wells.Any()) return NoContent(); diff --git a/AsbCloudWebApi/Controllers/OperationStatController.cs b/AsbCloudWebApi/Controllers/OperationStatController.cs index e9409e1d..72856a33 100644 --- a/AsbCloudWebApi/Controllers/OperationStatController.cs +++ b/AsbCloudWebApi/Controllers/OperationStatController.cs @@ -107,9 +107,15 @@ namespace AsbCloudWebApi.Controllers [Route("wellsStats")] [Permission] [ProducesResponseType(typeof(IEnumerable), (int)System.Net.HttpStatusCode.OK)] - public async Task GetWellsStatAsync([FromQuery] IEnumerable idWells, CancellationToken token = default) + public async Task GetWellsStatAsync([FromQuery] IEnumerable idWells, CancellationToken token) { - var protectedIdWells = idWells.Where(CanUserAccessToWell); + int? idCompany = User.GetCompanyId(); + if (idCompany is null) + return Forbid(); + + var allowedWells = await wellService.GetAsync(new() { IdCompany = idCompany }, token); + + var protectedIdWells = idWells.Where(id => allowedWells.Any(allowed => allowed.Id == id)); var result = await operationsStatService.GetWellsStatAsync(protectedIdWells, token) .ConfigureAwait(false); return Ok(result); @@ -157,12 +163,6 @@ namespace AsbCloudWebApi.Controllers return Ok(result); } - private bool CanUserAccessToWell(int idWell) - { - int? idCompany = User.GetCompanyId(); - return idCompany is not null && wellService.IsCompanyInvolvedInWell((int)idCompany, idWell); - } - private async Task CanUserAccessToWellAsync(int idWell, CancellationToken token = default) { int? idCompany = User.GetCompanyId(); diff --git a/AsbCloudWebApi/Controllers/WellController.cs b/AsbCloudWebApi/Controllers/WellController.cs index f7c57726..e92840ee 100644 --- a/AsbCloudWebApi/Controllers/WellController.cs +++ b/AsbCloudWebApi/Controllers/WellController.cs @@ -38,7 +38,27 @@ namespace AsbCloudWebApi.Controllers if (idCompany is null) return NoContent(); - var wells = await wellService.GetWellsByCompanyAsync((int)idCompany, + var wells = await wellService.GetAsync(new() { IdCompany = idCompany }, + token).ConfigureAwait(false); + + return Ok(wells); + } + + /// + /// Возвращает список доступных скважин + /// + /// Токен отмены задачи + /// Список скважин + [HttpGet("wellTree")] + [ProducesResponseType(typeof(IEnumerable), (int)System.Net.HttpStatusCode.OK)] + public async Task GetWellTreeAsync(CancellationToken token = default) + { + var idCompany = User.GetCompanyId(); + + if (idCompany is null) + return NoContent(); + + var wells = await wellService.GetWellTreeAsync((int)idCompany, token).ConfigureAwait(false); return Ok(wells);