/*
|
*所有关于Dt_TaskWCSinfo类的业务代码应在此处编写
|
*可使用repository.调用常用方法,获取EF/Dapper等信息
|
*如果需要事务请使用repository.DbContextBeginTransaction
|
*也可使用DBServerProvider.手动获取数据库相关信息
|
*用户信息、权限、角色等使用UserContext.Current操作
|
*Dt_TaskWCSinfoService对增、删、改查、导入、导出、审核业务代码扩展参照ServiceFunFilter
|
*/
|
using Microsoft.AspNetCore.Http;
|
using Microsoft.EntityFrameworkCore;
|
using Microsoft.Extensions.DependencyInjection;
|
using System;
|
using System.Collections.Generic;
|
using System.Linq;
|
using System.Linq.Expressions;
|
using WIDESEA_Common;
|
using WIDESEA_Common.CutomerModel;
|
using WIDESEA_Common.TaskEnum;
|
using WIDESEA_Common.Tools;
|
using WIDESEA_Core.BaseProvider;
|
using WIDESEA_Core.Extensions;
|
using WIDESEA_Core.Extensions.AutofacManager;
|
using WIDESEA_Core.Utilities;
|
using WIDESEA_Entity.DomainModels;
|
using WIDESEA_Services.IRepositories;
|
using WIDESEA_Services.Repositories;
|
|
namespace WIDESEA_Services.Services
|
{
|
public partial class Dt_TaskWCSinfoService
|
{
|
private readonly IHttpContextAccessor _httpContextAccessor;
|
private readonly IDt_TaskWCSinfoRepository _repository;//访问数据库
|
|
[ActivatorUtilitiesConstructor]
|
public Dt_TaskWCSinfoService(
|
IDt_TaskWCSinfoRepository dbRepository,
|
IHttpContextAccessor httpContextAccessor
|
)
|
: base(dbRepository)
|
{
|
_httpContextAccessor = httpContextAccessor;
|
_repository = dbRepository;
|
//多租户会用到这init代码,其他情况可以不用
|
//base.Init(dbRepository);
|
}
|
|
|
/// <summary>
|
/// 根据WMS下发的任务,添加WCS任务
|
/// </summary>
|
/// <param name="taskInfo"></param>
|
/// <returns></returns>
|
public WebResponseContent AddTaskByWms(List<WmsTaskInfo> taskInfos)
|
{
|
WebResponseContent content = new WebResponseContent();
|
try
|
{
|
List<Dt_TaskWCSinfo> wcsTaskList = new List<Dt_TaskWCSinfo>();
|
List<Dt_TaskRGVinfo> rgvTaskList = new List<Dt_TaskRGVinfo>();
|
foreach (var taskInfo in taskInfos)
|
{
|
if (repository.Exists(x => x.wcstask_barcode == taskInfo.task_barcode))
|
return content.Error(taskInfo.task_barcode + "已存在未完成的任务,请先检查。");
|
|
if (taskInfo.task_type.Contains("Inbound"))
|
if (repository.Exists(x => x.wcstask_startPoint == "20101" && x.wcstask_state == TaskState.TaskState_Assigned.ToString()))
|
return content.Error("当前存在待执行的入库任务,请等待.");
|
//空托盘入库
|
if (taskInfo.task_type == TaskType.TaskType_Empty_Pallet_Inbound.ToString())
|
{
|
Dt_TaskWCSinfo wcsInfo = CommonFunction.AddWCSEmptyInboundTask(taskInfo, Dt_TaskWCSinfoRepository.Instance);
|
wcsTaskList.Add(wcsInfo);
|
}
|
//空托盘出库
|
else if (taskInfo.task_type == TaskType.TaskType_Empty_Pallet_Outbound.ToString())
|
{
|
Dt_TaskWCSinfo wcsInfo = CommonFunction.AddWCSEmptyOutboundTask(taskInfo);
|
wcsTaskList.Add(wcsInfo);
|
if (taskInfo.task_endstation.Equal("20101"))
|
{
|
Dt_TaskRGVinfo rgvInfo = CommonFunction.AddOutboundTask(taskInfo, wcsInfo);
|
rgvTaskList.Add(rgvInfo);
|
}
|
}
|
//实托入库
|
else if (taskInfo.task_type == TaskType.TaskType_Box_Pallet_Inbound.ToString() || taskInfo.task_type == TaskType.TaskType_ErrorCheckBackIn.ToString()
|
|| taskInfo.task_type == TaskType.TaskType_CheckBackIn.ToString())
|
{
|
Dt_TaskWCSinfo wcsInfo = CommonFunction.AddWCSBoxInboundTask(taskInfo);
|
wcsTaskList.Add(wcsInfo);
|
}
|
//实托出库
|
else if (taskInfo.task_type == TaskType.TaskType_Box_Pallet_Outbound.ToString()|| taskInfo.task_type == TaskType.TaskType_CheckOutbound.ToString())
|
{
|
Dt_TaskWCSinfo wcsInfo = CommonFunction.AddWCSBoxOutboundTask(taskInfo);
|
wcsTaskList.Add(wcsInfo);
|
|
//入库区才直接添加AGV任务
|
if (taskInfo.task_endstation.Equal("20101"))
|
{
|
Dt_TaskRGVinfo rgvInfo = CommonFunction.AddOutboundTask(taskInfo, wcsInfo);
|
rgvTaskList.Add(rgvInfo);
|
}
|
}
|
//轴承测量出库
|
else if (taskInfo.task_type == TaskType.TaskType_Box_Pallet_Measure_Out.ToString())
|
{
|
Dt_TaskWCSinfo wcsInfo = CommonFunction.AddWCSMeasureOutboundTask(taskInfo);
|
wcsTaskList.Add(wcsInfo);
|
|
Dt_TaskRGVinfo rgvInfo = CommonFunction.AddOutboundTask(taskInfo, wcsInfo);
|
rgvTaskList.Add(rgvInfo);
|
}
|
//轴承测量完成后回库-----【该类任务不是WMS下发的,而是WCS在测量完成后,自动转变为该类任务的】
|
else if (taskInfo.task_type == TaskType.TaskType_Box_Pallet_Measure_Back.ToString())
|
{
|
|
}
|
else if (taskInfo.task_type == TaskType.TaskType_MoveOutbound.ToString())
|
{
|
Dt_TaskWCSinfo wcsInfo = CommonFunction.AddWCSMoveOutboundTask(taskInfo);
|
wcsTaskList.Add(wcsInfo);
|
|
string[] fromLocationArray = wcsInfo.wcstask_startLocation.Split('-');
|
string[] toLocationArray = wcsInfo.wcstask_endLocation.Split('-');
|
if (fromLocationArray[0] == toLocationArray[0])
|
{
|
Dt_TaskRGVinfo moveOutbound = CommonFunction.AddRGVMoveOutboundTask(taskInfo, wcsInfo, RGVTaskType.RgvTaskType_Move);
|
rgvTaskList.Add(moveOutbound);
|
|
}
|
else
|
{
|
Dt_TaskRGVinfo moveInbound = CommonFunction.AddRGVMoveOutboundTask(taskInfo, wcsInfo, RGVTaskType.RgvTaskType_Outbound);
|
rgvTaskList.Add(moveInbound);
|
}
|
}
|
else
|
throw new Exception("无效任务类型:" + taskInfo.task_type);
|
}
|
|
if (null != wcsTaskList && wcsTaskList.Count > 0)
|
{
|
content = repository.DbContextBeginTransaction(() =>
|
{
|
repository.AddRange(wcsTaskList, true);
|
if (null != rgvTaskList && rgvTaskList.Count > 0)
|
repository.AddRange(rgvTaskList, true);
|
|
return content.OK();
|
});
|
}
|
|
}
|
catch (Exception ex)
|
{
|
content.Error(ex.Message);
|
}
|
|
return content;
|
|
}
|
|
|
|
/// <summary>
|
/// 取消一条未开始执行的任务
|
/// </summary>
|
/// <param name="taskInfo"></param>
|
/// <returns></returns>
|
public WebResponseContent CancelATask(SaveModel saveModel)
|
{
|
WebResponseContent content = new WebResponseContent();
|
try
|
{
|
string barcode = saveModel.MainData["barcode"].ToString();
|
if (barcode == null)
|
throw new Exception("取消任务的托盘号不能为空");
|
|
Dt_TaskWCSinfo taskinfo = Dt_TaskWCSinfoRepository.Instance.FindFirst(x => x.wcstask_barcode == barcode);
|
if (taskinfo == null)
|
return content.OK($"没有找到托盘号:【{barcode}】对应的任务");
|
|
if (taskinfo.wcstask_state != TaskState.TaskState_Assigned.ToString())
|
throw new Exception($"托盘号:【{barcode}】对应的任务已经开始执行,无法取消");
|
|
content = Dt_TaskWCSinfoRepository.Instance.DbContextBeginTransaction(() =>
|
{
|
Dt_TaskWCSinfoRepository.Instance.Delete(taskinfo, true);
|
|
Dt_TaskRGVinfo rgvInfo = Dt_TaskRGVinfoRepository.Instance.FindFirst(x => x.rgvtask_barCode == barcode && x.rgvtask_taskStatus == RGVTaskState.RgvTaskState_Wait_Send.ToString());
|
if (rgvInfo != null)
|
Dt_TaskRGVinfoRepository.Instance.Delete(rgvInfo, true);
|
return content.OK();
|
});
|
}
|
catch (Exception ex)
|
{
|
content.Error(ex.Message);
|
}
|
return content;
|
|
}
|
|
|
/// <summary>
|
/// WMS下发的更改任务状态,给测量设备测量完毕后,更新WCS任务状态
|
/// </summary>
|
/// <param name="saveModel"></param>
|
/// <returns></returns>
|
public WebResponseContent UpdateWcsTaskState(SaveModel saveModel)
|
{
|
|
WebResponseContent content = new WebResponseContent();
|
try
|
{
|
string barcode = saveModel.MainData["barcode"].ToString();
|
string state = saveModel.MainData["state"].ToString();
|
string taskType = saveModel.MainData["tasktype"].ToString();
|
|
Dt_TaskWCSinfo wcsInfo = Dt_TaskWCSinfoRepository.Instance.FindFirst(x => x.wcstask_barcode == barcode);
|
if (wcsInfo != null)
|
{
|
//更新任务数据,准备回库,起点终点倒换
|
string endLoc = wcsInfo.wcstask_endPoint;
|
wcsInfo.wcstask_state = TaskState.TaskState_Measure_Back_Line_Executing.ToString();
|
wcsInfo.wcstask_endPoint = wcsInfo.wcstask_startPoint;
|
wcsInfo.wcstask_endLocation = wcsInfo.wcstask_startLocation;
|
wcsInfo.wcstask_startLocation = endLoc;
|
wcsInfo.wcstask_startPoint = "10301";
|
|
wcsInfo.wcstask_state = state;
|
wcsInfo.wcstask_type = taskType;
|
Dt_TaskWCSinfoRepository.Instance.Update(wcsInfo, true);
|
}
|
else
|
{
|
content.Error($"没有找到托盘码:【{barcode}】对应的任务!!");
|
return content;
|
}
|
|
content.OK();
|
}
|
catch (Exception ex)
|
{
|
content.Error(ex.Message);
|
}
|
return content;
|
|
}
|
|
|
|
/// <summary>
|
/// 手动更改任务状态
|
/// </summary>
|
/// <param name="saveModel"></param>
|
/// <returns></returns>
|
public static WebResponseContent ChangeWcsTaskStatus(SaveModel saveModel)
|
{
|
WebResponseContent content = new WebResponseContent();
|
try
|
{
|
int taskNumer = int.Parse(saveModel.MainData["taskNumber"].ToString());
|
string state = saveModel.MainData["state"].ToString();
|
Dt_TaskWCSinfo wcsInfo = Dt_TaskWCSinfoRepository.Instance.FindFirst(x => x.wcstask_taskNumber == taskNumer);
|
if (wcsInfo == null)
|
{
|
content.Error($"::Error::没有找到任务号:【{taskNumer}】对应的任务!");
|
return content;
|
}
|
|
content = Dt_TaskWCSinfoRepository.Instance.DbContextBeginTransaction(() =>
|
{
|
|
try
|
{
|
content = WMSApi.PostTaskStateToWMS(wcsInfo.wcstask_barcode, state);
|
if (content.Status)
|
{
|
wcsInfo.wcstask_state = state;
|
if (state == TaskState.TaskState_Measure_Back_Line_Executing.ToString())
|
{
|
//将任务类型改为回库中
|
wcsInfo.wcstask_type = TaskType.TaskType_Box_Pallet_Measure_Back.ToString();
|
//将任务起始站台和目的站台对调,准备回库
|
|
wcsInfo.wcstask_endPoint = wcsInfo.wcstask_startPoint;
|
wcsInfo.wcstask_startPoint = "10301";
|
wcsInfo.wcstask_endLocation = wcsInfo.wcstask_startLocation;
|
wcsInfo.wcstask_startLocation = wcsInfo.wcstask_endPoint;
|
|
wcsInfo.wcstask_state = TaskState.TaskState_Measure_Back_Line_Executing.ToString();
|
wcsInfo.wcstask_dispatcherTime = DateTime.Now;
|
}
|
Dt_TaskWCSinfoRepository.Instance.Update(wcsInfo, true);
|
WriteLog.Info("手动更改测量状态").Write($"{DateTime.Now}:测量回库异常,反转货位 任务号{taskNumer},托盘号{wcsInfo.wcstask_barcode},反转后起始站台【10301】" +
|
$"终点货位【{wcsInfo.wcstask_endLocation}】", "手动更改测量状态");
|
}
|
else
|
{
|
content.Error($"::Error::上报WMS更新任务号:【{taskNumer}】对应的任务出错!原因:{content.Message}");
|
return content;
|
}
|
content.OK();
|
}
|
catch (Exception ex)
|
{
|
content.Error(ex.Message);
|
}
|
|
return content;
|
});
|
|
if (content.Status)
|
{
|
Dt_TaskRGVinfoRepository taskRGVinfoRepository = new Dt_TaskRGVinfoRepository(Dt_TaskRGVinfoRepository.Instance.DbContext);
|
//根据任务类型和更改的任务状态,进行接着的逻辑
|
if (wcsInfo.wcstask_type == TaskType.TaskType_Box_Pallet_Inbound.ToString() ||
|
wcsInfo.wcstask_type == TaskType.TaskType_Empty_Pallet_Inbound.ToString())
|
{
|
//比如手动操作系统将托盘运送至入库口,则需要生成对应的穿梭车任务
|
if (state == TaskState.TaskState_ConveyorLineFinish.ToString())
|
{
|
Dt_TaskRGVinfo rgvInfo = new Dt_TaskRGVinfo();
|
rgvInfo.rgvtask_taskId = GetTaskNumber.GetRgvTaskNumber().ToString();
|
rgvInfo.rgvtask_taskType = RGVTaskType.RgvTaskType_Inbound.ToString();
|
rgvInfo.rgvtask_taskStatus = RGVTaskState.RgvTaskState_Wait_Send.ToString();
|
rgvInfo.rgvtask_priorityCode = wcsInfo.wcstask_grade.ToString();
|
rgvInfo.rgvtask_startNode = wcsInfo.wcstask_startLocation;
|
rgvInfo.rgvtask_endNode = wcsInfo.wcstask_endLocation;
|
rgvInfo.rgvtask_wcsTaskNumber = wcsInfo.wcstask_taskNumber;
|
rgvInfo.rgvtask_barCode = wcsInfo.wcstask_barcode;
|
rgvInfo.rgvtask_msgTime = DateTime.Now;
|
rgvInfo.rgvtask_areaCode = "InboundArea";
|
taskRGVinfoRepository.Add(rgvInfo, true);
|
}
|
}
|
else
|
{
|
|
}
|
}
|
}
|
catch (Exception ex)
|
{
|
content.Error(ex.Message);
|
}
|
|
return content;
|
}
|
|
|
/// <summary>
|
/// WMS下发更改任务信息,当入库任务与出库测量任务冲突时,WMS调用此接口来更换目的货位
|
/// </summary>
|
/// <param name="saveModel"></param>
|
/// <returns></returns>
|
public WebResponseContent UpdateWcsTaskInformation(SaveModel saveModel)
|
{
|
WebResponseContent content = new WebResponseContent();
|
try
|
{
|
string barcode = saveModel.MainData["barcode"].ToString();
|
string newLocationId = saveModel.MainData["newLocationId"].ToString();
|
string newStation = saveModel.MainData["newStation"].ToString();
|
|
Dt_TaskWCSinfo wcsInfo = Dt_TaskWCSinfoRepository.Instance.FindFirst(x => x.wcstask_barcode == barcode);
|
if (wcsInfo == null)
|
{
|
Console.WriteLine($"::Error::=> WMS下发新货位是,在WCS任务中没有找到对应托盘【{barcode}】的号的任务");
|
return content.Error($"::Error::=> WMS下发新货位是,在WCS任务中没有找到对应托盘【{barcode}】的号的任务");
|
}
|
wcsInfo.wcstask_startLocation = newStation;
|
wcsInfo.wcstask_endPoint = newStation;
|
wcsInfo.wcstask_endLocation = newLocationId;
|
Dt_TaskWCSinfoRepository.Instance.Update(wcsInfo, true);
|
|
content.OK();
|
}
|
catch (Exception ex)
|
{
|
content.Error(ex.Message);
|
}
|
|
return content;
|
}
|
|
|
|
/// <summary>
|
/// 取消测量,直接回库
|
/// </summary>
|
/// <param name="saveModel"></param>
|
/// <returns></returns>
|
public WebResponseContent CancelAMeasureTask(SaveModel saveModel)
|
{
|
WebResponseContent content = new WebResponseContent();
|
try
|
{
|
string barcode = saveModel.MainData["barcode"].ToString();
|
|
Dt_TaskWCSinfo wcsInfo = Dt_TaskWCSinfoRepository.Instance.FindFirst(x => x.wcstask_barcode == barcode);
|
if (wcsInfo == null)
|
{
|
Console.WriteLine($"::Error::=> 没有找到【{barcode}】对应的测量任务");
|
return content.Error($"::Error::=> 没有找到【{barcode}】对应的测量任务");
|
}
|
//将任务类型改为回库中
|
wcsInfo.wcstask_type = TaskType.TaskType_Box_Pallet_Measure_Back.ToString();
|
//将任务起始站台和目的站台对调,准备回库
|
wcsInfo.wcstask_endPoint = wcsInfo.wcstask_startPoint;
|
wcsInfo.wcstask_startPoint = "10301";
|
wcsInfo.wcstask_endLocation = wcsInfo.wcstask_startLocation;
|
wcsInfo.wcstask_startLocation = wcsInfo.wcstask_endPoint;
|
wcsInfo.wcstask_state = TaskState.TaskState_Measure_Back_Line_Wait_Executing.ToString();
|
wcsInfo.wcstask_dispatcherTime = DateTime.Now;
|
Dt_TaskWCSinfoRepository.Instance.Update(wcsInfo, true);
|
|
content.OK();
|
}
|
catch (Exception ex)
|
{
|
content.Error(ex.Message);
|
}
|
|
return content;
|
}
|
|
|
/// <summary>
|
/// 手动完成一个WCS任务(目前仅支持手动完成空托盘出库功能,因为空托盘到了缓存位经常有人手动去动)
|
/// </summary>
|
/// <param name="saveModel"></param>
|
/// <returns></returns>
|
public static WebResponseContent CompleteWcsTaskByMannual(SaveModel saveModel)
|
{
|
WebResponseContent content = new WebResponseContent();
|
try
|
{
|
int taskNumer = int.Parse(saveModel.MainData["taskNumber"].ToString());
|
Dt_TaskWCSinfo taskWCSinfo = Dt_TaskWCSinfoRepository.Instance.FindFirst(x => x.wcstask_taskNumber == taskNumer);
|
if (taskWCSinfo == null)
|
throw new Exception($"没有找到任务号:【{taskNumer}】对应的WCS任务");
|
//在此完成该空托出库任务
|
content = Dt_TaskWCSinfoRepository.Instance.DbContextBeginTransaction(() =>
|
{
|
WebResponseContent transContent = new WebResponseContent();
|
try
|
{
|
//上报WMS任务完成
|
transContent = WMSApi.TellWmsTaskFinished(taskWCSinfo.wcstask_barcode,taskWCSinfo.wcstask_backUp_2);
|
if (transContent.Status)
|
{
|
//移动任务到历史表
|
taskWCSinfo.wcstask_state = TaskState.TaskState_Finished.ToString();
|
CommonFunction.AddWcsTaskToHistory(taskWCSinfo, Dt_TaskWCSinfoRepository.Instance, Dt_TaskWCSinfo_HtyRepository.Instance);
|
}
|
else
|
{
|
throw new Exception($"上报WMS任务完成出错,原因:【{transContent.Message}】");
|
}
|
|
transContent.OK();
|
}
|
catch (Exception ex)
|
{
|
transContent.Error(ex.Message);
|
}
|
|
return transContent;
|
});
|
|
if (!content.Status)
|
throw new Exception($"::Error::=> 手动完成任务出错,原因:{content.Message}");
|
}
|
catch (Exception ex)
|
{
|
content.Error(ex.Message);
|
}
|
|
return content;
|
}
|
|
|
}
|
}
|