diff --git a/AsbCloudApp/Data/DailyReport/ItemInfoDto.cs b/AsbCloudApp/Data/DailyReport/ItemInfoDto.cs
index ac27a385..7cfaeed0 100644
--- a/AsbCloudApp/Data/DailyReport/ItemInfoDto.cs
+++ b/AsbCloudApp/Data/DailyReport/ItemInfoDto.cs
@@ -3,7 +3,8 @@
namespace AsbCloudApp.Data.DailyReport
{
///
- /// хранение дополнительной информации о записи
+ /// хранение дополнительной информации о записи
+ /// автоматическое формирование данных на серверной стороне
///
public class ItemInfoDto
{
diff --git a/AsbCloudApp/Data/DailyReport/TimeBalanceDto.cs b/AsbCloudApp/Data/DailyReport/TimeBalanceDto.cs
index 55db7850..efed1ea4 100644
--- a/AsbCloudApp/Data/DailyReport/TimeBalanceDto.cs
+++ b/AsbCloudApp/Data/DailyReport/TimeBalanceDto.cs
@@ -1,4 +1,5 @@
using System.Collections.Generic;
+using System.Linq;
namespace AsbCloudApp.Data.DailyReport
{
@@ -11,7 +12,7 @@ namespace AsbCloudApp.Data.DailyReport
///
/// Статистика по операциям
///
- public IEnumerable? OperationsStat { get; set; }
+ public IEnumerable OperationsStat { get; set; } = Enumerable.Empty();
}
}
diff --git a/AsbCloudApp/Services/IDailyReportService.cs b/AsbCloudApp/Services/IDailyReportService.cs
index 3943e86c..574a04bf 100644
--- a/AsbCloudApp/Services/IDailyReportService.cs
+++ b/AsbCloudApp/Services/IDailyReportService.cs
@@ -32,16 +32,6 @@ namespace AsbCloudApp.Services
///
Task AddAsync(int idWell, DateTime startDate, int idUser, CancellationToken token = default);
- ///
- /// изменить данные для суточного рапорта
- ///
- ///
- ///
- ///
- ///
- ///
- Task UpdateAsync(int idWell, DateTime date, DailyReportDto dto, CancellationToken token = default);
-
///
/// Сформировать файл рапорта
///
diff --git a/AsbCloudDb/Model/DailyReport/DailyReportInfo.cs b/AsbCloudDb/Model/DailyReport/DailyReportInfo.cs
index ea8fafe0..d5a7bfd6 100644
--- a/AsbCloudDb/Model/DailyReport/DailyReportInfo.cs
+++ b/AsbCloudDb/Model/DailyReport/DailyReportInfo.cs
@@ -7,7 +7,6 @@ namespace AsbCloudDb.Model
public Head Head { get; set; } = null!;
public Bha Bha { get; set; } = new();
public NoDrilling NoDrilling { get; set; } = new();
- public TimeBalance TimeBalance { get; set; } = new();
public Saub Saub { get; set; } = new();
public Sign Sign { get; set; } = new();
}
diff --git a/AsbCloudDb/Model/DailyReport/ItemInfo.cs b/AsbCloudDb/Model/DailyReport/ItemInfo.cs
index bf579080..3d7e6793 100644
--- a/AsbCloudDb/Model/DailyReport/ItemInfo.cs
+++ b/AsbCloudDb/Model/DailyReport/ItemInfo.cs
@@ -12,6 +12,6 @@ namespace AsbCloudDb.Model
///
/// дата последнего обновления блока
///
- public DateTimeOffset? LastUpdateDate { get; set; }
+ public DateTimeOffset LastUpdateDate { get; set; } = DateTimeOffset.Now;
}
}
diff --git a/AsbCloudDb/Model/DailyReport/TimeBalance.cs b/AsbCloudDb/Model/DailyReport/TimeBalance.cs
deleted file mode 100644
index db9a9ffc..00000000
--- a/AsbCloudDb/Model/DailyReport/TimeBalance.cs
+++ /dev/null
@@ -1,96 +0,0 @@
-namespace AsbCloudDb.Model.DailyReport
-{
- public class TimeBalance : ItemInfo
- {
- ///
- /// Бурение
- ///
- public string Drilling { get; set; } = string.Empty;
-
- ///
- /// Промывка
- ///
- public string Flushing { get; set; } = string.Empty;
-
- ///
- /// Наращивание
- ///
- public string Building { get; set; } = string.Empty;
-
- ///
- /// Проработка
- ///
- public string Elaboration { get; set; } = string.Empty;
-
- ///
- /// Расширка
- ///
- public string Extension { get; set; } = string.Empty;
-
- ///
- /// Ремонт
- ///
- public string Repair { get; set; } = string.Empty;
-
- ///
- /// КНБК
- ///
- public string Knbk { get; set; } = string.Empty;
-
- ///
- /// СПО
- ///
- public string Spo { get; set; } = string.Empty;
-
- ///
- /// ПЗР
- ///
- public string Pzr { get; set; } = string.Empty;
-
- ///
- /// ПВО
- ///
- public string Pvo { get; set; } = string.Empty;
-
- ///
- /// ПГР
- ///
- public string Pgr { get; set; } = string.Empty;
-
- ///
- /// ГИС
- ///
- public string Gis { get; set; } = string.Empty;
-
- ///
- /// ОЗЦ
- ///
- public string Ozc { get; set; } = string.Empty;
-
- ///
- /// Тех. работы
- ///
- public string EngineeringWorks { get; set; } = string.Empty;
-
- ///
- /// Снятие замера
- ///
- public string TakingMeasure { get; set; } = string.Empty;
-
- ///
- /// Цементирование
- ///
- public string Cementing { get; set; } = string.Empty;
-
- ///
- /// Простой
- ///
- public string Simple { get; set; } = string.Empty;
-
- ///
- /// НПВ
- ///
- public string Npv { get; set; } = string.Empty;
- }
-}
-
diff --git a/AsbCloudInfrastructure/Services/DailyReport/DailyReportService.cs b/AsbCloudInfrastructure/Services/DailyReport/DailyReportService.cs
index 1cc5f2b7..5a814373 100644
--- a/AsbCloudInfrastructure/Services/DailyReport/DailyReportService.cs
+++ b/AsbCloudInfrastructure/Services/DailyReport/DailyReportService.cs
@@ -47,52 +47,41 @@ namespace AsbCloudInfrastructure.Services.DailyReport
var query = db.DailyReports.Where(r => r.IdWell == idWell);
- DateOnly ExtractDate(DateTime dateTime)
- {
- var dateTimeOffset = dateTime.ToUtcDateTimeOffset(well!.Timezone.Hours);
- var date = new DateOnly(dateTimeOffset.Year, dateTimeOffset.Month, dateTimeOffset.Day);
- return date;
- }
-
if (begin is not null)
{
- var beginDateOnly = ExtractDate(begin.Value);
+ var beginDateOnly = ExtractDate(begin.Value, well);
query = query.Where(d => d.StartDate >= beginDateOnly);
}
if (end is not null)
{
- var endDateOnly = ExtractDate(end.Value);
+ var endDateOnly = ExtractDate(end.Value, well);
query = query.Where(d => d.StartDate <= endDateOnly);
}
- var entities = await query.OrderByDescending(e => e.StartDate).ToListAsync(token);
+ var entities = await query.OrderByDescending(e => e.StartDate)
+ .AsNoTracking()
+ .ToArrayAsync(token)
+ .ConfigureAwait(false);
- var dtos = entities.Select(Convert).ToList();
+ var factOperationsForDtos = await GetFactOperationsForDailyReportAsync(idWell, token);
- var factOperationsForDtos = await getFactOperationsForDailyReportAsync(idWell, token);
-
- foreach (var dto in dtos)
+ var dtos = new List(entities.Length);
+ foreach (var entity in entities)
{
- dto.TimeBalance.OperationsStat = (factOperationsForDtos
- .Where(o => DateOnly.FromDateTime(o.DateStart) == dto.StartDate)
- .GroupBy(o => o.IdCategory)
- .Select(g => new OperationStatDto() { Depth = g.Sum(o => o.DepthEnd - o.DepthStart) }));
-
- await SetUserNamesToDailyReportDtoAsync(dto, token);
- }
-
-
+ var dto = await Convert(entity, factOperationsForDtos, token);
+ dtos.Add(dto);
+ }
return dtos;
}
///
- /// получение фактических операций для суточного рапорта
+ /// Получение фактических операций для суточного рапорта
///
///
///
///
- private async Task> getFactOperationsForDailyReportAsync(int idWell, CancellationToken token)
+ private async Task> GetFactOperationsForDailyReportAsync(int idWell, CancellationToken token)
{
var request = new WellOperationRequest()
{
@@ -126,9 +115,7 @@ namespace AsbCloudInfrastructure.Services.DailyReport
if (block.IdUser is not null)
{
var user = await userRepository.GetOrDefaultAsync(block.IdUser.Value, token);
- block.UserName = user is not null
- ? string.Format("{0} {1} {2}", user.Surname, user.Name, user.Patronymic)
- : String.Empty;
+ block.UserName = user is not null ? user.MakeDisplayName() : $"userId:{block.IdUser.Value}";
}
}
@@ -138,35 +125,23 @@ namespace AsbCloudInfrastructure.Services.DailyReport
public async Task AddAsync(int idWell, DateTime startDate, int idUser, CancellationToken token = default)
{
var well = wellService.GetOrDefault(idWell);
- if (well is null || well.Timezone is null)
+ if (well is null)
throw new ArgumentInvalidException("idWell doesn`t exist", nameof(idWell));
- var startDateOnly = DateOnly.FromDateTime(startDate);
+ var startDateOnly = ExtractDate(startDate, well);
- var entity = await db.DailyReports
- .FirstOrDefaultAsync(r => r.IdWell == idWell && r.StartDate == startDateOnly, token);
- if (entity is not null)
- throw new Exception($"daily report on {startDateOnly} already exists");
+ var hasEntity = await db.DailyReports
+ .AnyAsync(r => r.IdWell == idWell && r.StartDate == startDateOnly, token);
+ if (hasEntity)
+ throw new ArgumentInvalidException($"daily report on {startDateOnly} already exists", nameof(startDateOnly));
- var customer = well.Companies.FirstOrDefault(company => company.IdCompanyType == 1);
- var contractor = well.Companies.FirstOrDefault(company => company.IdCompanyType == 2);
-
- entity = new AsbCloudDb.Model.DailyReport.DailyReport
+ var entity = new AsbCloudDb.Model.DailyReport.DailyReport
{
IdWell = idWell,
StartDate = startDateOnly,
Info = new DailyReportInfo()
{
- Head = new Head()
- {
- ReportDate = startDate.Date,
- WellName = well.Caption,
- ClusterName = well?.Cluster ?? String.Empty,
- Customer = customer?.Caption ?? String.Empty,
- Contractor = contractor?.Caption ?? String.Empty,
- IdUser = idUser,
- LastUpdateDate = DateTimeOffset.Now,
- }
+ Head = CreateHeadDailyReportBlock(well, startDate, idUser)
}
};
db.DailyReports.Add(entity);
@@ -174,31 +149,17 @@ namespace AsbCloudInfrastructure.Services.DailyReport
return result;
}
- public async Task UpdateAsync(int idWell, DateTime date, DailyReportDto dto, CancellationToken token)
- {
- var dateOffset = date.Date;
- var entity = await db.DailyReports
- .FirstOrDefaultAsync(r => r.IdWell == idWell &&
- r.StartDate.Year == dateOffset.Year &&
- r.StartDate.DayOfYear == dateOffset.DayOfYear
- , token);
-
- if (entity is null)
- return 0;
-
- entity.Info = Convert(dto);
- db.DailyReports.Update(entity);
- var result = await db.SaveChangesAsync(token);
- return result;
- }
-
public async Task UpdateBlockAsync(int idWell, DateTime startDate, ItemInfoDto dto, CancellationToken token)
{
+ var well = wellService.GetOrDefault(idWell);
+ if (well is null)
+ throw new ArgumentInvalidException("idWell doesn`t exist", nameof(idWell));
+
var startDateOnly = DateOnly.FromDateTime(startDate);
var entity = await db.DailyReports.FirstOrDefaultAsync(r => r.IdWell == idWell && r.StartDate == startDateOnly, token);
if (entity is null)
- return 0;
+ throw new ArgumentInvalidException("Daily report doesn`t exist", nameof(startDate));
dto.LastUpdateDate = DateTimeOffset.Now;
if (dto is HeadDto headDto)
@@ -207,8 +168,6 @@ namespace AsbCloudInfrastructure.Services.DailyReport
entity.Info.Bha = bhaDto.Adapt();
if (dto is NoDrillingDto noDrillingDto)
entity.Info.NoDrilling = noDrillingDto.Adapt();
- if (dto is TimeBalanceDto timeBalanceDto)
- entity.Info.TimeBalance = timeBalanceDto.Adapt();
if (dto is SaubDto saubDto)
entity.Info.Saub = saubDto.Adapt();
if (dto is SignDto signDto)
@@ -239,23 +198,73 @@ namespace AsbCloudInfrastructure.Services.DailyReport
, token);
if (entity is null)
- return null;
- var dto = Convert(entity);
+ throw new ArgumentInvalidException("Daily report doesn`t exist", nameof(date));
+
+ var factOperationsForDtos = await GetFactOperationsForDailyReportAsync(idWell, token);
+ var dto = await Convert(entity, factOperationsForDtos, token);
return dto;
}
- private static DailyReportDto Convert(AsbCloudDb.Model.DailyReport.DailyReport entity)
+ ///
+ /// конвертация данных из модели базы данных в dto
+ ///
+ /// модель базы данных
+ /// список фактичских операций для формирования суточного рапорта
+ ///
+ ///
+ private async Task Convert(
+ AsbCloudDb.Model.DailyReport.DailyReport entity,
+ IEnumerable factOperationsForDtos,
+ CancellationToken token)
{
var dto = entity.Info.Adapt();
dto.StartDate = entity.StartDate;
+
+ dto.TimeBalance.OperationsStat = (factOperationsForDtos
+ .Where(o => DateOnly.FromDateTime(o.DateStart) == dto.StartDate)
+ .GroupBy(o => o.IdCategory)
+ .Select(g => new OperationStatDto() { Depth = g.Sum(o => o.DepthEnd - o.DepthStart) }));
+
+ await SetUserNamesToDailyReportDtoAsync(dto, token);
+
return dto;
}
- private static DailyReportInfo Convert(DailyReportDto dto)
+ ///
+ /// Приведение данных к формату DateOnly с учетом часового пояса скважины
+ ///
+ ///
+ ///
+ ///
+ private DateOnly ExtractDate(DateTime dateTime, WellDto well)
{
- var entity = dto.Adapt();
- entity.Head.ReportDate = dto.Head.ReportDate.Date.Date;
- return entity;
+ var dateTimeOffset = dateTime.ToUtcDateTimeOffset(well!.Timezone.Hours);
+ var date = new DateOnly(dateTimeOffset.Year, dateTimeOffset.Month, dateTimeOffset.Day);
+ return date;
+ }
+
+ ///
+ /// Создание блока "Заголовок" по умолчанию
+ ///
+ ///
+ ///
+ ///
+ ///
+ private Head CreateHeadDailyReportBlock(WellDto well, DateTime startDate, int idUser)
+ {
+ var customer = well.Companies.FirstOrDefault(company => company.IdCompanyType == 1);
+ var contractor = well.Companies.FirstOrDefault(company => company.IdCompanyType == 2);
+
+ return new Head()
+ {
+ ReportDate = startDate.Date,
+ WellName = well.Caption,
+ ClusterName = well?.Cluster ?? string.Empty,
+ Customer = customer?.Caption ?? string.Empty,
+ Contractor = contractor?.Caption ?? string.Empty,
+ IdUser = idUser,
+ LastUpdateDate = DateTimeOffset.Now,
+ };
}
}
#nullable disable
diff --git a/AsbCloudWebApi/Controllers/DailyReportController.cs b/AsbCloudWebApi/Controllers/DailyReportController.cs
index bc44a4e1..0c5cfc38 100644
--- a/AsbCloudWebApi/Controllers/DailyReportController.cs
+++ b/AsbCloudWebApi/Controllers/DailyReportController.cs
@@ -1,4 +1,5 @@
using AsbCloudApp.Data.DailyReport;
+using AsbCloudApp.Exceptions;
using AsbCloudApp.Repositories;
using AsbCloudApp.Services;
using Microsoft.AspNetCore.Authorization;
@@ -71,19 +72,17 @@ namespace AsbCloudWebApi.Controllers
var result = await dailyReportService.AddAsync(idWell, startDate, (int)idUser, token);
return Ok(result);
}
- catch (Exception ex)
+ catch (ArgumentInvalidException ex)
{
return BadRequest(ex.Message);
}
}
-
-
///
/// Сохранение изменений набора данных для формирования рапорта (заголовок)
///
///
- ///
+ /// Дата без учета времени
///
///
///
@@ -91,18 +90,14 @@ namespace AsbCloudWebApi.Controllers
[ProducesResponseType(typeof(int), (int)System.Net.HttpStatusCode.OK)]
public async Task UpdateHeadAsync(int idWell, [Required] DateTime date, [Required] HeadDto dto, CancellationToken token = default)
{
- if (!setEditorIdToDailyReportBlock(dto))
- return Forbid();
-
- var result = await dailyReportService.UpdateBlockAsync(idWell, date, dto, token);
- return Ok(result);
+ return await UpdateReportBlockAsync(idWell, date, dto, token);
}
///
/// Сохранение изменений набора данных для формирования рапорта (блок КНБК)
///
///
- ///
+ /// Дата без учета времени
///
///
///
@@ -110,18 +105,14 @@ namespace AsbCloudWebApi.Controllers
[ProducesResponseType(typeof(int), (int)System.Net.HttpStatusCode.OK)]
public async Task UpdateBhaAsync(int idWell, [Required] DateTime date, [Required] BhaDto dto, CancellationToken token = default)
{
- if (!setEditorIdToDailyReportBlock(dto))
- return Forbid();
-
- var result = await dailyReportService.UpdateBlockAsync(idWell, date, dto, token);
- return Ok(result);
+ return await UpdateReportBlockAsync(idWell, date, dto, token);
}
///
/// Сохранение изменений набора данных для формирования рапорта (безметражные работы)
///
///
- ///
+ /// Дата без учета времени
///
///
///
@@ -129,18 +120,14 @@ namespace AsbCloudWebApi.Controllers
[ProducesResponseType(typeof(int), (int)System.Net.HttpStatusCode.OK)]
public async Task UpdateNoDrillingAsync(int idWell, [Required] DateTime date, [Required] NoDrillingDto dto, CancellationToken token = default)
{
- if (!setEditorIdToDailyReportBlock(dto))
- return Forbid();
-
- var result = await dailyReportService.UpdateBlockAsync(idWell, date, dto, token);
- return Ok(result);
+ return await UpdateReportBlockAsync(idWell, date, dto, token);
}
///
/// Сохранение изменений набора данных для формирования рапорта (САУБ)
///
///
- ///
+ /// Дата без учета времени
///
///
///
@@ -148,18 +135,14 @@ namespace AsbCloudWebApi.Controllers
[ProducesResponseType(typeof(int), (int)System.Net.HttpStatusCode.OK)]
public async Task UpdateSaubAsync(int idWell, [Required] DateTime date, [Required] SaubDto dto, CancellationToken token = default)
{
- if (!setEditorIdToDailyReportBlock(dto))
- return Forbid();
-
- var result = await dailyReportService.UpdateBlockAsync(idWell, date, dto, token);
- return Ok(result);
+ return await UpdateReportBlockAsync(idWell, date, dto, token);
}
///
/// Сохранение изменений набора данных для формирования рапорта (подпись)
///
///
- ///
+ /// Дата без учета времени
///
///
///
@@ -167,7 +150,20 @@ namespace AsbCloudWebApi.Controllers
[ProducesResponseType(typeof(int), (int)System.Net.HttpStatusCode.OK)]
public async Task UpdateSignAsync(int idWell, [Required] DateTime date, [Required] SignDto dto, CancellationToken token = default)
{
- if (!setEditorIdToDailyReportBlock(dto))
+ return await UpdateReportBlockAsync(idWell, date, dto, token);
+ }
+
+ ///
+ /// Обновление блока суточного рапорта
+ ///
+ /// ключ скважины
+ /// дата суточного рапорта
+ ///
+ ///
+ ///
+ private async Task UpdateReportBlockAsync(int idWell, DateTime date, ItemInfoDto dto, CancellationToken token)
+ {
+ if (!SetEditorIdToDailyReportBlock(dto))
return Forbid();
var result = await dailyReportService.UpdateBlockAsync(idWell, date, dto, token);
@@ -175,11 +171,11 @@ namespace AsbCloudWebApi.Controllers
}
///
- /// записать ключ пользователя, вносящего изменения в блок суточного рапорта
+ /// Записать ключ пользователя, вносящего изменения в блок суточного рапорта
///
///
///
- private bool setEditorIdToDailyReportBlock(ItemInfoDto dto)
+ private bool SetEditorIdToDailyReportBlock(ItemInfoDto dto)
{
var idUser = User.GetUserId();
if (idUser is null)