2023-11-03 19:35:52 +05:00
|
|
|
|
using System;
|
|
|
|
|
using System.Collections.Generic;
|
|
|
|
|
using System.IO;
|
|
|
|
|
using System.Linq;
|
|
|
|
|
using System.Reflection;
|
|
|
|
|
using System.Threading;
|
|
|
|
|
using System.Threading.Tasks;
|
|
|
|
|
using AsbCloudApp.Data.DailyReport;
|
|
|
|
|
using AsbCloudApp.Data.DailyReport.Blocks;
|
|
|
|
|
using AsbCloudApp.Data.DailyReport.Blocks.Sign;
|
|
|
|
|
using AsbCloudApp.Data.DailyReport.Blocks.Subsystems;
|
|
|
|
|
using AsbCloudApp.Data.DailyReport.Blocks.TimeBalance;
|
|
|
|
|
using AsbCloudApp.Data.DailyReport.Blocks.WellOperation;
|
|
|
|
|
using AsbCloudApp.Services.DailyReport;
|
|
|
|
|
using ClosedXML.Excel;
|
|
|
|
|
|
|
|
|
|
namespace AsbCloudInfrastructure.Services.DailyReport;
|
|
|
|
|
|
|
|
|
|
public class DailyReportExportService : IDailyReportExportService
|
|
|
|
|
{
|
|
|
|
|
private const int rowStartScheduleBlock = 20;
|
|
|
|
|
private const int rowStartSubsystemBlock = 26;
|
|
|
|
|
private const int rowStartFactWellOperationBlock = 39;
|
|
|
|
|
private const int rowStartTimeBalanceBlock = 62;
|
|
|
|
|
private const int rowStartProcessMapWellDrillingBlock = 68;
|
|
|
|
|
|
|
|
|
|
private const int columnTimeBalanceDurationPlan = 3;
|
2023-11-15 17:23:17 +05:00
|
|
|
|
private const int columnTimeBalanceDurationFact = 6;
|
2023-11-03 19:35:52 +05:00
|
|
|
|
private const int columnTimeBalanceReasonDeviation = 8;
|
|
|
|
|
private const int columnTimeBalanceDrillingDeviationPerSection = 10;
|
2023-11-14 11:01:34 +05:00
|
|
|
|
private const int columnTimeBalanceDrillingDeviationPerDay = 11;
|
2023-11-03 19:35:52 +05:00
|
|
|
|
|
|
|
|
|
private const int columnSheduleDriller = 3;
|
|
|
|
|
private const int columnSheduleShiftStart = 7;
|
|
|
|
|
private const int columnSheduleShiftEnd = 8;
|
|
|
|
|
|
|
|
|
|
private const int columnSubsystemName = 2;
|
|
|
|
|
private const int columnUseSubsystemPerDayUsedTimeHours = 3;
|
|
|
|
|
private const int columnUseSubsystemPerDaySumDepthInterval = 4;
|
|
|
|
|
private const int columnUseSubsystemPerDayKUsage = 5;
|
|
|
|
|
|
|
|
|
|
private const int columnUseSubsystemPerWellUsedTimeHours = 6;
|
|
|
|
|
private const int columnUseSubsystemPerWellSumDepthInterval = 7;
|
|
|
|
|
private const int columnUseSubsystemPerWellKUsage = 8;
|
|
|
|
|
|
2023-11-07 15:57:15 +05:00
|
|
|
|
private const int columnProcessMapWellDrillingBlockDrillingMode = 2;
|
2023-11-03 19:35:52 +05:00
|
|
|
|
private const int columnProcessMapWellDrillingBlockWellBoreDepth = 3;
|
|
|
|
|
private const int columnProcessMapWellDrillingBlockMechDrillingHours = 4;
|
|
|
|
|
private const int columnProcessMapWellDrillingBlockRopPlan = 5;
|
|
|
|
|
private const int columnProcessMapWellDrillingBlockRopFact = 6;
|
|
|
|
|
|
|
|
|
|
private const int columnWellOperationCategory = 2;
|
|
|
|
|
private const int columnWellOperationDurationHours = 4;
|
|
|
|
|
|
|
|
|
|
private const string cellCustomer = "C2";
|
|
|
|
|
private const string cellContractor = "C3";
|
|
|
|
|
private const string cellDeposit = "C5";
|
|
|
|
|
private const string cellCluster = "C6";
|
2023-11-14 11:01:34 +05:00
|
|
|
|
private const string cellWellCaption = "C7";
|
2023-11-03 19:35:52 +05:00
|
|
|
|
private const string cellWellType = "C8";
|
2023-11-14 11:01:34 +05:00
|
|
|
|
private const string cellDate = "C12";
|
2023-11-03 19:35:52 +05:00
|
|
|
|
private const string cellDepthStart = "C13";
|
|
|
|
|
private const string cellDepthEnd = "D13";
|
|
|
|
|
|
|
|
|
|
private const string cellTrajectoryBlockWellboreDepth = "B17";
|
|
|
|
|
private const string cellTrajectoryBlockVerticalDepth = "C17";
|
|
|
|
|
private const string cellTrajectoryBlockZenithAngle = "D17";
|
|
|
|
|
private const string cellTrajectoryBlockAzimuthGeo = "E17";
|
|
|
|
|
|
|
|
|
|
private const string cellTimeBalanceBlockSection = "C60";
|
|
|
|
|
private const string cellTimeBalanceBlockWellDepthPlan = "C61";
|
2023-11-09 15:01:29 +05:00
|
|
|
|
private const string cellSectionDrillingHours = "F77";
|
2023-11-03 19:35:52 +05:00
|
|
|
|
private const string cellTimeBalanceBlockWellDepthFact = "F78";
|
2023-11-09 15:01:29 +05:00
|
|
|
|
private const string cellTimeBalanceBlockWellOperationSlipsTimeCount = "F79";
|
2023-11-03 19:35:52 +05:00
|
|
|
|
|
|
|
|
|
private const string cellSubsystemComment = "D35";
|
2023-11-15 12:10:48 +05:00
|
|
|
|
private const string cellSubsystemTvgLagDays = "F80";
|
|
|
|
|
private const string cellSubsystemMeasurementsPerDay = "F81";
|
2023-11-09 15:01:29 +05:00
|
|
|
|
private const string cellSubsystemWellBore = "C9";
|
2023-11-03 19:35:52 +05:00
|
|
|
|
private const string cellSubsystemTotalRopPlan = "E70";
|
|
|
|
|
|
2023-11-15 12:10:48 +05:00
|
|
|
|
private const string cellSignDrillingMaster = "C85";
|
|
|
|
|
private const string cellSignSupervisor = "C86";
|
2023-11-03 19:35:52 +05:00
|
|
|
|
|
|
|
|
|
private readonly IDailyReportService dailyReportService;
|
|
|
|
|
|
|
|
|
|
public DailyReportExportService(IDailyReportService dailyReportService)
|
|
|
|
|
{
|
|
|
|
|
this.dailyReportService = dailyReportService;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
public async Task<(string FileName, Stream File)> ExportAsync(int idWell, DateTime dailyReportDateStart, CancellationToken cancellationToken)
|
|
|
|
|
{
|
|
|
|
|
var dailyReport = await dailyReportService.GetAsync(idWell, dailyReportDateStart, cancellationToken);
|
|
|
|
|
|
|
|
|
|
var stream = await GenerateFileAsync(dailyReport, cancellationToken);
|
|
|
|
|
|
2023-11-14 11:01:34 +05:00
|
|
|
|
var fileName = $"Суточный_рапорт_по_скважине_{dailyReport.WellCaption}_куст_{dailyReport.Cluster}_от_{dailyReport.Date:yy-MM-dd}.xlsx";
|
2023-11-03 19:35:52 +05:00
|
|
|
|
|
|
|
|
|
return (fileName, stream);
|
|
|
|
|
}
|
|
|
|
|
|
2023-11-07 15:57:15 +05:00
|
|
|
|
private static async Task<Stream> GenerateFileAsync(DailyReportDto dailyReport, CancellationToken cancellationToken)
|
2023-11-03 19:35:52 +05:00
|
|
|
|
{
|
|
|
|
|
using var excelTemplateStream = await Assembly
|
|
|
|
|
.GetExecutingAssembly()
|
|
|
|
|
.GetTemplateCopyStreamAsync("DailyReportTemplate.xlsx", cancellationToken);
|
|
|
|
|
|
|
|
|
|
using var workbook = new XLWorkbook(excelTemplateStream, XLEventTracking.Disabled);
|
|
|
|
|
|
|
|
|
|
AddDailyReportToWorkBook(workbook, dailyReport);
|
|
|
|
|
|
|
|
|
|
var memoryStream = new MemoryStream();
|
|
|
|
|
workbook.SaveAs(memoryStream, new SaveOptions { });
|
|
|
|
|
memoryStream.Seek(0, SeekOrigin.Begin);
|
|
|
|
|
return memoryStream;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
private static void AddDailyReportToWorkBook(IXLWorkbook workbook, DailyReportDto dailyReport)
|
|
|
|
|
{
|
|
|
|
|
const string sheetName = "Суточный отчёт";
|
|
|
|
|
|
|
|
|
|
var sheet = workbook.Worksheets.FirstOrDefault(ws => ws.Name == sheetName)
|
|
|
|
|
?? throw new FileFormatException($"Книга excel не содержит листа {sheetName}.");
|
|
|
|
|
|
|
|
|
|
sheet.Cell(cellCustomer).Value = dailyReport.Customer;
|
|
|
|
|
sheet.Cell(cellContractor).Value = dailyReport.Contractor;
|
|
|
|
|
sheet.Cell(cellDeposit).Value = dailyReport.Deposit;
|
|
|
|
|
sheet.Cell(cellCluster).Value = dailyReport.Cluster;
|
2023-11-14 11:01:34 +05:00
|
|
|
|
sheet.Cell(cellWellCaption).Value = dailyReport.WellCaption;
|
2023-11-03 19:35:52 +05:00
|
|
|
|
sheet.Cell(cellWellType).Value = dailyReport.WellType;
|
2023-11-14 11:01:34 +05:00
|
|
|
|
sheet.Cell(cellDate).Value = dailyReport.Date;
|
2023-11-03 19:35:52 +05:00
|
|
|
|
sheet.Cell(cellDepthStart).Value = dailyReport.DepthStart;
|
|
|
|
|
sheet.Cell(cellDepthEnd).Value = dailyReport.DepthEnd;
|
|
|
|
|
|
|
|
|
|
if (dailyReport.TimeBalanceBlock is not null)
|
|
|
|
|
AddTimeBalanceBlockToSheet(sheet, dailyReport.TimeBalanceBlock);
|
|
|
|
|
|
|
|
|
|
if (dailyReport.SubsystemBlock is not null)
|
|
|
|
|
AddSubsystemBlockToSheet(sheet, dailyReport.SubsystemBlock);
|
|
|
|
|
|
|
|
|
|
if (dailyReport.SignBlock is not null)
|
|
|
|
|
AddSignBlockToSheet(sheet, dailyReport.SignBlock);
|
|
|
|
|
|
|
|
|
|
AddTrajectoryBlockToSheet(sheet, dailyReport.TrajectoryBlock);
|
|
|
|
|
AddScheduleBlockToSheet(sheet, dailyReport.ScheduleBlock);
|
|
|
|
|
AddProcessMapWellDrillingBlockToSheet(sheet, dailyReport.ProcessMapWellDrillingBlock);
|
|
|
|
|
AddFactWellOperationBlockToSheet(sheet, dailyReport.FactWellOperationBlock);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
private static void AddTrajectoryBlockToSheet(IXLWorksheet sheet, TrajectoryBlockDto trajectoryBlock)
|
|
|
|
|
{
|
|
|
|
|
sheet.Cell(cellTrajectoryBlockWellboreDepth).Value = trajectoryBlock.WellboreDepth;
|
|
|
|
|
sheet.Cell(cellTrajectoryBlockVerticalDepth).Value = trajectoryBlock.VerticalDepth;
|
|
|
|
|
sheet.Cell(cellTrajectoryBlockZenithAngle).Value = trajectoryBlock.ZenithAngle;
|
|
|
|
|
sheet.Cell(cellTrajectoryBlockAzimuthGeo).Value = trajectoryBlock.AzimuthGeo;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
private static void AddTimeBalanceBlockToSheet(IXLWorksheet sheet, TimeBalanceBlockDto timeBalanceBlock)
|
|
|
|
|
{
|
|
|
|
|
var rowCurrent = rowStartTimeBalanceBlock;
|
|
|
|
|
|
|
|
|
|
foreach (var wellOperation in timeBalanceBlock.WellOperations.OrderBy(w => w.IdWellOperation))
|
|
|
|
|
{
|
2023-11-14 11:01:34 +05:00
|
|
|
|
sheet.Cell(rowCurrent, columnTimeBalanceDurationPlan).Value = wellOperation.DurationHours.Plan;
|
|
|
|
|
sheet.Cell(rowCurrent, columnTimeBalanceDurationFact).Value = wellOperation.DurationHours.Fact;
|
2023-11-03 19:35:52 +05:00
|
|
|
|
sheet.Cell(rowCurrent, columnTimeBalanceReasonDeviation).Value = wellOperation.ReasonDeviation;
|
|
|
|
|
sheet.Cell(rowCurrent, columnTimeBalanceDrillingDeviationPerSection).Value = wellOperation.DrillingDeviationPerSection;
|
2023-11-14 11:01:34 +05:00
|
|
|
|
sheet.Cell(rowCurrent, columnTimeBalanceDrillingDeviationPerDay).Value = wellOperation.DrillingDeviationPerDay;
|
2023-11-03 19:35:52 +05:00
|
|
|
|
|
|
|
|
|
rowCurrent++;
|
|
|
|
|
}
|
|
|
|
|
|
2023-11-07 15:57:15 +05:00
|
|
|
|
sheet.Cell(cellTimeBalanceBlockSection).Value = timeBalanceBlock.SectionName;
|
2023-11-14 11:01:34 +05:00
|
|
|
|
sheet.Cell(cellTimeBalanceBlockWellDepthPlan).Value = timeBalanceBlock.WellDepth.Plan;
|
|
|
|
|
sheet.Cell(cellTimeBalanceBlockWellDepthFact).Value = timeBalanceBlock.WellDepth.Fact;
|
2023-11-09 15:01:29 +05:00
|
|
|
|
sheet.Cell(cellTimeBalanceBlockWellOperationSlipsTimeCount).Value = timeBalanceBlock.WellOperationSlipsTimeCount;
|
2023-11-03 19:35:52 +05:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
private static void AddSubsystemBlockToSheet(IXLWorksheet sheet, SubsystemBlockDto subsystemBlock)
|
|
|
|
|
{
|
|
|
|
|
var rowСurrent = rowStartSubsystemBlock;
|
|
|
|
|
|
2023-11-15 17:23:17 +05:00
|
|
|
|
foreach (var subsystem in subsystemBlock.Subsystems)
|
2023-11-03 19:35:52 +05:00
|
|
|
|
{
|
2023-11-15 17:23:17 +05:00
|
|
|
|
sheet.Cell(rowСurrent, columnSubsystemName).Value = subsystem.Name;
|
2023-11-03 19:35:52 +05:00
|
|
|
|
|
2023-11-15 17:23:17 +05:00
|
|
|
|
sheet.Cell(rowСurrent, columnUseSubsystemPerDayUsedTimeHours).Value = subsystem.UsagePerDay?.UsedTimeHours;
|
|
|
|
|
sheet.Cell(rowСurrent, columnUseSubsystemPerDaySumDepthInterval).Value = subsystem.UsagePerDay?.SumDepthInterval;
|
|
|
|
|
sheet.Cell(rowСurrent, columnUseSubsystemPerDayKUsage).Value = subsystem.UsagePerDay?.KUsage;
|
2023-11-03 19:35:52 +05:00
|
|
|
|
|
2023-11-15 17:23:17 +05:00
|
|
|
|
sheet.Cell(rowСurrent, columnUseSubsystemPerWellUsedTimeHours).Value = subsystem.UsagePerWell?.UsedTimeHours;
|
|
|
|
|
sheet.Cell(rowСurrent, columnUseSubsystemPerWellSumDepthInterval).Value = subsystem.UsagePerWell?.SumDepthInterval;
|
|
|
|
|
sheet.Cell(rowСurrent, columnUseSubsystemPerWellKUsage).Value = subsystem.UsagePerWell?.KUsage;
|
2023-11-03 19:35:52 +05:00
|
|
|
|
|
|
|
|
|
rowСurrent++;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
sheet.Cell(cellSubsystemComment).Value = subsystemBlock.Comment;
|
2023-11-15 12:10:48 +05:00
|
|
|
|
sheet.Cell(cellSubsystemTvgLagDays).Value = subsystemBlock.TvgLagDays;
|
2023-11-09 15:01:29 +05:00
|
|
|
|
sheet.Cell(cellSubsystemMeasurementsPerDay).Value = subsystemBlock.MeasurementsPerDay;
|
|
|
|
|
sheet.Cell(cellSubsystemWellBore).Value = subsystemBlock.WellBore;
|
2023-11-03 19:35:52 +05:00
|
|
|
|
sheet.Cell(cellSubsystemTotalRopPlan).Value = subsystemBlock.TotalRopPlan;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
private static void AddScheduleBlockToSheet(IXLWorksheet sheet, IEnumerable<ScheduleRecordDto> scheduleBlock)
|
|
|
|
|
{
|
|
|
|
|
var rowCurrent = rowStartScheduleBlock;
|
|
|
|
|
|
|
|
|
|
foreach (var schedule in scheduleBlock.OrderBy(s => s.ShiftStart))
|
|
|
|
|
{
|
|
|
|
|
sheet.Cell(rowCurrent, columnSheduleDriller).Value = $"{schedule.Surname} {schedule.Name} {schedule.Patronymic}";
|
|
|
|
|
sheet.Cell(rowCurrent, columnSheduleShiftStart).Value = schedule.ShiftStart;
|
|
|
|
|
sheet.Cell(rowCurrent, columnSheduleShiftEnd).Value = schedule.ShiftEnd;
|
|
|
|
|
|
|
|
|
|
rowCurrent++;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
private static void AddProcessMapWellDrillingBlockToSheet(IXLWorksheet sheet,
|
|
|
|
|
IEnumerable<ProcessMapWellDrillingRecordDto> processMapWellDrillingBlock)
|
|
|
|
|
{
|
|
|
|
|
var rowCurrent = rowStartProcessMapWellDrillingBlock;
|
|
|
|
|
|
2023-11-07 15:57:15 +05:00
|
|
|
|
foreach (var processMapWellDrilling in processMapWellDrillingBlock.OrderBy(p => p.DrillingMode))
|
2023-11-03 19:35:52 +05:00
|
|
|
|
{
|
2023-11-07 15:57:15 +05:00
|
|
|
|
sheet.Cell(rowCurrent, columnProcessMapWellDrillingBlockDrillingMode).Value = processMapWellDrilling.DrillingMode;
|
2023-11-03 19:35:52 +05:00
|
|
|
|
sheet.Cell(rowCurrent, columnProcessMapWellDrillingBlockWellBoreDepth).Value = processMapWellDrilling.WellBoreDepth;
|
|
|
|
|
sheet.Cell(rowCurrent, columnProcessMapWellDrillingBlockMechDrillingHours).Value = processMapWellDrilling.MechDrillingHours;
|
|
|
|
|
sheet.Cell(rowCurrent, columnProcessMapWellDrillingBlockRopPlan).Value = processMapWellDrilling.Rop.Plan;
|
|
|
|
|
sheet.Cell(rowCurrent, columnProcessMapWellDrillingBlockRopFact).Value = processMapWellDrilling.Rop.Fact;
|
|
|
|
|
|
|
|
|
|
rowCurrent++;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
private static void AddFactWellOperationBlockToSheet(IXLWorksheet sheet, WellOperationBlockDto factWellOperationBlock)
|
|
|
|
|
{
|
2023-11-09 15:01:29 +05:00
|
|
|
|
sheet.Cell(cellSectionDrillingHours).Value = factWellOperationBlock.SectionDrillingHours;
|
2023-11-03 19:35:52 +05:00
|
|
|
|
|
2023-11-07 15:57:15 +05:00
|
|
|
|
foreach (var factOperation in factWellOperationBlock.WellOperations.OrderBy(w => w.CategoryName))
|
2023-11-03 19:35:52 +05:00
|
|
|
|
{
|
2023-11-07 15:57:15 +05:00
|
|
|
|
sheet.Cell(rowStartFactWellOperationBlock, columnWellOperationCategory).Value = factOperation.CategoryName;
|
2023-11-03 19:35:52 +05:00
|
|
|
|
sheet.Cell(rowStartFactWellOperationBlock, columnWellOperationDurationHours).Value = factOperation.DurationHours;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
private static void AddSignBlockToSheet(IXLWorksheet sheet, SignBlockDto signBlock)
|
|
|
|
|
{
|
|
|
|
|
sheet.Cell(cellSignDrillingMaster).Value = signBlock.DrillingMaster?.ToString();
|
|
|
|
|
sheet.Cell(cellSignSupervisor).Value = signBlock.Supervisor?.ToString();
|
|
|
|
|
}
|
|
|
|
|
}
|