diff --git a/PARR.API/Contracts/V1/Requests/Queries/RobotTaskQuery.cs b/PARR.API/Contracts/V1/Requests/Queries/RobotTaskQuery.cs
index c503ff61..8fc3d2d5 100644
--- a/PARR.API/Contracts/V1/Requests/Queries/RobotTaskQuery.cs
+++ b/PARR.API/Contracts/V1/Requests/Queries/RobotTaskQuery.cs
@@ -1,10 +1,15 @@
namespace PARR.API.Contracts.V1.Requests.Queries
{
- public class RobotTaskQuery
+ public record RobotTaskQuery
{
///
/// Установить статус задания - InProgress (Робот взял в работу)
///
- public bool? SetInProgressStatus { get; set; }
+ public bool? SetInProgressStatus { get; init; }
+
+ ///
+ /// Идентификатор робота
+ ///
+ public string? RobotId { get; init; }
}
}
diff --git a/PARR.API/Contracts/V1/Requests/RobotHistoryRequest.cs b/PARR.API/Contracts/V1/Requests/RobotHistoryRequest.cs
index 872f2e54..524d2d40 100644
--- a/PARR.API/Contracts/V1/Requests/RobotHistoryRequest.cs
+++ b/PARR.API/Contracts/V1/Requests/RobotHistoryRequest.cs
@@ -2,14 +2,19 @@
namespace PARR.API.Contracts.V1.Requests
{
- public class RobotHistoryRequest
+ public record RobotHistoryRequest
{
- public RobotHistoryLevelEnum HistoryLevel { get; set; }
+ public RobotHistoryLevelEnum HistoryLevel { get; init; }
- public string? RobotMessage { get; set; }
+ public string? RobotMessage { get; init; }
- public string? EsppMessage { get; set; }
+ public string? EsppMessage { get; init; }
- public Guid TaskId { get; set; }
+ public Guid TaskId { get; init; }
+
+ ///
+ /// ИД робота
+ ///
+ public string? RobotId { get; init; }
}
}
diff --git a/PARR.API/Contracts/V1/Responses/RobotHistoryResponse.cs b/PARR.API/Contracts/V1/Responses/RobotHistoryResponse.cs
index e52480a4..2daf18f0 100644
--- a/PARR.API/Contracts/V1/Responses/RobotHistoryResponse.cs
+++ b/PARR.API/Contracts/V1/Responses/RobotHistoryResponse.cs
@@ -26,6 +26,8 @@
public string? RobotIp { get; set; }
+ public string? RobotId { get; set; }
+
public UserBaseResponse? User { get; set; }
}
diff --git a/PARR.API/Controllers/V1/RobotHistoryController.cs b/PARR.API/Controllers/V1/RobotHistoryController.cs
index 721297c1..e47734e4 100644
--- a/PARR.API/Controllers/V1/RobotHistoryController.cs
+++ b/PARR.API/Controllers/V1/RobotHistoryController.cs
@@ -123,7 +123,8 @@ namespace PARR.API.Controllers.V1
EsppMessage = request.EsppMessage,
TaskStatusCode = config.TaskStatusCode,
RobotConfigurationId = request.TaskId,
- RobotIp = clientService.GetClientIp()?.ToString()
+ RobotIp = clientService.GetClientIp()?.ToString(),
+ RobotId = request.RobotId
};
if (!await robotHistoryService.CreateAsync(history) || !await robotHistoryService.CommitAsync())
diff --git a/PARR.API/Controllers/V1/RobotTaskController.cs b/PARR.API/Controllers/V1/RobotTaskController.cs
index 4293d917..42047ae1 100644
--- a/PARR.API/Controllers/V1/RobotTaskController.cs
+++ b/PARR.API/Controllers/V1/RobotTaskController.cs
@@ -1,62 +1,55 @@
using AutoMapper;
using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Mvc;
-using Microsoft.EntityFrameworkCore;
using PARR.API.Contracts.V1;
using PARR.API.Contracts.V1.Requests.Queries;
using PARR.API.Contracts.V1.Responses;
using PARR.API.Contracts.V1.Responses.Base;
using PARR.API.Controllers.V1.Base;
using PARR.API.Services.Interfaces;
-using PARR.BLL.Helpers;
-using PARR.Core.Repositories.Interfaces;
-using PARR.Core.Services.NextRunServices;
-using PARR.Core.Services.Shortcodes;
+using PARR.Core.Services.RobotTask.Interfaces;
using PARR.Domain.Common.Roles;
-using PARR.Domain.Entities;
using PARR.Domain.Entities.Base.History;
using PARR.Domain.Enums;
-using PARR.Domain.Settings;
+using PARR.Domain.Exceptions;
namespace PARR.API.Controllers.V1
{
[Authorize(Roles = ParrRoles.EsppRobot.RoleOrAdmin)]
public class RobotTaskController : BaseApiController
{
+ private readonly IRobotTaskService robotTaskService;
+
private readonly IMapper mapper;
- private readonly SettingsFromDb settingsFromDb;
- private readonly IRobotConfigurationRepository robotConfigurationService;
- //private readonly IEsppScheduleTransformService esppScheduleTransformService;
- private readonly ILogger logger;
+ //private readonly SettingsFromDb settingsFromDb;
+ //private readonly IRobotConfigurationRepository robotConfigurationService;
+ //private readonly ILogger logger;
private readonly IClientService clientService;
- private readonly IRobotHistoryRepository robotHistoryService;
- private readonly IShortcodesService shortcodesService;
- private readonly INextRunService nextRunService;
- //private readonly IScheduleResponseAreaTimeOffsetService scheduleResponseAreaTimeOffsetService;
+ //private readonly IRobotHistoryRepository robotHistoryService;
+ //private readonly IShortcodesService shortcodesService;
+ //private readonly INextRunService nextRunService;
public RobotTaskController(
IMapper mapper,
- SettingsFromDb settingsFromDb,
- IRobotConfigurationRepository robotConfigurationService,
- //IEsppScheduleTransformService esppScheduleTransformService,
- ILogger logger,
+ //SettingsFromDb settingsFromDb,
+ //IRobotConfigurationRepository robotConfigurationService,
+ //ILogger logger,
IClientService clientService,
- IRobotHistoryRepository robotHistoryService,
- IShortcodesService shortcodesService,
- INextRunService nextRunService
- //IScheduleResponseAreaTimeOffsetService scheduleResponseAreaTimeOffsetService
+ //IRobotHistoryRepository robotHistoryService,
+ //IShortcodesService shortcodesService,
+ //INextRunService nextRunService
+ IRobotTaskService robotTaskService
)
{
+ this.robotTaskService = robotTaskService;
this.mapper = mapper;
- this.settingsFromDb = settingsFromDb;
- this.robotConfigurationService = robotConfigurationService;
- //this.esppScheduleTransformService = esppScheduleTransformService;
- this.logger = logger;
+ //this.settingsFromDb = settingsFromDb;
+ //this.robotConfigurationService = robotConfigurationService;
+ //this.logger = logger;
this.clientService = clientService;
- this.robotHistoryService = robotHistoryService;
- this.shortcodesService = shortcodesService;
- this.nextRunService = nextRunService;
- //this.scheduleResponseAreaTimeOffsetService = scheduleResponseAreaTimeOffsetService;
+ //this.robotHistoryService = robotHistoryService;
+ //this.shortcodesService = shortcodesService;
+ //this.nextRunService = nextRunService;
}
@@ -65,272 +58,320 @@ namespace PARR.API.Controllers.V1
///
///
///
+ ///
///
[HttpGet(ApiRoutes.RobotTask.GetByRobotAndStatusTask)]
public async Task GetByRobotAndStatusTask([FromRoute] RobotsEnum robotCode, [FromRoute] TaskStatusEnum taskStatusCode, [FromQuery] RobotTaskQuery requestQuery)
{
- //Ищем все задания с превышенным кол-вом попыток и с просроченным временем и ставим им статус ошибки
- await robotConfigurationService.FindUnfulfilledTaskAndSetRobotErrorStatusAsync(settingsFromDb.RobotAttemptsNumber, settingsFromDb.RobotWaitTime);
-
-
- var query = robotConfigurationService.Get().AsSingleQuery()
- .Where(t => t.RobotCode == (int)robotCode && t.TaskStatusCode == (int)taskStatusCode);
-
switch (robotCode)
{
case RobotsEnum.TemplateOrder:
- // шаблоны
- query = query
- .Include(t => t.Template)
- .ThenInclude(t => t!.Unit)
- .ThenInclude(t => t!.UnitValues)
- .ThenInclude(t => t.Field)
- .Include(t => t.Template)
- .ThenInclude(t => t!.Unit)
- .ThenInclude(t => t!.UnitValues)
- .ThenInclude(t => t.Value)
- .Include(t => t.Template)
- .ThenInclude(a => a!.Job)
- .ThenInclude(t => t!.Group)
- .ThenInclude(g => g.GroupType)
- .Include(t => t.Template)
- .ThenInclude(w => w!.Job)
- .ThenInclude(t => t!.Tnk)
- .ThenInclude(s => s!.Subprocess)
- .ThenInclude(p => p!.Process);
-
- query = query
- .Include(t => t.Template)
- .ThenInclude(t => t!.UnitsInTemplate);
-
- break;
+ var templateTask = await robotTaskService.GetTemplateTaskAsync(
+ taskStatusCode,
+ requestQuery.SetInProgressStatus ?? false,
+ clientService.GetClientIp()?.ToString(),
+ requestQuery.RobotId
+ );
+ var templateResponse = mapper.Map(templateTask);
+ return Ok(new Response(templateResponse, true));
case RobotsEnum.ScheduleOrder:
- //расписание
- query = query
- .AsSingleQuery()
- .Include(t => t.Template)
- .ThenInclude(t => t!.Unit)
- .ThenInclude(t => t!.UnitValues)
- .ThenInclude(t => t.Field)
- .Include(t => t.Template)
- .ThenInclude(t => t!.Unit)
- .ThenInclude(t => t!.UnitValues)
- .ThenInclude(t => t.Value)
- .Include(t => t.Template)
- .ThenInclude(a => a!.Job)
- .ThenInclude(t => t!.Group)
- .ThenInclude(g => g.GroupType)
- .Include(t => t.Template)
- .ThenInclude(a => a!.Job)
- .ThenInclude(t => t!.Group)
- .ThenInclude(t => t!.EsppSchValues)
- .ThenInclude(t => t!.EsppSchTypeConfig)
- .ThenInclude(t => t!.EsppSchTypeSchedule)
- .Include(t => t.Template)
- .ThenInclude(t => t!.Job)
- .ThenInclude(t => t!.Group)
- .ThenInclude(t => t!.ScheduleExcludeType)
- .Include(t => t.Template)
- .ThenInclude(t => t!.Job)
- .ThenInclude(t => t!.Group)
- .ThenInclude(t => t.ScheduleExcludeTypeCalendar)
- .Include(t => t.Template)
- .ThenInclude(t => t!.Job)
- .ThenInclude(t => t!.Tnk)
- .Include(t => t.Template)
- .ThenInclude(t => t!.UnitsInTemplate);
+ var historyIniciator = new HistoryInitiator
+ {
- //выбираем только записи с созданными шаблонами (у которых статус 20 или 30), а только потом у них ищем расписания
- var createdTemplates = robotConfigurationService.Get()
- .Where(t => t.RobotCode == (int)RobotsEnum.TemplateOrder && (t.TaskStatusCode == (int)TaskStatusEnum.Ok))
- .Select(t => t.TemplateId);
- query = query.Where(t => t.RobotCode == (int)RobotsEnum.ScheduleOrder && createdTemplates.Contains(t.TemplateId));
- // query = query.Where(t => t.RobotCode == (int)RobotsEnum.ScheduleOrder && t.TemplateId==Guid.Parse("7cb7c3be-506d-40e0-a63f-4554edb52459"));
- break;
+ };
+ var scheduleTask = await robotTaskService.GetScheduleTaskAsync(
+ taskStatusCode,
+ requestQuery.SetInProgressStatus ?? false,
+ historyIniciator.InitiatorIp,
+ requestQuery.RobotId,
+ historyIniciator
+ );
+ var scheduleResponse = mapper.Map(scheduleTask);
+
+ return Ok(new Response(scheduleResponse, true));
default:
- break;
+ throw new AppValidationException("Некорректное значение robotCode");
}
-
-
- // сортируем по NextRun, чтобы те у которых дата след срабатывания ближе к текущей, выполнились скорее
- query = query.OrderBy(t => t.Template!.NextRun).ThenBy(t => t.Template!.IsActiveSchedule).ThenBy(t => t.Template.IsActiveTemplate);
-
- RobotConfiguration? task = null;
-
- //ищем задание в ожидании, если нашли, выбираем его
- task = await query.FirstOrDefaultAsync(t => t.RobotStatusCode == (int)RobotStatusEnum.Wait);
-
- if (task == null)
- {
- //ищем задания в работе, которые можно перезапустить
- //Поиск по `RobotStatusCode` = 22.
- //Далее проверяется `LastStatusUpdated`, что время последнего смены статуса не превышает допустимого(берется из настроек, поле `RobotWaitTime`)
- //и что текущая попытка не больше разрешенной(берется из настроек, поле `RobotAttemptsNumber`) - если это так, берется эта запись.
-
- var endDate = DateTimeOffset.UtcNow.Add(-settingsFromDb.RobotWaitTime);
- task = await query
- .FirstOrDefaultAsync(t =>
- t.RobotStatusCode == (int)RobotStatusEnum.InProgress
- && t.AttemptsNumber < settingsFromDb.RobotAttemptsNumber
- && t.LastRobotStatusUpdated < endDate
- );
- }
-
- if (task == null)
- return NotFound();
-
- if (requestQuery?.SetInProgressStatus == true)
- {
- var resultSetStatus = await SetInProgressStatusAsync(task.Id);
- if (resultSetStatus == false)
- {
- logger.LogError($"Ошибка при установке статуса {RobotStatusEnum.InProgress.ToString()} для задания RobotConfigutationId {task.Id} (при выдаче задания роботу)");
- return BadRequest(new Response(false, new List { new ErrorModel { Message = "Ошибка при выдаче задания." } }));
- }
- }
-
- switch (robotCode)
- {
- case RobotsEnum.TemplateOrder:
- { //RobotTaskTemplateResponse
- var robotTaskTemplateResponse = mapper.Map(task);
-
- robotTaskTemplateResponse.FullDescription = NormalizeLineEndingsToCrlf(await shortcodesService.ApplyShortcodesAsync(robotTaskTemplateResponse.FullDescription, task.Template!));
- robotTaskTemplateResponse.ShortDescription = await shortcodesService.ApplyShortcodesAsync(robotTaskTemplateResponse.ShortDescription, task.Template!);
- robotTaskTemplateResponse.Solution = NormalizeLineEndingsToCrlf(await shortcodesService.ApplyShortcodesAsync(robotTaskTemplateResponse.Solution, task.Template!));
- robotTaskTemplateResponse.TnkName = await shortcodesService.ApplyShortcodesAsync(robotTaskTemplateResponse.TnkName, task.Template!);
- robotTaskTemplateResponse.WorkName = await shortcodesService.ApplyShortcodesAsync(robotTaskTemplateResponse.WorkName, task.Template!);
- robotTaskTemplateResponse.WorkGroup = await shortcodesService.ApplyShortcodesAsync(robotTaskTemplateResponse.WorkGroup, task.Template!);
- robotTaskTemplateResponse.ResponseArea = await shortcodesService.ApplyShortcodesAsync(robotTaskTemplateResponse.ResponseArea, task.Template!);
-
- return Ok(new Response(robotTaskTemplateResponse, true));
- }
- case RobotsEnum.ScheduleOrder:
- { // если был запрос на расписание, проверяем у него nextRun, lastRun, обновляем их
- var resultUpdateNextRun = await UpdateNextRunAsync(task);
- if (!resultUpdateNextRun)
- {
- logger.LogError("Ошибка при расчете NextRun для templateId: {templateId}", task.TemplateId);
- return BadRequest(new Response(false, new List { new ErrorModel { Message = "Ошибка при расчете NextRun" } }));
- }
-
- //RobotTaskScheduleResponse
- var robotTaskScheduleResponse = mapper.Map(task);
-
- robotTaskScheduleResponse.Timezone = settingsFromDb.EsppScheduleTimezone;
-
- robotTaskScheduleResponse.WorkGroup = await shortcodesService.ApplyShortcodesAsync(robotTaskScheduleResponse.WorkGroup, task.Template!);
- robotTaskScheduleResponse.ResponseArea = await shortcodesService.ApplyShortcodesAsync(robotTaskScheduleResponse.ResponseArea, task.Template!);
-
- //var nextRunWithRobotTz = nextRunService.GetNextRunWithTimezoneEsppAndResponseArea(task.Template!.NextRun, task.Template!.Job?.Group?.IsResponseAreaTimezone, robotTaskScheduleResponse.ResponseArea);
- //nextRun в часовой зоне УЗ Робота ЕСПП
- var nextRunWithRobotTz = task.Template!.NextRun.Add(nextRunService.GetEsppAccountOffset());
-
- //на всякий случай еще раз проверяем, что дата не устарела и отправляем задание
- if (nextRunWithRobotTz < DateTimeOffset.UtcNow)
- {
- logger.LogError("Ошибка при расчете NextRun для templateId: {templateId}, итоговое значение для робота, меньше чем сейчас {nextRunWithRobotTz}<{now}",
- task.TemplateId, nextRunWithRobotTz, DateTimeOffset.UtcNow);
- return BadRequest(new Response(false, new List { new ErrorModel { Message = "Ошибка при расчете NextRun" } }));
- }
-
- robotTaskScheduleResponse.NextStart = EsppScheduleHelpers.GetNextRun(nextRunWithRobotTz);
- robotTaskScheduleResponse.GenerationTime = EsppScheduleHelpers.GetGenerationTime(nextRunWithRobotTz);
-
- return Ok(new Response(robotTaskScheduleResponse, true));
- }
- default:
- break;
- }
-
- return BadRequest();
}
- ///
- /// Обоновить NextRun если он устарел
- ///
- ///
- ///
- private async Task UpdateNextRunAsync(RobotConfiguration task)
- {
- var template = task.Template!;
+ #region Old
- //var nextRun = await esppScheduleTransformService.GetNextDateAsync(template.Job!.GroupId, template!.Job!.Group!.ReferenceDate);
- var nextRun = await nextRunService.GetNextRunForTemplateAsync(template.Id, false);
-
- if (!nextRun.HasValue)
- {
- logger.LogError("При обновлении nextRun для шаблона {templateId}, расчитанный nextRun=null, ошибка в расчетах.", template.Id);
- return false;
- }
-
- if (nextRun.Value < DateTimeOffset.UtcNow)
- {
- logger.LogError("При обновлении nextRun для шаблона {templateId}, расчитанный nextRun
+ // /// Получить задание для робота по коду робота и по статусу задания
+ // ///
+ // ///
+ // ///
+ // ///
+ // [HttpGet(ApiRoutes.RobotTask.GetByRobotAndStatusTask)]
+ // public async Task GetByRobotAndStatusTask([FromRoute] RobotsEnum robotCode, [FromRoute] TaskStatusEnum taskStatusCode, [FromQuery] RobotTaskQuery requestQuery)
+ // {
+ // //Ищем все задания с превышенным кол-вом попыток и с просроченным временем и ставим им статус ошибки
+ // await robotConfigurationService.MarkExpiredTasksAsFailedAsync(settingsFromDb.RobotAttemptsNumber, settingsFromDb.RobotWaitTime);
- ///
- /// Устанавливаем статус "Робот взял в работу", пишем в историю работы роботов инф о начале работ
- ///
- ///
- ///
- private async Task SetInProgressStatusAsync(Guid taskId)
- {
- var config = await robotConfigurationService.GetAsync(taskId);
+ // var query = robotConfigurationService.Get()
+ // .AsSingleQuery()
+ // .Where(t => t.RobotCode == (int)robotCode && t.TaskStatusCode == (int)taskStatusCode);
- //изменение статуса робота
- robotConfigurationService.ChangeRobotStatus(RobotStatusEnum.InProgress, config!);
+ // switch (robotCode)
+ // {
+ // case RobotsEnum.TemplateOrder:
+ // // шаблоны
+ // query = query
+ // .Include(t => t.Template)
+ // .ThenInclude(t => t!.Unit)
+ // .ThenInclude(t => t!.UnitValues)
+ // .ThenInclude(t => t.Field)
+ // .Include(t => t.Template)
+ // .ThenInclude(t => t!.Unit)
+ // .ThenInclude(t => t!.UnitValues)
+ // .ThenInclude(t => t.Value)
+ // .Include(t => t.Template)
+ // .ThenInclude(a => a!.Job)
+ // .ThenInclude(t => t!.Group)
+ // .ThenInclude(g => g.GroupType)
+ // .Include(t => t.Template)
+ // .ThenInclude(w => w!.Job)
+ // .ThenInclude(t => t!.Tnk)
+ // .ThenInclude(s => s!.Subprocess)
+ // .ThenInclude(p => p!.Process);
- if (!await robotConfigurationService.CommitAsync())
- return false;
+ // query = query
+ // .Include(t => t.Template)
+ // .ThenInclude(t => t!.UnitsInTemplate);
- //записываем в лог робота
- var history = new RobotHistory
- {
- Id = Guid.NewGuid(),
- HistoryLevel = (int)RobotHistoryLevelEnum.Start,
- TaskStatusCode = config.TaskStatusCode,
- RobotConfigurationId = config.Id,
- RobotIp = clientService.GetClientIp()?.ToString()
- };
+ // break;
- if (!await robotHistoryService.CreateAsync(history) || !await robotHistoryService.CommitAsync())
- return false;
+ // case RobotsEnum.ScheduleOrder:
+ // //расписание
+ // query = query
+ // .Include(t => t.Template)
+ // .ThenInclude(t => t!.Unit)
+ // .ThenInclude(t => t!.UnitValues)
+ // .ThenInclude(t => t.Field)
+ // .Include(t => t.Template)
+ // .ThenInclude(t => t!.Unit)
+ // .ThenInclude(t => t!.UnitValues)
+ // .ThenInclude(t => t.Value)
+ // .Include(t => t.Template)
+ // .ThenInclude(a => a!.Job)
+ // .ThenInclude(t => t!.Group)
+ // .ThenInclude(g => g.GroupType)
+ // .Include(t => t.Template)
+ // .ThenInclude(a => a!.Job)
+ // .ThenInclude(t => t!.Group)
+ // .ThenInclude(t => t!.EsppSchValues)
+ // .ThenInclude(t => t!.EsppSchTypeConfig)
+ // .ThenInclude(t => t!.EsppSchTypeSchedule)
+ // .Include(t => t.Template)
+ // .ThenInclude(t => t!.Job)
+ // .ThenInclude(t => t!.Group)
+ // .ThenInclude(t => t!.ScheduleExcludeType)
+ // .Include(t => t.Template)
+ // .ThenInclude(t => t!.Job)
+ // .ThenInclude(t => t!.Group)
+ // .ThenInclude(t => t.ScheduleExcludeTypeCalendar)
+ // .Include(t => t.Template)
+ // .ThenInclude(t => t!.Job)
+ // .ThenInclude(t => t!.Tnk)
+ // .Include(t => t.Template)
+ // .ThenInclude(t => t!.UnitsInTemplate);
- return true;
- }
+ // //выбираем только записи с созданными шаблонами (у которых статус 20 или 30), а только потом у них ищем расписания
+ // var createdTemplates = robotConfigurationService.Get()
+ // .Where(t => t.RobotCode == (int)RobotsEnum.TemplateOrder && (t.TaskStatusCode == (int)TaskStatusEnum.Ok))
+ // .Select(t => t.TemplateId);
+ // query = query.Where(t => t.RobotCode == (int)RobotsEnum.ScheduleOrder && createdTemplates.Contains(t.TemplateId));
+ // // query = query.Where(t => t.RobotCode == (int)RobotsEnum.ScheduleOrder && t.TemplateId==Guid.Parse("7cb7c3be-506d-40e0-a63f-4554edb52459"));
+ // break;
+
+ // default:
+ // break;
+ // }
- ///
- /// Приводит переносы строк в тексте к формату CRLF (\r\n)
- ///
- /// Исходный текст
- /// Текст с унифицированными переносами строк
- private string NormalizeLineEndingsToCrlf(string? text)
- {
- if (string.IsNullOrEmpty(text))
- return string.Empty;
+ // // сортируем по NextRun, чтобы те у которых дата след срабатывания ближе к текущей, выполнились скорее
+ // query = query.OrderBy(t => t.Template!.NextRun).ThenBy(t => t.Template!.IsActiveSchedule).ThenBy(t => t.Template.IsActiveTemplate);
- // Заменяем любые варианты переносов (\r\n, \r, \n) на единый \r\n
- return System.Text.RegularExpressions.Regex.Replace(text, @"\r\n|\r|\n", "\r\n");
- }
+ // RobotConfiguration? task = null;
+
+ // //ищем задание в ожидании, если нашли, выбираем его
+ // task = await query.FirstOrDefaultAsync(t => t.RobotStatusCode == (int)RobotStatusEnum.Wait);
+
+ // if (task == null)
+ // {
+ // //ищем задания в работе, которые можно перезапустить
+ // //Поиск по `RobotStatusCode` = 22.
+ // //Далее проверяется `LastStatusUpdated`, что время последнего смены статуса не превышает допустимого(берется из настроек, поле `RobotWaitTime`)
+ // //и что текущая попытка не больше разрешенной(берется из настроек, поле `RobotAttemptsNumber`) - если это так, берется эта запись.
+
+ // var endDate = DateTimeOffset.UtcNow.Add(-settingsFromDb.RobotWaitTime);
+ // task = await query
+ // .FirstOrDefaultAsync(t =>
+ // t.RobotStatusCode == (int)RobotStatusEnum.InProgress
+ // && t.AttemptsNumber < settingsFromDb.RobotAttemptsNumber
+ // && t.LastRobotStatusUpdated < endDate
+ // );
+ // }
+
+ // if (task == null)
+ // return NotFound();
+
+ // if (requestQuery?.SetInProgressStatus == true)
+ // {
+ // var resultSetStatus = await SetInProgressStatusAsync(task.Id);
+ // if (resultSetStatus == false)
+ // {
+ // logger.LogError($"Ошибка при установке статуса {RobotStatusEnum.InProgress.ToString()} для задания RobotConfigutationId {task.Id} (при выдаче задания роботу)");
+ // return BadRequest(new Response(false, new List { new ErrorModel { Message = "Ошибка при выдаче задания." } }));
+ // }
+ // }
+
+ // switch (robotCode)
+ // {
+ // case RobotsEnum.TemplateOrder:
+ // { //RobotTaskTemplateResponse
+ // var robotTaskTemplateResponse = mapper.Map(task);
+
+ // robotTaskTemplateResponse.FullDescription = NormalizeLineEndingsToCrlf(await shortcodesService.ApplyShortcodesAsync(robotTaskTemplateResponse.FullDescription, task.Template!));
+ // robotTaskTemplateResponse.ShortDescription = await shortcodesService.ApplyShortcodesAsync(robotTaskTemplateResponse.ShortDescription, task.Template!);
+ // robotTaskTemplateResponse.Solution = NormalizeLineEndingsToCrlf(await shortcodesService.ApplyShortcodesAsync(robotTaskTemplateResponse.Solution, task.Template!));
+ // robotTaskTemplateResponse.TnkName = await shortcodesService.ApplyShortcodesAsync(robotTaskTemplateResponse.TnkName, task.Template!);
+ // robotTaskTemplateResponse.WorkName = await shortcodesService.ApplyShortcodesAsync(robotTaskTemplateResponse.WorkName, task.Template!);
+ // robotTaskTemplateResponse.WorkGroup = await shortcodesService.ApplyShortcodesAsync(robotTaskTemplateResponse.WorkGroup, task.Template!);
+ // robotTaskTemplateResponse.ResponseArea = await shortcodesService.ApplyShortcodesAsync(robotTaskTemplateResponse.ResponseArea, task.Template!);
+
+ // return Ok(new Response(robotTaskTemplateResponse, true));
+ // }
+ // case RobotsEnum.ScheduleOrder:
+ // { // если был запрос на расписание, проверяем у него nextRun, lastRun, обновляем их
+ // var resultUpdateNextRun = await UpdateNextRunAsync(task);
+ // if (!resultUpdateNextRun)
+ // {
+ // logger.LogError("Ошибка при расчете NextRun для templateId: {templateId}", task.TemplateId);
+ // return BadRequest(new Response(false, new List { new ErrorModel { Message = "Ошибка при расчете NextRun" } }));
+ // }
+
+ // //RobotTaskScheduleResponse
+ // var robotTaskScheduleResponse = mapper.Map(task);
+
+ // robotTaskScheduleResponse.Timezone = settingsFromDb.EsppScheduleTimezone;
+
+ // robotTaskScheduleResponse.WorkGroup = await shortcodesService.ApplyShortcodesAsync(robotTaskScheduleResponse.WorkGroup, task.Template!);
+ // robotTaskScheduleResponse.ResponseArea = await shortcodesService.ApplyShortcodesAsync(robotTaskScheduleResponse.ResponseArea, task.Template!);
+
+ // //var nextRunWithRobotTz = nextRunService.GetNextRunWithTimezoneEsppAndResponseArea(task.Template!.NextRun, task.Template!.Job?.Group?.IsResponseAreaTimezone, robotTaskScheduleResponse.ResponseArea);
+ // //nextRun в часовой зоне УЗ Робота ЕСПП
+ // var nextRunWithRobotTz = task.Template!.NextRun.Add(nextRunService.GetEsppAccountOffset());
+
+ // //на всякий случай еще раз проверяем, что дата не устарела и отправляем задание
+ // if (nextRunWithRobotTz < DateTimeOffset.UtcNow)
+ // {
+ // logger.LogError("Ошибка при расчете NextRun для templateId: {templateId}, итоговое значение для робота, меньше чем сейчас {nextRunWithRobotTz}<{now}",
+ // task.TemplateId, nextRunWithRobotTz, DateTimeOffset.UtcNow);
+ // return BadRequest(new Response(false, new List { new ErrorModel { Message = "Ошибка при расчете NextRun" } }));
+ // }
+
+ // robotTaskScheduleResponse.NextStart = EsppScheduleHelpers.GetNextRun(nextRunWithRobotTz);
+ // robotTaskScheduleResponse.GenerationTime = EsppScheduleHelpers.GetGenerationTime(nextRunWithRobotTz);
+
+ // return Ok(new Response(robotTaskScheduleResponse, true));
+ // }
+ // default:
+ // break;
+ // }
+
+ // return BadRequest();
+ // }
+
+
+ // ///
+ // /// Обоновить NextRun если он устарел
+ // ///
+ // ///
+ // ///
+ // private async Task UpdateNextRunAsync(RobotConfiguration task)
+ // {
+ // var template = task.Template!;
+
+ // //var nextRun = await esppScheduleTransformService.GetNextDateAsync(template.Job!.GroupId, template!.Job!.Group!.ReferenceDate);
+ // var nextRun = await nextRunService.GetNextRunForTemplateAsync(template.Id, false);
+
+ // if (!nextRun.HasValue)
+ // {
+ // logger.LogError("При обновлении nextRun для шаблона {templateId}, расчитанный nextRun=null, ошибка в расчетах.", template.Id);
+ // return false;
+ // }
+
+ // if (nextRun.Value < DateTimeOffset.UtcNow)
+ // {
+ // logger.LogError("При обновлении nextRun для шаблона {templateId}, расчитанный nextRun
+ // /// Устанавливаем статус "Робот взял в работу", пишем в историю работы роботов инф о начале работ
+ // ///
+ // ///
+ // ///
+ // private async Task SetInProgressStatusAsync(Guid taskId)
+ // {
+ // var config = await robotConfigurationService.GetAsync(taskId);
+
+ // //изменение статуса робота
+ // robotConfigurationService.ChangeRobotStatus(RobotStatusEnum.InProgress, config!);
+
+ // if (!await robotConfigurationService.CommitAsync())
+ // return false;
+
+ // //записываем в лог робота
+ // var history = new RobotHistory
+ // {
+ // Id = Guid.NewGuid(),
+ // HistoryLevel = (int)RobotHistoryLevelEnum.Start,
+ // TaskStatusCode = config.TaskStatusCode,
+ // RobotConfigurationId = config.Id,
+ // RobotIp = clientService.GetClientIp()?.ToString()
+ // };
+
+ // if (!await robotHistoryService.CreateAsync(history) || !await robotHistoryService.CommitAsync())
+ // return false;
+
+ // return true;
+ // }
+
+
+ // ///
+ // /// Приводит переносы строк в тексте к формату CRLF (\r\n)
+ // ///
+ // /// Исходный текст
+ // /// Текст с унифицированными переносами строк
+ // private string NormalizeLineEndingsToCrlf(string? text)
+ // {
+ // if (string.IsNullOrEmpty(text))
+ // return string.Empty;
+
+ // // Заменяем любые варианты переносов (\r\n, \r, \n) на единый \r\n
+ // return System.Text.RegularExpressions.Regex.Replace(text, @"\r\n|\r|\n", "\r\n");
+ // }
+
+ #endregion
}
}
diff --git a/PARR.API/Infrastructure/Middleware/GlobalExceptionHandler.cs b/PARR.API/Infrastructure/Middleware/GlobalExceptionHandler.cs
index da6ce47e..1b202511 100644
--- a/PARR.API/Infrastructure/Middleware/GlobalExceptionHandler.cs
+++ b/PARR.API/Infrastructure/Middleware/GlobalExceptionHandler.cs
@@ -32,6 +32,7 @@ namespace PARR.API.Infrastructure.Middleware
AlreadyExistsException => StatusCodes.Status409Conflict,
UnauthorizedException => StatusCodes.Status401Unauthorized,
ForbiddenException => StatusCodes.Status403Forbidden,
+ NextRunException => StatusCodes.Status422UnprocessableEntity,
//todo: ---------- другие ошибки ----------
_ => StatusCodes.Status500InternalServerError
};
diff --git a/PARR.API/MappingProfiles/DomainToResponseProfile.cs b/PARR.API/MappingProfiles/DomainToResponseProfile.cs
index aa478cf1..5735968c 100644
--- a/PARR.API/MappingProfiles/DomainToResponseProfile.cs
+++ b/PARR.API/MappingProfiles/DomainToResponseProfile.cs
@@ -5,6 +5,7 @@ using PARR.API.Contracts.V1.Responses.Statistics;
using PARR.API.MappingProfiles.Resolvers;
using PARR.Core.Repositories.Interfaces.Schedule;
using PARR.Domain.DTOs.Matching;
+using PARR.Domain.DTOs.RobotTask;
using PARR.Domain.DTOs.Shortcode;
using PARR.Domain.DTOs.TaskDTO;
using PARR.Domain.DTOs.Workload;
@@ -180,64 +181,73 @@ namespace PARR.API.MappingProfiles
#region RobotConfiguration
// --- RobotConfiguration ---
- CreateMap()
- .Include()
- .Include()
- .ForMember(d => d.TaskId, o => o.MapFrom(s => s.Id));
- CreateMap()
- .ForMember(d => d.IsActive, o => o.MapFrom(s => s.Template!.IsActiveTemplate))
- .ForMember(d => d.ClosingCode, o => o.MapFrom())
- .ForMember(d => d.FullDescription, o => o.MapFrom(s => s.Template!.Job!.Group!.FullDescription))
- .ForMember(d => d.ShortDescription, o => o.MapFrom(s => s.Template!.Job!.Group!.ShortDescription))
- .ForMember(d => d.Solution, o => o.MapFrom(s => s.Template!.Job!.Group!.Solution))
- //.ForMember(d => d.ResponseArea, o => o.MapFrom(s => s.Template!.Host!.ResponseArea!.Name))
- //ЗО берем у группы а не у хоста
- .ForMember(d => d.ResponseArea, o => o.MapFrom(s => s.Template!.Unit!.BaseFields!.ResponseArea))
- .ForMember(d => d.TemplateDuration, o => o.MapFrom(s => s.Template!.Job!.Group!.TemplateDuration))
- .ForMember(d => d.Initiator, o => o.MapFrom())
- .ForMember(d => d.Category, o => o.MapFrom())
- .ForMember(d => d.WorkGroup, o => o.MapFrom(s => s.Template!.Job!.WorkGroupMask))
- .ForMember(d => d.Ek, o => o.MapFrom(s => s.Template!.Unit!.Name))
- .ForMember(d => d.Name, o => o.MapFrom(s => s.Template!.Name))
- .ForMember(d => d.ProcessName, o => o.MapFrom(s => s.Template!.Job!.Tnk!.Subprocess!.Process!.Name))
- .ForMember(d => d.ProcessEsppId, o => o.MapFrom(s => s.Template!.Job!.Tnk!.Subprocess!.Process!.EsppId))
- .ForMember(d => d.SubprocessName, o => o.MapFrom(s => s.Template!.Job!.Tnk!.Subprocess!.Name))
- .ForMember(d => d.SubprocessEsppId, o => o.MapFrom(s => s.Template!.Job!.Tnk!.Subprocess!.EsppId))
- .ForMember(d => d.TnkName, o => o.MapFrom(s => s.Template!.Job!.Tnk!.Name))
- .ForMember(d => d.TnkEsppId, o => o.MapFrom(s =>
- s.Template!.Job!.Tnk!.EsppId.HasValue
- ? s.Template!.Job!.Tnk!.EsppId.Value.ToString()
- : string.Empty
- ))
- .ForMember(d => d.WorkName, o => o.MapFrom(s => s.Template!.Job!.WorkName))
- //.ForMember(d => d.WorkEsppId, o => o.MapFrom(s => s.Template!.Job!.EsppId))
- .ForMember(d => d.ScheduleEsppId, o => o.MapFrom(s => s.Template!.ScheduleEsppId));
+ CreateMap();
+ CreateMap();
- CreateMap()
- .ForMember(d => d.EsppId, o => o.MapFrom(s => s.Template!.ScheduleEsppId))
- .ForMember(d => d.ScheduleName, o => o.MapFrom(s => s.Template!.Name))
- .ForMember(d => d.IsActive, o => o.MapFrom(s => s.Template!.IsActiveSchedule))
- .ForMember(d => d.ResponseArea, o => o.MapFrom(s => s.Template!.Unit!.BaseFields!.ResponseArea))
- .ForMember(d => d.TemplateName, o => o.MapFrom(s => s.Template!.Name))
- .ForMember(d => d.TemplateId, o => o.MapFrom(s => s.Template!.Id))
- .ForMember(d => d.WorkGroup, o => o.MapFrom(s => s.Template!.Job!.WorkGroupMask))
- //.ForMember(d => d.Exclude, o => o.MapFrom())
- .ForMember(d => d.Exclude, o => o.MapFrom(s => s.Template!.Job!.Group!.ScheduleExcludeType!.EsppName))
- //.ForMember(d => d.ExcludeCalendar, o => o.MapFrom())
- .ForMember(d => d.ExcludeCalendar, o => o.MapFrom(s => s.Template!.Job!.Group!.ScheduleExcludeTypeCalendar != null ? s.Template!.Job!.Group!.ScheduleExcludeTypeCalendar.EsppName : null))
- //.ForMember(d => d.Timezone, o => o.MapFrom())
- .ForMember(d => d.RepeatRange, o => o.MapFrom())
- //todo: GenerationTime
- //.ForMember(d => d.GenerationTime, o => o.MapFrom(s => EsppScheduleHelpers.GetGenerationTime(s.Template!.NextRun)))
- //.ForMember(d => d.GenerationTime, o => o.MapFrom())
- //.ForMember(d => d.NextStart, o => o.MapFrom(s => EsppScheduleHelpers.GetNextRun(s.Template!.NextRun)))
- //.ForMember(d => d.NextStart, o => o.MapFrom())
- .ForMember(d => d.ScheduleType, o => o.MapFrom(s =>
- s.Template!.Job!.Group!.EsppSchValues!.First()!.EsppSchTypeConfig!.EsppSchTypeSchedule!.Description))
- .ForMember(d => d.ScheduleTypeCode, o => o.MapFrom(s =>
- s.Template!.Job!.Group!.EsppSchValues!.First()!.EsppSchTypeConfig!.EsppSchTypeSchedule!.Id))
- .ForMember(d => d.Schedule, o => o.MapFrom());
+ CreateMap();
+
+ #region old robot task
+ //CreateMap()
+ // .Include()
+ // .Include()
+ // .ForMember(d => d.TaskId, o => o.MapFrom(s => s.Id));
+
+ //CreateMap()
+ // .ForMember(d => d.IsActive, o => o.MapFrom(s => s.Template!.IsActiveTemplate))
+ // .ForMember(d => d.ClosingCode, o => o.MapFrom())
+ // .ForMember(d => d.FullDescription, o => o.MapFrom(s => s.Template!.Job!.Group!.FullDescription))
+ // .ForMember(d => d.ShortDescription, o => o.MapFrom(s => s.Template!.Job!.Group!.ShortDescription))
+ // .ForMember(d => d.Solution, o => o.MapFrom(s => s.Template!.Job!.Group!.Solution))
+ // //.ForMember(d => d.ResponseArea, o => o.MapFrom(s => s.Template!.Host!.ResponseArea!.Name))
+ // //ЗО берем у группы а не у хоста
+ // .ForMember(d => d.ResponseArea, o => o.MapFrom(s => s.Template!.Unit!.BaseFields!.ResponseArea))
+ // .ForMember(d => d.TemplateDuration, o => o.MapFrom(s => s.Template!.Job!.Group!.TemplateDuration))
+ // .ForMember(d => d.Initiator, o => o.MapFrom())
+ // .ForMember(d => d.Category, o => o.MapFrom())
+ // .ForMember(d => d.WorkGroup, o => o.MapFrom(s => s.Template!.Job!.WorkGroupMask))
+ // .ForMember(d => d.Ek, o => o.MapFrom(s => s.Template!.Unit!.Name))
+ // .ForMember(d => d.Name, o => o.MapFrom(s => s.Template!.Name))
+ // .ForMember(d => d.ProcessName, o => o.MapFrom(s => s.Template!.Job!.Tnk!.Subprocess!.Process!.Name))
+ // .ForMember(d => d.ProcessEsppId, o => o.MapFrom(s => s.Template!.Job!.Tnk!.Subprocess!.Process!.EsppId))
+ // .ForMember(d => d.SubprocessName, o => o.MapFrom(s => s.Template!.Job!.Tnk!.Subprocess!.Name))
+ // .ForMember(d => d.SubprocessEsppId, o => o.MapFrom(s => s.Template!.Job!.Tnk!.Subprocess!.EsppId))
+ // .ForMember(d => d.TnkName, o => o.MapFrom(s => s.Template!.Job!.Tnk!.Name))
+ // .ForMember(d => d.TnkEsppId, o => o.MapFrom(s =>
+ // s.Template!.Job!.Tnk!.EsppId.HasValue
+ // ? s.Template!.Job!.Tnk!.EsppId.Value.ToString()
+ // : string.Empty
+ // ))
+ // .ForMember(d => d.WorkName, o => o.MapFrom(s => s.Template!.Job!.WorkName))
+ // //.ForMember(d => d.WorkEsppId, o => o.MapFrom(s => s.Template!.Job!.EsppId))
+ // .ForMember(d => d.ScheduleEsppId, o => o.MapFrom(s => s.Template!.ScheduleEsppId));
+
+ //CreateMap()
+ // .ForMember(d => d.EsppId, o => o.MapFrom(s => s.Template!.ScheduleEsppId))
+ // .ForMember(d => d.ScheduleName, o => o.MapFrom(s => s.Template!.Name))
+ // .ForMember(d => d.IsActive, o => o.MapFrom(s => s.Template!.IsActiveSchedule))
+ // .ForMember(d => d.ResponseArea, o => o.MapFrom(s => s.Template!.Unit!.BaseFields!.ResponseArea))
+ // .ForMember(d => d.TemplateName, o => o.MapFrom(s => s.Template!.Name))
+ // .ForMember(d => d.TemplateId, o => o.MapFrom(s => s.Template!.Id))
+ // .ForMember(d => d.WorkGroup, o => o.MapFrom(s => s.Template!.Job!.WorkGroupMask))
+ // //.ForMember(d => d.Exclude, o => o.MapFrom())
+ // .ForMember(d => d.Exclude, o => o.MapFrom(s => s.Template!.Job!.Group!.ScheduleExcludeType!.EsppName))
+ // //.ForMember(d => d.ExcludeCalendar, o => o.MapFrom())
+ // .ForMember(d => d.ExcludeCalendar, o => o.MapFrom(s => s.Template!.Job!.Group!.ScheduleExcludeTypeCalendar != null ? s.Template!.Job!.Group!.ScheduleExcludeTypeCalendar.EsppName : null))
+ // //.ForMember(d => d.Timezone, o => o.MapFrom())
+ // .ForMember(d => d.RepeatRange, o => o.MapFrom())
+ // //todo: GenerationTime
+ // //.ForMember(d => d.GenerationTime, o => o.MapFrom(s => EsppScheduleHelpers.GetGenerationTime(s.Template!.NextRun)))
+ // //.ForMember(d => d.GenerationTime, o => o.MapFrom())
+ // //.ForMember(d => d.NextStart, o => o.MapFrom(s => EsppScheduleHelpers.GetNextRun(s.Template!.NextRun)))
+ // //.ForMember(d => d.NextStart, o => o.MapFrom())
+ // .ForMember(d => d.ScheduleType, o => o.MapFrom(s =>
+ // s.Template!.Job!.Group!.EsppSchValues!.First()!.EsppSchTypeConfig!.EsppSchTypeSchedule!.Description))
+ // .ForMember(d => d.ScheduleTypeCode, o => o.MapFrom(s =>
+ // s.Template!.Job!.Group!.EsppSchValues!.First()!.EsppSchTypeConfig!.EsppSchTypeSchedule!.Id))
+ // .ForMember(d => d.Schedule, o => o.MapFrom());
+
+ #endregion
CreateMap();
@@ -460,7 +470,7 @@ namespace PARR.API.MappingProfiles
//CreateMap();
CreateMap();
-
+
// ---
CreateMap();
diff --git a/PARR.Core/DependencyInjection.cs b/PARR.Core/DependencyInjection.cs
index 7a6fd864..8de67dc6 100644
--- a/PARR.Core/DependencyInjection.cs
+++ b/PARR.Core/DependencyInjection.cs
@@ -7,6 +7,8 @@ using PARR.Core.Common.Interfaces;
using PARR.Core.Services.MatchingStatusService;
using PARR.Core.Services.NextRunServices;
using PARR.Core.Services.NextRunServices.Subservices;
+using PARR.Core.Services.RobotTask.Implementations;
+using PARR.Core.Services.RobotTask.Interfaces;
using PARR.Core.Services.Shortcodes;
using PARR.Core.Services.Shortcodes.Handlers;
using PARR.Core.Services.TaskServices.Handlers;
@@ -78,8 +80,6 @@ namespace PARR.Core
#endregion
- #region Services
-
#region Shortсodes
services.AddScoped();
@@ -97,10 +97,13 @@ namespace PARR.Core
services.AddScoped();
#endregion
+ #region Services
+
services.AddTransient();
- //services.AddScoped();
+ services.AddScoped();
+ //services.AddScoped();
#endregion
diff --git a/PARR.Core/Infrastructure/Mapping/RobotTask/Resolvers/RobotTaskScheduleSchResolver.cs b/PARR.Core/Infrastructure/Mapping/RobotTask/Resolvers/RobotTaskScheduleSchResolver.cs
new file mode 100644
index 00000000..5b40620c
--- /dev/null
+++ b/PARR.Core/Infrastructure/Mapping/RobotTask/Resolvers/RobotTaskScheduleSchResolver.cs
@@ -0,0 +1,46 @@
+using AutoMapper;
+using Microsoft.Extensions.Logging;
+using PARR.Core.Repositories.Interfaces.Schedule;
+using PARR.Domain.DTOs.RobotTask;
+using PARR.Domain.Entities;
+
+namespace PARR.Core.Infrastructure.Mapping.RobotTask.Resolvers
+{
+ public class RobotTaskScheduleSchResolver : IValueResolver?>
+ {
+ private readonly IEsppSchTypeConfigRepository esppConfigRepository;
+ private readonly ILogger logger;
+
+ public RobotTaskScheduleSchResolver(
+ IEsppSchTypeConfigRepository esppConfigRepository,
+ ILogger logger
+ )
+ {
+ this.esppConfigRepository = esppConfigRepository;
+ this.logger = logger;
+ }
+
+ public List? Resolve(RobotConfiguration source, RobotTaskSchedule destination, List? destMember, ResolutionContext context)
+ {
+ var jobGroupId = source.Template!.Job!.GroupId;
+
+ var schedule = esppConfigRepository.GetEsppScheduleDto(jobGroupId);
+
+ if (schedule == null)
+ {
+ logger.LogError("RobotTaskScheduleSchResolver: Не смог замапить расписание для робота, так как оно null. JobGroupId: {JobGroupId}", jobGroupId);
+ return null;
+ }
+
+ var response = schedule.Values.Select(t => new RobotTaskScheduleSch
+ {
+ Order = t.Order,
+ Type = t.Type.Name,
+ TypeCode = t.Type.Id,
+ Value = t.Value.Value
+ }).OrderBy(t => t.Order).ToList();
+
+ return response;
+ }
+ }
+}
diff --git a/PARR.Core/Infrastructure/Mapping/RobotTask/RobotTaskMappingProfile.cs b/PARR.Core/Infrastructure/Mapping/RobotTask/RobotTaskMappingProfile.cs
new file mode 100644
index 00000000..0bd37e14
--- /dev/null
+++ b/PARR.Core/Infrastructure/Mapping/RobotTask/RobotTaskMappingProfile.cs
@@ -0,0 +1,70 @@
+using AutoMapper;
+using PARR.Core.Infrastructure.Mapping.RobotTask.Resolvers;
+using PARR.Domain.DTOs.RobotTask;
+using PARR.Domain.Entities;
+using PARR.Domain.Settings;
+
+namespace PARR.Core.Infrastructure.Mapping.RobotTask
+{
+ ///
+ /// Маппинг RobotTask
+ ///
+ internal class RobotTaskMappingProfile : Profile
+ {
+ public RobotTaskMappingProfile()
+ {
+
+ CreateMap()
+ .Include()
+ .Include()
+ .ForMember(d => d.TaskId, o => o.MapFrom(s => s.Id));
+
+ // Задание роботам, шаблоны
+ CreateMap()
+ .ForMember(d => d.IsActive, o => o.MapFrom(s => s.Template!.IsActiveTemplate))
+ //.ForMember(d => d.ClosingCode, o => o.MapFrom())
+ .ForMember(d => d.FullDescription, o => o.MapFrom(s => s.Template!.Job!.Group!.FullDescription))
+ .ForMember(d => d.ShortDescription, o => o.MapFrom(s => s.Template!.Job!.Group!.ShortDescription))
+ .ForMember(d => d.Solution, o => o.MapFrom(s => s.Template!.Job!.Group!.Solution))
+ //ЗО берем у группы а не у хоста
+ .ForMember(d => d.ResponseArea, o => o.MapFrom(s => s.Template!.Unit!.BaseFields!.ResponseArea))
+ .ForMember(d => d.TemplateDuration, o => o.MapFrom(s => s.Template!.Job!.Group!.TemplateDuration))
+ //.ForMember(d => d.Initiator, o => o.MapFrom())
+ //.ForMember(d => d.Category, o => o.MapFrom())
+ .ForMember(d => d.WorkGroup, o => o.MapFrom(s => s.Template!.Job!.WorkGroupMask))
+ .ForMember(d => d.Ek, o => o.MapFrom(s => s.Template!.Unit!.Name))
+ .ForMember(d => d.Name, o => o.MapFrom(s => s.Template!.Name))
+ .ForMember(d => d.ProcessName, o => o.MapFrom(s => s.Template!.Job!.Tnk!.Subprocess!.Process!.Name))
+ .ForMember(d => d.ProcessEsppId, o => o.MapFrom(s => s.Template!.Job!.Tnk!.Subprocess!.Process!.EsppId))
+ .ForMember(d => d.SubprocessName, o => o.MapFrom(s => s.Template!.Job!.Tnk!.Subprocess!.Name))
+ .ForMember(d => d.SubprocessEsppId, o => o.MapFrom(s => s.Template!.Job!.Tnk!.Subprocess!.EsppId))
+ .ForMember(d => d.TnkName, o => o.MapFrom(s => s.Template!.Job!.Tnk!.Name))
+ .ForMember(d => d.TnkEsppId, o => o.MapFrom(s =>
+ s.Template!.Job!.Tnk!.EsppId.HasValue
+ ? s.Template!.Job!.Tnk!.EsppId.Value.ToString()
+ : string.Empty
+ ))
+ .ForMember(d => d.WorkName, o => o.MapFrom(s => s.Template!.Job!.WorkName))
+ .ForMember(d => d.ScheduleEsppId, o => o.MapFrom(s => s.Template!.ScheduleEsppId));
+
+
+ // Задание роботам, расписания
+ CreateMap()
+ .ForMember(d => d.EsppId, o => o.MapFrom(s => s.Template!.ScheduleEsppId))
+ .ForMember(d => d.ScheduleName, o => o.MapFrom(s => s.Template!.Name))
+ .ForMember(d => d.IsActive, o => o.MapFrom(s => s.Template!.IsActiveSchedule))
+ .ForMember(d => d.ResponseArea, o => o.MapFrom(s => s.Template!.Unit!.BaseFields!.ResponseArea))
+ .ForMember(d => d.TemplateName, o => o.MapFrom(s => s.Template!.Name))
+ .ForMember(d => d.TemplateId, o => o.MapFrom(s => s.Template!.Id))
+ .ForMember(d => d.WorkGroup, o => o.MapFrom(s => s.Template!.Job!.WorkGroupMask))
+ .ForMember(d => d.Exclude, o => o.MapFrom(s => s.Template!.Job!.Group!.ScheduleExcludeType!.EsppName))
+ .ForMember(d => d.ExcludeCalendar, o => o.MapFrom(s => s.Template!.Job!.Group!.ScheduleExcludeTypeCalendar != null ? s.Template!.Job!.Group!.ScheduleExcludeTypeCalendar.EsppName : null))
+ //.ForMember(d => d.RepeatRange, o => o.MapFrom())
+ .ForMember(d => d.ScheduleType, o => o.MapFrom(s =>
+ s.Template!.Job!.Group!.EsppSchValues!.First()!.EsppSchTypeConfig!.EsppSchTypeSchedule!.Description))
+ .ForMember(d => d.ScheduleTypeCode, o => o.MapFrom(s =>
+ s.Template!.Job!.Group!.EsppSchValues!.First()!.EsppSchTypeConfig!.EsppSchTypeSchedule!.Id))
+ .ForMember(d => d.Schedule, o => o.MapFrom());
+ }
+ }
+}
diff --git a/PARR.Core/Repositories/Interfaces/IRobotConfigurationRepository.cs b/PARR.Core/Repositories/Interfaces/IRobotConfigurationRepository.cs
index 06b019c8..5bc2d65a 100644
--- a/PARR.Core/Repositories/Interfaces/IRobotConfigurationRepository.cs
+++ b/PARR.Core/Repositories/Interfaces/IRobotConfigurationRepository.cs
@@ -26,7 +26,7 @@ namespace PARR.Core.Repositories.Interfaces
///
///
///
- Task FindUnfulfilledTaskAndSetRobotErrorStatusAsync(int robotAttemptsNumber, TimeSpan robotWaitTime);
+ Task MarkExpiredTasksAsFailedAsync(int robotAttemptsNumber, TimeSpan robotWaitTime);
///
/// Получить конфигурацию из шаблона по RobotCode. У шаблона обязательно должен быть Include таблицы RobotConfiguration
@@ -42,5 +42,12 @@ namespace PARR.Core.Repositories.Interfaces
///
/// true - если изменил статус, false - нельзя изменить статус
bool SetUpdateTaskStatusIfAllow(RobotConfiguration configuration);
+
+ ///
+ /// Атомарно установить статус задачи "В работе" если текущий статус "В ожидании".
+ ///
+ ///
+ ///
+ Task SetInProgressStatusAsync(Guid id);
}
}
diff --git a/PARR.Core/Services/RobotTask/Implementations/RobotTaskService.cs b/PARR.Core/Services/RobotTask/Implementations/RobotTaskService.cs
new file mode 100644
index 00000000..3d41f915
--- /dev/null
+++ b/PARR.Core/Services/RobotTask/Implementations/RobotTaskService.cs
@@ -0,0 +1,387 @@
+using AutoMapper;
+using Microsoft.EntityFrameworkCore;
+using Microsoft.Extensions.Logging;
+using PARR.BLL.Helpers;
+using PARR.Core.Repositories.Interfaces;
+using PARR.Core.Services.NextRunServices;
+using PARR.Core.Services.RobotTask.Interfaces;
+using PARR.Core.Services.Shortcodes;
+using PARR.Domain.DTOs.RobotTask;
+using PARR.Domain.Entities;
+using PARR.Domain.Entities.Base.History;
+using PARR.Domain.Enums;
+using PARR.Domain.Exceptions;
+using PARR.Domain.Settings;
+
+namespace PARR.Core.Services.RobotTask.Implementations
+{
+ internal class RobotTaskService : IRobotTaskService
+ {
+ ///
+ /// Количество заданий которые рассматриваем для взятия в работу.
+ ///
+ private readonly int TakeTasks = 10;
+
+ private readonly ILogger logger;
+ private readonly IRobotConfigurationRepository robotConfigurationRepository;
+ private readonly SettingsFromDb settingsFromDb;
+ private readonly IRobotHistoryRepository robotHistoryRepository;
+ private readonly IMapper mapper;
+ private readonly IShortcodesService shortcodesService;
+ private readonly INextRunService nextRunService;
+
+ public RobotTaskService(
+ ILogger logger,
+ IRobotConfigurationRepository robotConfigurationRepository,
+ SettingsFromDb settingsFromDb,
+ IRobotHistoryRepository robotHistoryRepository,
+ IMapper mapper,
+ IShortcodesService shortcodesService,
+ INextRunService nextRunService
+ )
+ {
+ this.logger = logger;
+ this.robotConfigurationRepository = robotConfigurationRepository;
+ this.settingsFromDb = settingsFromDb;
+ this.robotHistoryRepository = robotHistoryRepository;
+ this.mapper = mapper;
+ this.shortcodesService = shortcodesService;
+ this.nextRunService = nextRunService;
+ }
+
+
+ public async Task GetTemplateTaskAsync(TaskStatusEnum taskStatusCode, bool acquireTask, string? robotIp, string? robotId)
+ {
+ var templateTask = await GetTaskAsync(RobotsEnum.TemplateOrder, taskStatusCode, acquireTask, robotIp, robotId);
+
+ var task = mapper.Map(templateTask);
+
+ task = task with { FullDescription = NormalizeLineEndingsToCrlf(await shortcodesService.ApplyShortcodesAsync(task.FullDescription, templateTask.Template!)) };
+ task = task with { ShortDescription = await shortcodesService.ApplyShortcodesAsync(task.ShortDescription, templateTask.Template!) };
+ task = task with { Solution = NormalizeLineEndingsToCrlf(await shortcodesService.ApplyShortcodesAsync(task.Solution, templateTask.Template!)) };
+ task = task with { TnkName = await shortcodesService.ApplyShortcodesAsync(task.TnkName, templateTask.Template!) };
+ task = task with { WorkName = await shortcodesService.ApplyShortcodesAsync(task.WorkName, templateTask.Template!) };
+ task = task with { WorkGroup = await shortcodesService.ApplyShortcodesAsync(task.WorkGroup, templateTask.Template!) };
+ task = task with { ResponseArea = await shortcodesService.ApplyShortcodesAsync(task.ResponseArea, templateTask.Template!) };
+
+ task = task with { ClosingCode = settingsFromDb.ClosingCode };
+ task = task with { Initiator = settingsFromDb.Initiator };
+ task = task with { Category = settingsFromDb.Category };
+
+ return task;
+ }
+
+
+ public async Task GetScheduleTaskAsync(TaskStatusEnum taskStatusCode, bool acquireTask, string? robotIp, string? robotId, IHistoryInitiator historyInitiator)
+ {
+ var scheduleTask = await GetTaskAsync(RobotsEnum.ScheduleOrder, taskStatusCode, acquireTask, robotIp, robotId);
+
+ // Проверяем nextRun, lastRun, обновляем их
+
+ var resultUpdateNextRun = await UpdateNextRunAsync(scheduleTask, historyInitiator);
+ if (!resultUpdateNextRun)
+ {
+ logger.LogError("Ошибка при расчете NextRun для templateId: {templateId}", scheduleTask.TemplateId);
+ throw new NextRunException($"Ошибка при расчете NextRun для templateId: {scheduleTask.TemplateId}");
+ }
+
+ var task = mapper.Map(scheduleTask);
+
+ task = task with { Timezone = settingsFromDb.EsppScheduleTimezone };
+ task = task with { WorkGroup = await shortcodesService.ApplyShortcodesAsync(task.WorkGroup, scheduleTask.Template!) };
+ task = task with { ResponseArea = await shortcodesService.ApplyShortcodesAsync(task.ResponseArea, scheduleTask.Template!) };
+
+ //nextRun в часовой зоне УЗ Робота ЕСПП
+ var nextRunWithRobotTz = scheduleTask.Template!.NextRun.Add(nextRunService.GetEsppAccountOffset());
+ //на всякий случай еще раз проверяем, что дата не устарела и отправляем задание
+ if (nextRunWithRobotTz < DateTimeOffset.UtcNow)
+ {
+ logger.LogError("Ошибка при расчете NextRun для templateId: {templateId}, итоговое значение для робота, меньше чем сейчас {nextRunWithRobotTz}<{now}",
+ task.TemplateId, nextRunWithRobotTz, DateTimeOffset.UtcNow);
+ throw new NextRunException($"Ошибка при расчете NextRun для templateId: {scheduleTask.TemplateId}");
+ }
+
+ task = task with { NextStart = EsppScheduleHelpers.GetNextRun(nextRunWithRobotTz) };
+ task = task with { GenerationTime = EsppScheduleHelpers.GetGenerationTime(nextRunWithRobotTz) };
+
+ task = task with { RepeatRange = settingsFromDb.ScheduleRepeatRange };
+ task = task with { };
+
+ return task;
+ }
+
+
+ ///
+ /// Получить задачу для робота.
+ /// Метод может генерировать исключения.
+ ///
+ ///
+ ///
+ /// Взять в работу
+ ///
+ ///
+ ///
+ private async Task GetTaskAsync(RobotsEnum robotCode, TaskStatusEnum taskStatusCode, bool acquireTask, string? robotIp, string? robotId)
+ {
+ // 1. Ищем все задания с превышенным кол-вом попыток и просроченным временем, ставим им статус ошибки
+ await robotConfigurationRepository.MarkExpiredTasksAsFailedAsync(settingsFromDb.RobotAttemptsNumber, settingsFromDb.RobotWaitTime);
+
+
+ // 2. Ищем доступные задания
+ var availableTasks = await GetAvailableTasksAsync(robotCode, taskStatusCode);
+
+ if (availableTasks.Count == 0)
+ throw new NotFoundException("Нет доступных заданий для робота");
+
+ Guid? acquiredTaskId = null;
+
+ if (acquireTask)
+ {
+ // Берем задание в работу, устанавливаем ей статус "В работе"
+ acquiredTaskId = await AcquireTaskAsync(availableTasks, robotIp, robotId);
+
+ if (acquiredTaskId == null)
+ throw new Exception($"Не удалось взять ни одну из доступных задач ({availableTasks.Count}) в работу");
+ }
+ else
+ {
+ // Берем первую задачу из списка доступных
+ acquiredTaskId = availableTasks.First();
+ logger.LogDebug("Задача не требует захвата, взята первая из доступных: {TaskId}", acquiredTaskId);
+ }
+
+
+ //3. Получаем задачу со всеми нужными инклудами в зависимости от типа робота
+ var task = await GetTaskWithAllDataAsync(acquiredTaskId.Value, robotCode);
+
+ return task;
+ }
+
+
+ ///
+ /// Получить список возможных заданий для взятия в работу.
+ /// Кол-во заданй ограничено переменной TakeTasks
+ ///
+ ///
+ ///
+ ///
+ private async Task> GetAvailableTasksAsync(RobotsEnum robotCode, TaskStatusEnum taskStatusCode)
+ {
+ var query = robotConfigurationRepository.Get()
+ .AsNoTracking()
+ .Where(t => t.RobotCode == (int)robotCode && t.TaskStatusCode == (int)taskStatusCode);
+
+ // Если это задание для робота расписаний
+ if (robotCode == RobotsEnum.ScheduleOrder)
+ {
+ // Выбираем только записи с созданными шаблонами (у которых статус 30), а только потом ищем у них расписания
+ var createdTemplates = robotConfigurationRepository.Get()
+ .Where(t => t.RobotCode == (int)RobotsEnum.TemplateOrder && t.TaskStatusCode == (int)TaskStatusEnum.Ok)
+ .Select(t => t.TemplateId);
+
+ query = query.Where(t => createdTemplates.Contains(t.TemplateId));
+ }
+
+ // Сортируем по nextRun, чтобы те, у кого nextRun ближе к текущей, выполнились скорее
+ query = query.OrderBy(t => t.Template!.NextRun).ThenBy(t => t.Template!.IsActiveSchedule).ThenBy(t => t.Template!.IsActiveTemplate);
+
+ // Кандидаты заданий
+ var tasks = new List();
+
+ // Ещем первые 10 заданий в статусе ОЖИДАНИЕ
+ tasks = await query.Where(t => t.RobotStatusCode == (int)RobotStatusEnum.Wait).Take(TakeTasks).Select(t => t.Id).ToListAsync();
+
+ logger.LogDebug("Найдено заданий в статусе 'Ожидание' {Count} шт. Робот '{Robot}'", tasks.Count, robotCode.ToString());
+
+ if (tasks.Count == 0)
+ {
+ // Ищем задания в статусе В РАБОТЕ, которые можно перезапустить
+ // Поиск по `RobotStatusCode` = 22.
+ // Далее проверяется `LastStatusUpdated`, что время последнего смены статуса не превышает допустимого(берется из настроек, поле `RobotWaitTime`)
+ // и что текущая попытка не больше разрешенной(берется из настроек, поле `RobotAttemptsNumber`) - если это так, берется эта запись.
+
+ var endDate = DateTimeOffset.UtcNow.Add(-settingsFromDb.RobotWaitTime);
+
+ tasks = await query.Where(t => t.RobotStatusCode == (int)RobotStatusEnum.InProgress
+ && t.AttemptsNumber < settingsFromDb.RobotAttemptsNumber
+ && t.LastRobotStatusUpdated < endDate)
+ .Take(TakeTasks)
+ .Select(t => t.Id)
+ .ToListAsync();
+
+ logger.LogDebug("Найдено заданий в статусе 'В работе' {Count} шт. Робот '{Robot}'", tasks.Count, robotCode.ToString());
+ }
+
+ return tasks;
+ }
+
+
+ ///
+ /// Взять задачу в работу
+ ///
+ ///
+ ///
+ private async Task AcquireTaskAsync(List tasks, string? robotIp, string? robotId)
+ {
+ foreach (var taskId in tasks)
+ {
+ var isChangedStatus = await robotConfigurationRepository.SetInProgressStatusAsync(taskId);
+ if (isChangedStatus)
+ {
+ logger.LogDebug("Захвачена задача {TaskId}", taskId);
+
+ var task = await robotConfigurationRepository.Get()
+ .AsNoTracking()
+ .FirstAsync(t => t.Id == taskId);
+
+ // пишем в историю робота
+ var history = new RobotHistory
+ {
+ Id = Guid.NewGuid(),
+ HistoryLevel = (int)RobotHistoryLevelEnum.Start,
+ TaskStatusCode = task.TaskStatusCode,
+ RobotConfigurationId = taskId,
+ RobotIp = robotIp,
+ RobotId = robotId
+ };
+
+ if (!await robotHistoryRepository.CreateAsync(history) || !await robotHistoryRepository.CommitAsync())
+ throw new DbErrorException("Ошибка при добавлении истории робота, при взятии задания в работу.");
+
+ return taskId;
+ }
+ else
+ {
+ logger.LogDebug("Не удалось захватить задачу {TaskId}", taskId);
+ }
+ }
+
+ logger.LogDebug("Не удалось захватить ни одну из доступных задач для робота");
+
+ return null;
+ }
+
+
+ ///
+ /// Получить задачу со всем необходимыми полями
+ ///
+ ///
+ ///
+ ///
+ private async Task GetTaskWithAllDataAsync(Guid taskId, RobotsEnum robotCode)
+ {
+ IQueryable query = robotConfigurationRepository.Get()
+ //.AsNoTracking() // нужно обязательно трекать, так как может измениться nextRun и его нужно будет сохранить
+ .AsSingleQuery()
+ // Общие инклуды для шаблонов и расписаний
+ // Units
+ .Include(t => t.Template)
+ .ThenInclude(t => t!.Unit)
+ .ThenInclude(t => t!.UnitValues)
+ .ThenInclude(t => t!.Field)
+ .Include(t => t.Template)
+ .ThenInclude(t => t!.Unit)
+ .ThenInclude(t => t!.UnitValues)
+ .ThenInclude(t => t!.Value)
+ .Include(t => t.Template)
+ .ThenInclude(t => t!.UnitsInTemplate)
+ // Группа с типом
+ .Include(t => t.Template)
+ .ThenInclude(t => t!.Job)
+ .ThenInclude(t => t!.Group)
+ .ThenInclude(t => t!.GroupType)
+ // ТНК
+ .Include(t => t.Template)
+ .ThenInclude(t => t!.Job)
+ .ThenInclude(t => t!.Tnk)
+ .ThenInclude(t => t!.Subprocess)
+ .ThenInclude(t => t!.Process);
+
+ if (robotCode == RobotsEnum.ScheduleOrder)
+ {
+ // Инклуды только для расписаний
+ query = query
+ // Расписание
+ .Include(t => t.Template)
+ .ThenInclude(t => t!.Job)
+ .ThenInclude(t => t!.Group)
+ .ThenInclude(t => t!.EsppSchValues)
+ .ThenInclude(t => t!.EsppSchTypeConfig)
+ .ThenInclude(t => t!.EsppSchTypeSchedule)
+ // Исключения по типу
+ .Include(t => t.Template)
+ .ThenInclude(t => t!.Job)
+ .ThenInclude(t => t!.Group)
+ .ThenInclude(t => t!.ScheduleExcludeType)
+ // Исключения по календарю
+ .Include(t => t.Template)
+ .ThenInclude(t => t!.Job)
+ .ThenInclude(t => t!.Group)
+ .ThenInclude(t => t!.ScheduleExcludeTypeCalendar);
+ }
+
+ return await query.FirstAsync(t => t.Id == taskId);
+ }
+
+
+ ///
+ /// Приводит переносы строк в тексте к формату CRLF (\r\n)
+ ///
+ /// Исходный текст
+ /// Текст с унифицированными переносами строк
+ private string NormalizeLineEndingsToCrlf(string? text)
+ {
+ if (string.IsNullOrEmpty(text))
+ return string.Empty;
+
+ // Заменяем любые варианты переносов (\r\n, \r, \n) на единый \r\n
+ return System.Text.RegularExpressions.Regex.Replace(text, @"\r\n|\r|\n", "\r\n");
+ }
+
+
+ ///
+ /// Обоновить NextRun если он устарел
+ ///
+ ///
+ ///
+ private async Task UpdateNextRunAsync(RobotConfiguration task, IHistoryInitiator historyInitiator)
+ {
+ var template = task.Template!;
+
+ //var nextRun = await esppScheduleTransformService.GetNextDateAsync(template.Job!.GroupId, template!.Job!.Group!.ReferenceDate);
+ var nextRun = await nextRunService.GetNextRunForTemplateAsync(template.Id, false);
+
+ if (!nextRun.HasValue)
+ {
+ logger.LogError("При обновлении nextRun для шаблона {templateId}, расчитанный nextRun=null, ошибка в расчетах.", template.Id);
+ return false;
+ }
+
+ if (nextRun.Value < DateTimeOffset.UtcNow)
+ {
+ logger.LogError("При обновлении nextRun для шаблона {templateId}, расчитанный nextRun
+ /// Управление заданиями роботам
+ ///
+ public interface IRobotTaskService
+ {
+
+ ///
+ /// Получить задание роботу - шаблоны.
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ Task GetTemplateTaskAsync(TaskStatusEnum taskStatusCode, bool acquireTask, string? robotIp, string? robotId);
+
+
+ ///
+ /// Получить задание роботу - расписания.
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ Task GetScheduleTaskAsync(TaskStatusEnum taskStatusCode, bool acquireTask, string? robotIp, string? robotId, IHistoryInitiator historyInitiator);
+ }
+}
diff --git a/PARR.DAL/Migrations/20260526013309_tblRobotHistoriesAddRobotId.Designer.cs b/PARR.DAL/Migrations/20260526013309_tblRobotHistoriesAddRobotId.Designer.cs
new file mode 100644
index 00000000..67017380
--- /dev/null
+++ b/PARR.DAL/Migrations/20260526013309_tblRobotHistoriesAddRobotId.Designer.cs
@@ -0,0 +1,3822 @@
+//
+using System;
+using Microsoft.EntityFrameworkCore;
+using Microsoft.EntityFrameworkCore.Infrastructure;
+using Microsoft.EntityFrameworkCore.Migrations;
+using Microsoft.EntityFrameworkCore.Storage.ValueConversion;
+using Npgsql.EntityFrameworkCore.PostgreSQL.Metadata;
+using PARR.DAL.Context;
+
+#nullable disable
+
+namespace PARR.DAL.Migrations
+{
+ [DbContext(typeof(DataContext))]
+ [Migration("20260526013309_tblRobotHistoriesAddRobotId")]
+ partial class tblRobotHistoriesAddRobotId
+ {
+ ///
+ protected override void BuildTargetModel(ModelBuilder modelBuilder)
+ {
+#pragma warning disable 612, 618
+ modelBuilder
+ .HasAnnotation("ProductVersion", "9.0.16")
+ .HasAnnotation("Relational:MaxIdentifierLength", 63);
+
+ NpgsqlModelBuilderExtensions.UseIdentityByDefaultColumns(modelBuilder);
+
+ modelBuilder.Entity("PARR.Domain.Entities.AgentHistory", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("uuid");
+
+ b.Property("DateCreated")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("HistoryLevelId")
+ .HasColumnType("integer");
+
+ b.Property("Message")
+ .HasColumnType("text");
+
+ b.Property("OrderId")
+ .HasColumnType("uuid");
+
+ b.Property("TemplateId")
+ .HasColumnType("uuid");
+
+ b.HasKey("Id");
+
+ b.HasIndex("HistoryLevelId");
+
+ b.HasIndex("OrderId");
+
+ b.HasIndex("TemplateId");
+
+ b.ToTable("AgentHistories");
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.AgentHistoryLevel", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("integer");
+
+ NpgsqlPropertyBuilderExtensions.UseIdentityByDefaultColumn(b.Property("Id"));
+
+ b.Property("Description")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("Name")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.HasKey("Id");
+
+ b.ToTable("AgentHistoryLevels");
+
+ b.HasData(
+ new
+ {
+ Id = 1,
+ Description = "Агент начал выполнять задание",
+ Name = "Start"
+ },
+ new
+ {
+ Id = 5,
+ Description = "Агент завершил выполнение задания",
+ Name = "End"
+ });
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.DistributionPeriod", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("uuid");
+
+ b.Property("Duration")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("Name")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("Type")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.HasKey("Id");
+
+ b.HasIndex("Type");
+
+ b.ToTable("DistributionPeriods", "schedule");
+
+ b.HasData(
+ new
+ {
+ Id = new Guid("9bd0bfa8-c316-480b-a001-e09ffe8c9340"),
+ Duration = "7",
+ Name = "Еженедельно",
+ Type = "Day"
+ },
+ new
+ {
+ Id = new Guid("3a7341a8-085c-461c-babc-6b78dd5d2c67"),
+ Duration = "30",
+ Name = "Ежемесячно",
+ Type = "Day"
+ },
+ new
+ {
+ Id = new Guid("0ad2dfdb-3833-46d9-979a-c408b7eadc6c"),
+ Duration = "90",
+ Name = "Каждые 90 дней",
+ Type = "Day"
+ },
+ new
+ {
+ Id = new Guid("31dd3947-8471-4f09-852c-a4f075f1ba7f"),
+ Duration = "182",
+ Name = "Каждые пол года",
+ Type = "Day"
+ });
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.DistributionPeriodType", b =>
+ {
+ b.Property("Type")
+ .HasColumnType("text");
+
+ b.Property("Description")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.HasKey("Type");
+
+ b.ToTable("DistributionPeriodTypes", "schedule");
+
+ b.HasData(
+ new
+ {
+ Type = "Day",
+ Description = "День"
+ },
+ new
+ {
+ Type = "Month",
+ Description = "Месяц"
+ },
+ new
+ {
+ Type = "Year",
+ Description = "Год"
+ });
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.Job.Job", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("uuid");
+
+ b.Property("DateCreated")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("DateModified")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("GroupId")
+ .HasColumnType("uuid");
+
+ b.Property("IsParentRelationships")
+ .HasColumnType("boolean");
+
+ b.Property("MaxValueRelationships")
+ .HasColumnType("integer");
+
+ b.Property("MinValueRelationships")
+ .HasColumnType("integer");
+
+ b.Property("Name")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("ResponseAreaMask")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("TemplateNameMask")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("TnkId")
+ .HasColumnType("uuid");
+
+ b.Property("WorkGroupMask")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("WorkName")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.HasKey("Id");
+
+ b.HasIndex("GroupId");
+
+ b.HasIndex("TnkId");
+
+ b.ToTable("Jobs", "job", t =>
+ {
+ t.HasComment("Таблица видов работ");
+ });
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.Job.JobAutoControl", b =>
+ {
+ b.Property("JobId")
+ .HasColumnType("uuid");
+
+ b.Property("InitUsedScheduleState")
+ .HasColumnType("boolean");
+
+ b.Property("InitUsedTemplateState")
+ .HasColumnType("boolean");
+
+ b.Property("IsEnable")
+ .HasColumnType("boolean");
+
+ b.HasKey("JobId");
+
+ b.ToTable("AutoControls", "job", t =>
+ {
+ t.HasComment("Таблица управления автоконтролем для работ");
+ });
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.Job.JobFieldFilter", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("uuid");
+
+ b.Property("DateCreated")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("DateModified")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("FieldId")
+ .HasColumnType("uuid");
+
+ b.Property("IsInverse")
+ .HasColumnType("boolean");
+
+ b.Property("UnitFilterId")
+ .HasColumnType("uuid");
+
+ b.Property("ValueMask")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.HasKey("Id");
+
+ b.HasIndex("FieldId");
+
+ b.HasIndex("UnitFilterId");
+
+ b.ToTable("FieldFilters", "job", t =>
+ {
+ t.HasComment("Таблица описания критериев выборки аттрибутов ЭК");
+ });
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.Job.JobGroup", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("uuid");
+
+ b.Property("AgentName")
+ .HasColumnType("text");
+
+ b.Property("AgentScript")
+ .HasColumnType("text");
+
+ b.Property("AgentTimeOutSec")
+ .HasColumnType("integer");
+
+ b.Property("DateCreated")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("DateModified")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("FullDescription")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("GroupName")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("GroupTypeId")
+ .HasColumnType("uuid");
+
+ b.Property("GroupingUnitFieldId")
+ .HasColumnType("uuid");
+
+ b.Property("IsAgent")
+ .HasColumnType("boolean");
+
+ b.Property("IsAutoDistributionEnabled")
+ .HasColumnType("boolean");
+
+ b.Property("IsGroupByResponsible")
+ .HasColumnType("boolean");
+
+ b.Property("IsResponseAreaTimezone")
+ .HasColumnType("boolean");
+
+ b.Property("ReferenceDate")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("ScheduleExcludeTypeCalendarId")
+ .HasColumnType("uuid");
+
+ b.Property("ScheduleExcludeTypeId")
+ .HasColumnType("uuid");
+
+ b.Property("ShortDescription")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("Solution")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("TemplateDuration")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("UserTimeZoneOffsetMinutes")
+ .HasColumnType("integer")
+ .HasComment("Смещение часового пояса пользователя в минутах относительно UTC на момент ReferenceDate");
+
+ b.HasKey("Id");
+
+ b.HasIndex("GroupTypeId");
+
+ b.HasIndex("GroupingUnitFieldId");
+
+ b.HasIndex("ScheduleExcludeTypeCalendarId");
+
+ b.HasIndex("ScheduleExcludeTypeId");
+
+ b.ToTable("Groups", "job", t =>
+ {
+ t.HasComment("Таблица описания групп работ, для реализации зонтиков");
+ });
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.Job.JobGroupDistributionConfig", b =>
+ {
+ b.Property("GroupId")
+ .HasColumnType("uuid");
+
+ b.Property("DistributionPeriodId")
+ .HasColumnType("uuid");
+
+ b.Property("IsExcludeWeekends")
+ .HasColumnType("boolean");
+
+ b.Property("IsGroupingByWorkGroup")
+ .HasColumnType("boolean");
+
+ b.HasKey("GroupId");
+
+ b.HasIndex("DistributionPeriodId");
+
+ b.ToTable("GroupDistributionConfigs", "job", t =>
+ {
+ t.HasComment("Настройки автораспределения для группы работ");
+ });
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.Job.JobGroupType", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("uuid");
+
+ b.Property("Code")
+ .HasColumnType("integer");
+
+ b.Property("DateCreated")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("Description")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("Name")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.HasKey("Id");
+
+ b.ToTable("GroupTypes", "job", t =>
+ {
+ t.HasComment("Таблица типов групп работ");
+ });
+
+ b.HasData(
+ new
+ {
+ Id = new Guid("4fa62e79-86bb-47c2-be1a-72a716a170fa"),
+ Code = 0,
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ Description = "Обычный",
+ Name = "Simple"
+ },
+ new
+ {
+ Id = new Guid("6ec58b1a-5c40-47b9-b036-4fa490e8d503"),
+ Code = 1,
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ Description = "Зонтик",
+ Name = "Umbrella"
+ },
+ new
+ {
+ Id = new Guid("318625e5-f833-436a-99df-2a382a1e71c7"),
+ Code = 2,
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ Description = "Сгруппированный",
+ Name = "Group"
+ });
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.Job.JobRelationshipFilter", b =>
+ {
+ b.Property("UnitFilterId")
+ .HasColumnType("uuid");
+
+ b.Property("FieldId")
+ .HasColumnType("uuid");
+
+ b.Property("IsFullMatch")
+ .HasColumnType("boolean");
+
+ b.Property("IsInverse")
+ .HasColumnType("boolean");
+
+ b.Property("IsParent")
+ .HasColumnType("boolean");
+
+ b.Property("ValueMask")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.HasKey("UnitFilterId", "FieldId");
+
+ b.HasIndex("FieldId");
+
+ b.ToTable("RelationshipFilters", "job", t =>
+ {
+ t.HasComment("Таблица фильтров связей ЭК");
+ });
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.Job.JobUnitFilter", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("uuid");
+
+ b.Property("DateCreated")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("DateModified")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("JobId")
+ .HasColumnType("uuid");
+
+ b.Property("UnitFilter")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.HasKey("Id");
+
+ b.HasIndex("JobId");
+
+ b.ToTable("UnitFilters", "job", t =>
+ {
+ t.HasComment("Таблица описания критериев выборки ЭК, описание полей в АСУ ЕСПП");
+ });
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.Job.UnitsInTemplate", b =>
+ {
+ b.Property("TemplateId")
+ .HasColumnType("uuid");
+
+ b.Property("UnitId")
+ .HasColumnType("uuid");
+
+ b.Property("UnitFieldValueId")
+ .HasColumnType("uuid");
+
+ b.Property("DateCreated")
+ .HasColumnType("timestamp with time zone");
+
+ b.HasKey("TemplateId", "UnitId", "UnitFieldValueId");
+
+ b.HasIndex("UnitFieldValueId");
+
+ b.HasIndex("UnitId");
+
+ b.ToTable("UnitsInTemplates", "job", t =>
+ {
+ t.HasComment("Таблица связи ЭК в шаблонах");
+ });
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.Order", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("uuid");
+
+ b.Property("DateCreated")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("DateModified")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("ExpirationDate")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("GenerateDate")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("NextStatusCode")
+ .HasColumnType("integer");
+
+ b.Property("Number")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("ShortName")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("StatusCode")
+ .HasColumnType("integer");
+
+ b.Property("TemplateId")
+ .HasColumnType("uuid");
+
+ b.Property("WorkGroup")
+ .HasColumnType("text");
+
+ b.HasKey("Id");
+
+ b.HasIndex("NextStatusCode");
+
+ b.HasIndex("Number")
+ .IsUnique();
+
+ b.HasIndex("StatusCode");
+
+ b.HasIndex("TemplateId");
+
+ b.ToTable("Orders");
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.OrderStatus", b =>
+ {
+ b.Property("Code")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("integer");
+
+ NpgsqlPropertyBuilderExtensions.UseIdentityByDefaultColumn(b.Property("Code"));
+
+ b.Property("Description")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("Name")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.HasKey("Code");
+
+ b.ToTable("OrderStatuses");
+
+ b.HasData(
+ new
+ {
+ Code = 1,
+ Description = "1-Направлен в группу",
+ Name = "New"
+ },
+ new
+ {
+ Code = 2,
+ Description = "2-В работе",
+ Name = "InWork"
+ },
+ new
+ {
+ Code = 3,
+ Description = "3-Приостановлен",
+ Name = "Stop"
+ },
+ new
+ {
+ Code = 4,
+ Description = "4-Выполнен",
+ Name = "Complete"
+ },
+ new
+ {
+ Code = 5,
+ Description = "5-Закрыт",
+ Name = "Closed"
+ });
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.ParrComponent", b =>
+ {
+ b.Property("Id")
+ .HasColumnType("integer");
+
+ b.Property("Description")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("Name")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.HasKey("Id");
+
+ b.HasIndex("Name")
+ .IsUnique();
+
+ b.ToTable("ParrComponents");
+
+ b.HasData(
+ new
+ {
+ Id = 0,
+ Description = "API",
+ Name = "Api"
+ },
+ new
+ {
+ Id = 1,
+ Description = "Загрузчик из АИХИТ",
+ Name = "AihitLoader"
+ },
+ new
+ {
+ Id = 2,
+ Description = "Синхронизатор АИХИТ",
+ Name = "AihitSyncer"
+ },
+ new
+ {
+ Id = 3,
+ Description = "Загрузчик нарядов из ЕСПП",
+ Name = "EsppOrderLoader"
+ },
+ new
+ {
+ Id = 4,
+ Description = "Управление нарядами ЕСПП",
+ Name = "EsppOrderManager"
+ },
+ new
+ {
+ Id = 5,
+ Description = "Синхронизатор расписаний",
+ Name = "EsppScheduleSync"
+ },
+ new
+ {
+ Id = 6,
+ Description = "Синхронизатор шаблонов",
+ Name = "EsppTemplateSync"
+ },
+ new
+ {
+ Id = 7,
+ Description = "Генератор шаблонов",
+ Name = "GeneratorTemplates"
+ },
+ new
+ {
+ Id = 8,
+ Description = "Авто-контроль РР",
+ Name = "JobAutoControl"
+ },
+ new
+ {
+ Id = 9,
+ Description = "Связывание нарядов ЕСПП с ПАРР (шаблонами, агентами)",
+ Name = "Master"
+ },
+ new
+ {
+ Id = 10,
+ Description = "Рассчет даты следующего срабатывания",
+ Name = "NextRun"
+ },
+ new
+ {
+ Id = 11,
+ Description = "Активатор шаблонов / расписаний",
+ Name = "TemplateActivator"
+ },
+ new
+ {
+ Id = 12,
+ Description = "Автораспределение РР",
+ Name = "TemplateDistributor"
+ },
+ new
+ {
+ Id = 13,
+ Description = "Генератор шаблонов",
+ Name = "TemplateTaskGenerator"
+ },
+ new
+ {
+ Id = 14,
+ Description = "Генератор кэша отчетов workload",
+ Name = "WorkloadBuilder"
+ });
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.Process", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("uuid");
+
+ b.Property("DateCreated")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("DateModified")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("EsppId")
+ .HasColumnType("integer");
+
+ b.Property("Name")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.HasKey("Id");
+
+ b.HasIndex("EsppId")
+ .IsUnique();
+
+ b.ToTable("Processes");
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.Robot", b =>
+ {
+ b.Property("Code")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("integer");
+
+ NpgsqlPropertyBuilderExtensions.UseIdentityByDefaultColumn(b.Property("Code"));
+
+ b.Property("Description")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("Name")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.HasKey("Code");
+
+ b.HasIndex("Name")
+ .IsUnique();
+
+ b.ToTable("Robots");
+
+ b.HasData(
+ new
+ {
+ Code = 1,
+ Description = "Робот по созданию/изменению шаблона наряда ЕСПП",
+ Name = "TemplateOrder"
+ },
+ new
+ {
+ Code = 2,
+ Description = "Робот по созданию/изменению расписания шаблона наряда в ЕСПП",
+ Name = "ScheduleOrder"
+ });
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.RobotConfiguration", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("uuid");
+
+ b.Property("AttemptsNumber")
+ .HasColumnType("integer");
+
+ b.Property("DateCreated")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("LastRobotStatusUpdated")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("RobotCode")
+ .HasColumnType("integer");
+
+ b.Property("RobotStatusCode")
+ .HasColumnType("integer");
+
+ b.Property("TaskStatusCode")
+ .HasColumnType("integer");
+
+ b.Property("TemplateId")
+ .HasColumnType("uuid");
+
+ b.HasKey("Id");
+
+ b.HasIndex("RobotCode");
+
+ b.HasIndex("RobotStatusCode");
+
+ b.HasIndex("TaskStatusCode");
+
+ b.HasIndex("TemplateId", "RobotCode")
+ .IsUnique();
+
+ b.HasIndex("TemplateId", "RobotStatusCode");
+
+ b.HasIndex("TemplateId", "TaskStatusCode");
+
+ b.ToTable("RobotConfigurations");
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.RobotHistory", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("uuid");
+
+ b.Property("DateCreated")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("EsppMessage")
+ .HasColumnType("text");
+
+ b.Property("HistoryLevel")
+ .HasColumnType("integer");
+
+ b.Property("RobotConfigurationId")
+ .HasColumnType("uuid");
+
+ b.Property("RobotId")
+ .HasColumnType("text")
+ .HasComment("Идентификатор робота. Форматы: H20-R1-T, H20-R1-S, H20-R1-ET, H20-R1-ES.");
+
+ b.Property("RobotIp")
+ .HasColumnType("text");
+
+ b.Property("RobotMessage")
+ .HasColumnType("text");
+
+ b.Property("TaskStatusCode")
+ .HasColumnType("integer");
+
+ b.HasKey("Id");
+
+ b.HasIndex("DateCreated");
+
+ b.HasIndex("TaskStatusCode");
+
+ b.HasIndex("HistoryLevel", "DateCreated")
+ .IsDescending(false, true);
+
+ b.HasIndex("RobotConfigurationId", "DateCreated");
+
+ b.ToTable("RobotHistories");
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.RobotHistoryLevel", b =>
+ {
+ b.Property("Level")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("integer");
+
+ NpgsqlPropertyBuilderExtensions.UseIdentityByDefaultColumn(b.Property("Level"));
+
+ b.Property("Description")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("Name")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.HasKey("Level");
+
+ b.ToTable("RobotHistoryLevels");
+
+ b.HasData(
+ new
+ {
+ Level = 1,
+ Description = "Робот начал работу ",
+ Name = "Start"
+ },
+ new
+ {
+ Level = 5,
+ Description = "Информация",
+ Name = "Information"
+ },
+ new
+ {
+ Level = 10,
+ Description = "Ошибка",
+ Name = "Error"
+ },
+ new
+ {
+ Level = 15,
+ Description = "Успешно завершил работу",
+ Name = "Complete"
+ });
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.RobotStatus", b =>
+ {
+ b.Property("Code")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("integer");
+
+ NpgsqlPropertyBuilderExtensions.UseIdentityByDefaultColumn(b.Property("Code"));
+
+ b.Property("Description")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("Name")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.HasKey("Code");
+
+ b.ToTable("RobotStatuses");
+
+ b.HasData(
+ new
+ {
+ Code = 11,
+ Description = "Ожидание, ждет пока робот возьмет в работу.",
+ Name = "Wait"
+ },
+ new
+ {
+ Code = 22,
+ Description = "Робот взял в работу.",
+ Name = "InProgress"
+ },
+ new
+ {
+ Code = 33,
+ Description = "Ошибка отработки роботом. Требует ручного вмешательства.",
+ Name = "Error"
+ },
+ new
+ {
+ Code = 44,
+ Description = "Робот успешно отработал.",
+ Name = "Complete"
+ });
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.Role", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("uuid");
+
+ b.Property("DateCreated")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("Description")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("Name")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.HasKey("Id");
+
+ b.ToTable("Roles");
+
+ b.HasData(
+ new
+ {
+ Id = new Guid("c8f2f144-e6c2-45d7-ba66-5e9bbd376376"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ Description = "Администратор",
+ Name = "administrator"
+ },
+ new
+ {
+ Id = new Guid("13bca225-7fa4-42fa-9d80-d2d46de261fe"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ Description = "Робот ЕСПП",
+ Name = "espp-robot"
+ });
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.Schedule.EsppSchType", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("integer");
+
+ NpgsqlPropertyBuilderExtensions.UseIdentityByDefaultColumn(b.Property("Id"));
+
+ b.Property("Description")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("Name")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.HasKey("Id");
+
+ b.ToTable("EsppSchTypes", "schedule");
+
+ b.HasData(
+ new
+ {
+ Id = 1,
+ Description = "Через интервал",
+ Name = "Interval"
+ },
+ new
+ {
+ Id = 2,
+ Description = "День недели: пнд, вт...",
+ Name = "DayOfWeek"
+ },
+ new
+ {
+ Id = 3,
+ Description = "Число месяца: 1,2,3,4",
+ Name = "DayOfMonth"
+ },
+ new
+ {
+ Id = 4,
+ Description = "Каждый: первый, второй, третий, четвертый, последний",
+ Name = "Order"
+ },
+ new
+ {
+ Id = 5,
+ Description = "Месяц: январь, февраль...",
+ Name = "Month"
+ },
+ new
+ {
+ Id = 6,
+ Description = "Месяц (родительный падеж): января, февраля...",
+ Name = "MonthGenitive"
+ });
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.Schedule.EsppSchTypeConfig", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("uuid");
+
+ b.Property("DateCreated")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("DateModified")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("Order")
+ .HasColumnType("integer");
+
+ b.Property("TypeId")
+ .HasColumnType("integer");
+
+ b.Property("TypeScheduleId")
+ .HasColumnType("integer");
+
+ b.HasKey("Id");
+
+ b.HasIndex("TypeId");
+
+ b.HasIndex("TypeScheduleId", "TypeId")
+ .IsUnique();
+
+ b.ToTable("EsppSchTypeConfigs", "schedule");
+
+ b.HasData(
+ new
+ {
+ Id = new Guid("d2693562-b3eb-41e9-97db-c6b5d2ef1bea"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ Order = 0,
+ TypeId = 1,
+ TypeScheduleId = 1
+ },
+ new
+ {
+ Id = new Guid("06b2e7aa-6927-4fbf-99fb-67c92a4fce8a"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ Order = 0,
+ TypeId = 2,
+ TypeScheduleId = 2
+ },
+ new
+ {
+ Id = new Guid("78079071-ff80-417e-9bb0-d928cec853e7"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ Order = 0,
+ TypeId = 3,
+ TypeScheduleId = 3
+ },
+ new
+ {
+ Id = new Guid("accb1d46-e1c1-4396-9182-4c0766155921"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ Order = 0,
+ TypeId = 4,
+ TypeScheduleId = 4
+ },
+ new
+ {
+ Id = new Guid("162ffe73-2428-4abe-8f83-235c2593664c"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ Order = 1,
+ TypeId = 2,
+ TypeScheduleId = 4
+ },
+ new
+ {
+ Id = new Guid("8470d1ef-165d-42fc-ab05-8203e4d263cf"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ Order = 0,
+ TypeId = 5,
+ TypeScheduleId = 5
+ },
+ new
+ {
+ Id = new Guid("006900b5-f65c-413e-bc67-09e6dae60b7c"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ Order = 1,
+ TypeId = 3,
+ TypeScheduleId = 5
+ },
+ new
+ {
+ Id = new Guid("85635bc8-f17a-46b8-9c15-8615761be3d9"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ Order = 0,
+ TypeId = 4,
+ TypeScheduleId = 6
+ },
+ new
+ {
+ Id = new Guid("439460c2-deca-4b54-80e7-2f20806696ec"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ Order = 1,
+ TypeId = 2,
+ TypeScheduleId = 6
+ },
+ new
+ {
+ Id = new Guid("5c63ad8c-e9b4-43fd-9d24-5c2eed80dadd"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ Order = 2,
+ TypeId = 6,
+ TypeScheduleId = 6
+ });
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.Schedule.EsppSchTypeSchedule", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("integer");
+
+ NpgsqlPropertyBuilderExtensions.UseIdentityByDefaultColumn(b.Property("Id"));
+
+ b.Property("Description")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("Name")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.HasKey("Id");
+
+ b.ToTable("EsppSchTypeSchedules", "schedule");
+
+ b.HasData(
+ new
+ {
+ Id = 1,
+ Description = "Регулярно",
+ Name = "Regularly"
+ },
+ new
+ {
+ Id = 2,
+ Description = "Еженедельно",
+ Name = "Weekly"
+ },
+ new
+ {
+ Id = 3,
+ Description = "Ежемесячно",
+ Name = "Monthly"
+ },
+ new
+ {
+ Id = 4,
+ Description = "Ежемесячно-2",
+ Name = "Monthly2"
+ },
+ new
+ {
+ Id = 5,
+ Description = "Ежегодно",
+ Name = "Annually"
+ },
+ new
+ {
+ Id = 6,
+ Description = "Ежегодно-2",
+ Name = "Annually2"
+ });
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.Schedule.EsppSchTypeValue", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("uuid");
+
+ b.Property("DateCreated")
+ .HasColumnType("timestamp with time zone");
+
+ b.Property("EsppExportValue")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.Property("Order")
+ .HasColumnType("integer");
+
+ b.Property("TypeId")
+ .HasColumnType("integer");
+
+ b.Property("Value")
+ .IsRequired()
+ .HasColumnType("text");
+
+ b.HasKey("Id");
+
+ b.HasIndex("TypeId");
+
+ b.ToTable("EsppSchTypeValues", "schedule");
+
+ b.HasData(
+ new
+ {
+ Id = new Guid("6e3b5dd2-b2f7-40bc-bace-15bfa6bbd4ff"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "01:00:00",
+ Order = 0,
+ TypeId = 1,
+ Value = "Каждый час"
+ },
+ new
+ {
+ Id = new Guid("4df04834-f14f-43d9-8984-334f080f4107"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "02:00:00",
+ Order = 1,
+ TypeId = 1,
+ Value = "Каждые 2 часа"
+ },
+ new
+ {
+ Id = new Guid("dab6e3f9-2385-4966-b77c-133ad233c592"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "03:00:00",
+ Order = 2,
+ TypeId = 1,
+ Value = "Каждые 3 часа"
+ },
+ new
+ {
+ Id = new Guid("035f485d-8451-47df-bfaa-ba4dd36cf146"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "04:00:00",
+ Order = 3,
+ TypeId = 1,
+ Value = "Каждые 4 часа"
+ },
+ new
+ {
+ Id = new Guid("d627daa7-3eed-4571-acae-ffbb3c5bedb9"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "06:00:00",
+ Order = 4,
+ TypeId = 1,
+ Value = "Каждые 6 часов"
+ },
+ new
+ {
+ Id = new Guid("ae0a0015-0f1e-4496-b71e-6244f7e321e7"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "12:00:00",
+ Order = 5,
+ TypeId = 1,
+ Value = "Каждые 12 часов"
+ },
+ new
+ {
+ Id = new Guid("8df097aa-9860-4a62-9675-a8eecd3f2ce7"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "1 00:00:00",
+ Order = 6,
+ TypeId = 1,
+ Value = "Ежедневно"
+ },
+ new
+ {
+ Id = new Guid("dee32e60-c1a1-4206-98bc-aa03deabfdf6"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "3 00:00:00",
+ Order = 7,
+ TypeId = 1,
+ Value = "Каждые 72 часа"
+ },
+ new
+ {
+ Id = new Guid("e0465fbf-e3a5-4486-9f53-5bb85c6feeca"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "4 00:00:00",
+ Order = 8,
+ TypeId = 1,
+ Value = "Каждые 96 часов"
+ },
+ new
+ {
+ Id = new Guid("4e3f73d1-a0f3-4dd1-bca9-68ada0dd5ce2"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "14 00:00:00",
+ Order = 9,
+ TypeId = 1,
+ Value = "Каждые 2 недели"
+ },
+ new
+ {
+ Id = new Guid("55833417-6a24-42f6-bcc2-5d032f883202"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "60 00:00:00",
+ Order = 10,
+ TypeId = 1,
+ Value = "Каждые 60 дней"
+ },
+ new
+ {
+ Id = new Guid("7fefa052-29db-4ce5-9c57-2fd9ff855f21"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "80 00:00:00",
+ Order = 11,
+ TypeId = 1,
+ Value = "Каждые 80 дней"
+ },
+ new
+ {
+ Id = new Guid("b0ca99f9-5ee0-45b3-bb80-948f82b1fcb1"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "90 00:00:00",
+ Order = 12,
+ TypeId = 1,
+ Value = "Каждые 90 дней"
+ },
+ new
+ {
+ Id = new Guid("086f7a37-9848-423a-a3cc-36dbb5ad43e3"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "182 00:00:00",
+ Order = 13,
+ TypeId = 1,
+ Value = "Каждые полгода"
+ },
+ new
+ {
+ Id = new Guid("f2da9e02-d619-4517-a598-374880a8c8e8"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "540 00:00:00",
+ Order = 14,
+ TypeId = 1,
+ Value = "Каждые 1,5 года"
+ },
+ new
+ {
+ Id = new Guid("f38d7d30-8923-4ea0-aa7c-5b251e19ab61"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "1095 00:00:00",
+ Order = 15,
+ TypeId = 1,
+ Value = "Каждые 3 года"
+ },
+ new
+ {
+ Id = new Guid("b7303461-9a30-43fa-8e55-305aa13f186f"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "1",
+ Order = 0,
+ TypeId = 2,
+ Value = "Понедельник"
+ },
+ new
+ {
+ Id = new Guid("e951135e-71f2-4262-9342-df4d5315ab6c"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "2",
+ Order = 1,
+ TypeId = 2,
+ Value = "Вторник"
+ },
+ new
+ {
+ Id = new Guid("c34d5375-70e7-4632-b3af-30e279a0621a"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "3",
+ Order = 2,
+ TypeId = 2,
+ Value = "Среда"
+ },
+ new
+ {
+ Id = new Guid("ec9540df-c2de-4bda-a063-34d02d4b6e03"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "4",
+ Order = 3,
+ TypeId = 2,
+ Value = "Четверг"
+ },
+ new
+ {
+ Id = new Guid("2ed85534-4684-4eb2-9ccb-e264d212c945"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "5",
+ Order = 4,
+ TypeId = 2,
+ Value = "Пятница"
+ },
+ new
+ {
+ Id = new Guid("a6804315-96ef-484e-82ee-c5795694468b"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "6",
+ Order = 5,
+ TypeId = 2,
+ Value = "Суббота"
+ },
+ new
+ {
+ Id = new Guid("eb71e699-937f-4894-9688-f7a7f95e5e58"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "7",
+ Order = 6,
+ TypeId = 2,
+ Value = "Воскресенье"
+ },
+ new
+ {
+ Id = new Guid("e86adbfb-3345-4e0c-aa3b-b4418f9cfe88"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "1",
+ Order = 0,
+ TypeId = 3,
+ Value = "1"
+ },
+ new
+ {
+ Id = new Guid("5b4d7ca6-31e7-475b-b7c8-13c6680c3dc3"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "2",
+ Order = 1,
+ TypeId = 3,
+ Value = "2"
+ },
+ new
+ {
+ Id = new Guid("0da03db0-9404-425d-bea1-5da0c9b60b59"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "3",
+ Order = 2,
+ TypeId = 3,
+ Value = "3"
+ },
+ new
+ {
+ Id = new Guid("199474c8-0a77-47e5-aab8-ba33c216cc9e"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "4",
+ Order = 3,
+ TypeId = 3,
+ Value = "4"
+ },
+ new
+ {
+ Id = new Guid("e6619da1-f7e8-45b9-bbd3-9c17bec2ccd3"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "5",
+ Order = 4,
+ TypeId = 3,
+ Value = "5"
+ },
+ new
+ {
+ Id = new Guid("a8708763-c838-49a5-95fe-bf4f73518d71"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "6",
+ Order = 5,
+ TypeId = 3,
+ Value = "6"
+ },
+ new
+ {
+ Id = new Guid("7ec056aa-820c-4900-96cb-4564d2ea6398"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "7",
+ Order = 6,
+ TypeId = 3,
+ Value = "7"
+ },
+ new
+ {
+ Id = new Guid("554d7d0c-91b1-4b81-b94d-1ee864192962"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "8",
+ Order = 7,
+ TypeId = 3,
+ Value = "8"
+ },
+ new
+ {
+ Id = new Guid("8b7847a4-23de-4199-8aad-3b5c0323b5a2"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "9",
+ Order = 8,
+ TypeId = 3,
+ Value = "9"
+ },
+ new
+ {
+ Id = new Guid("fb7f41ca-950b-4dc1-a0a6-bd9a221ab2ad"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "10",
+ Order = 9,
+ TypeId = 3,
+ Value = "10"
+ },
+ new
+ {
+ Id = new Guid("a28b530f-ea38-4a2c-a16b-0b7fa3770d3c"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "11",
+ Order = 10,
+ TypeId = 3,
+ Value = "11"
+ },
+ new
+ {
+ Id = new Guid("7a004a11-32e1-40ae-ab35-0d3dc3a69785"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "12",
+ Order = 11,
+ TypeId = 3,
+ Value = "12"
+ },
+ new
+ {
+ Id = new Guid("e0f2f4d1-4a5e-4997-8336-83c3c35f38df"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "13",
+ Order = 12,
+ TypeId = 3,
+ Value = "13"
+ },
+ new
+ {
+ Id = new Guid("9c5aaf48-88ec-4c67-b936-2be45550f8bf"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "14",
+ Order = 13,
+ TypeId = 3,
+ Value = "14"
+ },
+ new
+ {
+ Id = new Guid("8dbd680c-ce49-4d2e-8a1a-05619685e240"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "15",
+ Order = 14,
+ TypeId = 3,
+ Value = "15"
+ },
+ new
+ {
+ Id = new Guid("2f476f70-b1ef-419d-aad5-3911f1e3231f"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "16",
+ Order = 15,
+ TypeId = 3,
+ Value = "16"
+ },
+ new
+ {
+ Id = new Guid("2c635ce2-fc18-47be-b3e9-98c211abf312"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "17",
+ Order = 16,
+ TypeId = 3,
+ Value = "17"
+ },
+ new
+ {
+ Id = new Guid("f9d5b03b-624a-4f9f-8da3-1490ea5d2914"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "18",
+ Order = 17,
+ TypeId = 3,
+ Value = "18"
+ },
+ new
+ {
+ Id = new Guid("4f4b249c-db60-4582-86ed-75cfee4edd0c"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "19",
+ Order = 18,
+ TypeId = 3,
+ Value = "19"
+ },
+ new
+ {
+ Id = new Guid("220a1464-4d39-416c-b4b2-3093eb007298"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "20",
+ Order = 19,
+ TypeId = 3,
+ Value = "20"
+ },
+ new
+ {
+ Id = new Guid("c887ca60-b05d-4d3c-ad1f-223c879b1a6d"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "21",
+ Order = 20,
+ TypeId = 3,
+ Value = "21"
+ },
+ new
+ {
+ Id = new Guid("2905765d-63fb-41fe-a111-ee2f1d03d62e"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "22",
+ Order = 21,
+ TypeId = 3,
+ Value = "22"
+ },
+ new
+ {
+ Id = new Guid("dbbe704a-8d6d-40e7-bd30-6974035b1fab"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "23",
+ Order = 22,
+ TypeId = 3,
+ Value = "23"
+ },
+ new
+ {
+ Id = new Guid("cf7b9645-52ed-43a2-8267-267e0aed19b1"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "24",
+ Order = 23,
+ TypeId = 3,
+ Value = "24"
+ },
+ new
+ {
+ Id = new Guid("454788d6-d0ad-4c07-878c-da3fd3cd05e1"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "25",
+ Order = 24,
+ TypeId = 3,
+ Value = "25"
+ },
+ new
+ {
+ Id = new Guid("40d70d73-8582-4be6-a9e6-503b96ae3d49"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "26",
+ Order = 25,
+ TypeId = 3,
+ Value = "26"
+ },
+ new
+ {
+ Id = new Guid("8f6610dc-ef46-4842-a57e-18d7aaa75931"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "27",
+ Order = 26,
+ TypeId = 3,
+ Value = "27"
+ },
+ new
+ {
+ Id = new Guid("03858472-d4ce-47fd-9497-8051728766e4"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "28",
+ Order = 27,
+ TypeId = 3,
+ Value = "28"
+ },
+ new
+ {
+ Id = new Guid("b1018e07-e90e-42ee-b399-19f3d0c14dd6"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "29",
+ Order = 28,
+ TypeId = 3,
+ Value = "29"
+ },
+ new
+ {
+ Id = new Guid("a1669207-aa31-40fe-98d0-d941008d1655"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "30",
+ Order = 29,
+ TypeId = 3,
+ Value = "30"
+ },
+ new
+ {
+ Id = new Guid("0936aa99-73e0-43de-b6df-334c1228a226"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "31",
+ Order = 30,
+ TypeId = 3,
+ Value = "31"
+ },
+ new
+ {
+ Id = new Guid("626ca076-f09e-4a7a-8610-b7de6337b24a"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "1",
+ Order = 0,
+ TypeId = 4,
+ Value = "Первый"
+ },
+ new
+ {
+ Id = new Guid("032fbd02-67d0-4b8c-bed0-42629ab7113b"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "2",
+ Order = 1,
+ TypeId = 4,
+ Value = "Второй"
+ },
+ new
+ {
+ Id = new Guid("fa8a8f60-e41e-495e-ac86-35174d9976bf"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "3",
+ Order = 2,
+ TypeId = 4,
+ Value = "Третий"
+ },
+ new
+ {
+ Id = new Guid("d2f90168-2b49-42f2-820b-79db2c522adf"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "4",
+ Order = 3,
+ TypeId = 4,
+ Value = "Четвертый"
+ },
+ new
+ {
+ Id = new Guid("12bb8db2-cf7f-4113-baff-6883770f1ba5"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "5",
+ Order = 4,
+ TypeId = 4,
+ Value = "Последний"
+ },
+ new
+ {
+ Id = new Guid("18260e91-3fbe-4401-9edc-78dbc419370e"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "1",
+ Order = 0,
+ TypeId = 5,
+ Value = "Январь"
+ },
+ new
+ {
+ Id = new Guid("361526aa-3e1c-452e-bb44-0ade8521830d"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "2",
+ Order = 1,
+ TypeId = 5,
+ Value = "Февраль"
+ },
+ new
+ {
+ Id = new Guid("fad4bdb0-6c51-4810-a30b-6d031a0d4c46"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "3",
+ Order = 2,
+ TypeId = 5,
+ Value = "Март"
+ },
+ new
+ {
+ Id = new Guid("06ab835d-3d3e-4057-8422-a553b6b40995"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "4",
+ Order = 3,
+ TypeId = 5,
+ Value = "Апрель"
+ },
+ new
+ {
+ Id = new Guid("83f56b5d-b16b-4aa5-89d7-a253fee4e4ad"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "5",
+ Order = 4,
+ TypeId = 5,
+ Value = "Май"
+ },
+ new
+ {
+ Id = new Guid("e679ec84-a9ee-4bed-a051-2b14edddcb18"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "6",
+ Order = 5,
+ TypeId = 5,
+ Value = "Июнь"
+ },
+ new
+ {
+ Id = new Guid("d439808a-6a10-409b-8809-a755b7cca60b"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "7",
+ Order = 6,
+ TypeId = 5,
+ Value = "Июль"
+ },
+ new
+ {
+ Id = new Guid("6e9972c4-6bf7-4fe4-b4ea-bbb333fb69c8"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "8",
+ Order = 7,
+ TypeId = 5,
+ Value = "Август"
+ },
+ new
+ {
+ Id = new Guid("0883aac2-9d5b-4098-b672-c684d2a3a0c9"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "9",
+ Order = 8,
+ TypeId = 5,
+ Value = "Сентябрь"
+ },
+ new
+ {
+ Id = new Guid("5e6592bc-acb2-45a4-979b-fdecf8457453"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "10",
+ Order = 9,
+ TypeId = 5,
+ Value = "Октябрь"
+ },
+ new
+ {
+ Id = new Guid("edd7cb49-d6a0-4969-b2d6-1967da69b336"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "11",
+ Order = 10,
+ TypeId = 5,
+ Value = "Ноябрь"
+ },
+ new
+ {
+ Id = new Guid("dd695fb2-4ad0-4cda-a4df-e15059c56b24"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "12",
+ Order = 11,
+ TypeId = 5,
+ Value = "Декабрь"
+ },
+ new
+ {
+ Id = new Guid("2f473624-4eb3-49b4-a4b9-cc7fc08a50f5"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "1",
+ Order = 0,
+ TypeId = 6,
+ Value = "Января"
+ },
+ new
+ {
+ Id = new Guid("f0003490-a249-44bd-814f-4566999915d8"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "2",
+ Order = 1,
+ TypeId = 6,
+ Value = "Февраля"
+ },
+ new
+ {
+ Id = new Guid("f4c3fe38-aeaa-42f7-a9ba-190ea2dfe339"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "3",
+ Order = 2,
+ TypeId = 6,
+ Value = "Марта"
+ },
+ new
+ {
+ Id = new Guid("06a8bd2f-68e1-42f5-961c-ac3b98a2181e"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "4",
+ Order = 3,
+ TypeId = 6,
+ Value = "Апреля"
+ },
+ new
+ {
+ Id = new Guid("963b9c41-d607-444a-9fe0-fe429590e326"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "5",
+ Order = 4,
+ TypeId = 6,
+ Value = "Мая"
+ },
+ new
+ {
+ Id = new Guid("ec8554c8-dee4-49a1-b1b7-474ad8ec1473"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "6",
+ Order = 5,
+ TypeId = 6,
+ Value = "Июня"
+ },
+ new
+ {
+ Id = new Guid("e15c7c63-e29f-41a3-9c82-f70eb6c24fde"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "7",
+ Order = 6,
+ TypeId = 6,
+ Value = "Июля"
+ },
+ new
+ {
+ Id = new Guid("0b1f3cea-301a-4d74-9ce1-2cd93b41897d"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "8",
+ Order = 7,
+ TypeId = 6,
+ Value = "Августа"
+ },
+ new
+ {
+ Id = new Guid("e2fa3769-f66f-4753-a161-35adad7717a5"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "9",
+ Order = 8,
+ TypeId = 6,
+ Value = "Сентября"
+ },
+ new
+ {
+ Id = new Guid("c1de4aca-9f49-48ae-9279-cf9ec4092112"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "10",
+ Order = 9,
+ TypeId = 6,
+ Value = "Октября"
+ },
+ new
+ {
+ Id = new Guid("a74b9ebd-bcd8-4537-b371-194de2fe0a4d"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "11",
+ Order = 10,
+ TypeId = 6,
+ Value = "Ноября"
+ },
+ new
+ {
+ Id = new Guid("852a5ebd-4545-494b-bc69-c27409a41adc"),
+ DateCreated = new DateTimeOffset(new DateTime(2023, 5, 1, 0, 0, 0, 0, DateTimeKind.Unspecified), new TimeSpan(0, 0, 0, 0, 0)),
+ EsppExportValue = "12",
+ Order = 11,
+ TypeId = 6,
+ Value = "Декабря"
+ });
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.Schedule.EsppSchValue", b =>
+ {
+ b.Property("JobGroupId")
+ .HasColumnType("uuid");
+
+ b.Property("TypeValueId")
+ .HasColumnType("uuid");
+
+ b.Property("TypeConfigId")
+ .HasColumnType("uuid");
+
+ b.HasKey("JobGroupId", "TypeValueId", "TypeConfigId");
+
+ b.HasIndex("TypeConfigId");
+
+ b.HasIndex("TypeValueId");
+
+ b.ToTable("EsppSchValues", "schedule");
+ });
+
+ modelBuilder.Entity("PARR.Domain.Entities.Schedule.ScheduleExcludeType", b =>
+ {
+ b.Property