using System.Diagnostics.CodeAnalysis; using WIDESEAWCS_Common.TaskEnum; using WIDESEAWCS_ITaskInfoService; using WIDESEAWCS_Model.Models; using WIDESEAWCS_QuartzJob; using WIDESEAWCS_QuartzJob.Models; using WIDESEAWCS_QuartzJob.Service; namespace WIDESEAWCS_Tasks { /// /// 分容堆垛机任务选择器:封装任务挑选与站台可用性判断。 /// public class FormationStackerCraneTaskSelector { private readonly ITaskService _taskService; private readonly IRouterService _routerService; public FormationStackerCraneTaskSelector(ITaskService taskService, IRouterService routerService) { _taskService = taskService; _routerService = routerService; } public Dt_Task? SelectTask(SpeFormationStackerCrane commonStackerCrane) { Dt_Task? task; if (commonStackerCrane.LastTaskType == null) { task = _taskService.QueryStackerCraneTask(commonStackerCrane.DeviceCode); } else if (commonStackerCrane.LastTaskType.GetValueOrDefault().GetTaskTypeGroup() == TaskTypeGroup.OutbondGroup) { task = _taskService.QueryStackerCraneInTask(commonStackerCrane.DeviceCode); task ??= _taskService.QueryStackerCraneOutTask(commonStackerCrane.DeviceCode); } else { task = _taskService.QueryStackerCraneOutTask(commonStackerCrane.DeviceCode); } if (task != null && task.TaskType.GetTaskTypeGroup() == TaskTypeGroup.OutbondGroup) { if (IsOutTaskStationAvailable(task)) { return task; } var otherOutStationCodes = _routerService .QueryNextRoutes(commonStackerCrane.DeviceCode, task.NextAddress, task.TaskType) .Select(x => x.ChildPosi) .ToList(); var tasks = _taskService.QueryStackerCraneOutTasks(commonStackerCrane.DeviceCode, otherOutStationCodes); foreach (var alternativeTask in tasks) { if (IsOutTaskStationAvailable(alternativeTask)) { return alternativeTask; } } task = _taskService.QueryStackerCraneInTask(commonStackerCrane.DeviceCode); } return task; } private bool IsOutTaskStationAvailable([NotNull] Dt_Task task) { Dt_Router? router = _routerService.QueryNextRoute(task.Roadway, task.NextAddress, task.TaskType); if (router == null) { _taskService.UpdateTaskExceptionMessage(task.TaskNum, $"未找到站台【{task.NextAddress}】信息,无法校验站台"); return false; } IDevice? device = Storage.Devices.FirstOrDefault(x => x.DeviceCode == router.ChildPosiDeviceCode); if (device == null) { _taskService.UpdateTaskExceptionMessage(task.TaskNum, $"未找到出库站台【{router.ChildPosiDeviceCode}】对应的通讯对象,无法判断出库站台是否被占用"); return false; } CommonConveyorLine conveyorLine = (CommonConveyorLine)device; return conveyorLine.IsOccupied(router.ChildPosi); } } }