using HH.WCS.Mobox3.YNJT_PT.core; using HH.WCS.Mobox3.YNJT_PT.device; using HH.WCS.Mobox3.YNJT_PT.models; using HH.WCS.Mobox3.YNJT_PT.process; using HH.WCS.Mobox3.YNJT_PT.util; using HH.WCS.Mobox3.YNJT_PT.wms; using MySqlX.XDevAPI.Common; using Newtonsoft.Json; using Newtonsoft.Json.Linq; using SqlSugar; using Swashbuckle.Swagger; using System; using System.Collections.Generic; using System.Linq; using System.Reflection; using System.Text.RegularExpressions; using System.Threading; using Ubiety.Dns.Core; using static HH.WCS.Mobox3.YNJT_PT.api.ApiModel; using static HH.WCS.Mobox3.YNJT_PT.api.OtherModel; using static HH.WCS.Mobox3.YNJT_PT.api.WmsController; using static HH.WCS.Mobox3.YNJT_PT.dispatch.WCSDispatch; using static HH.WCS.Mobox3.YNJT_PT.util.Settings; using static HH.WCS.Mobox3.YNJT_PT.wms.WMSHelper; using static System.Net.Mime.MediaTypeNames; namespace HH.WCS.Mobox3.YNJT_PT.api { /// /// api接口辅助类 /// public class ApiHelper { static ApiHelper() { } /// /// 成型机下线记录 /// /// public static ResponseResult cxjOffLineRecord(NotifyDeviceSignalModel model) { ResponseResult response = new ResponseResult(); var container = ContainerHelper.GetCntr(model.cntrNo); if (container == null) { ContainerHelper.AddCntr(model.cntrNo); } try { OffLineModel extData1 = JsonConvert.DeserializeObject(model.extData.ToString()); OffLineRecord record = new OffLineRecord() { S_RFID = model.cntrNo, S_DEVICE_NO = model.deviceNo, N_IS_URGENT = extData1.isUrgent, T_OFF_TIME = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss"), N_IS_FULL = extData1.isFull, N_NEED_PAIR = extData1.needPair, S_LOC = model.loc }; WMSHelper.addOffLineRecord(record); } catch (Exception ex) { LogHelper.Info($"添加成型机下线记录错误,错误原因:{ex.Message}", "WMS"); response.code = 500; response.msg = "WMS系统内部错误,请联系开发人员排查问题"; } return response; } /// /// 下线请求 /// /// public static ResponseResult offLineRequest(NotifyDeviceSignalModel model) { ResponseResult response = new ResponseResult(); var startLoc = LocationHelper.GetLoc(model.loc); if (startLoc != null) { List extData = JsonConvert.DeserializeObject>(model.extData.ToString()); int dataCount = extData.Count; if (dataCount > 0) { var rfidExistNull = extData.Where(a => string.IsNullOrEmpty(a.rfid)).Count()>0; if (rfidExistNull) { response.code = 1; response.msg = "rfid不能为空"; return response; } else { if (extData.Count > 0) { List barcodeList = new List(); foreach (var ext in extData) { string rfid = ext.rfid; if (rfid == "88888888") { // 记录托盘异常 } else { // 查询成型机中间表,rfid 是否存在 var offLineRecord = WMSHelper.getOffLineRecord(rfid); if (offLineRecord != null) { if (offLineRecord.N_IS_FULL == 1) { if (ext.barcode.Contains("99999999")) { // 记录条码扫描异常 } else { // 2.查询物料条码信息表,条码信息是否存在 var itemBarcodeInfo = WMSHelper.GetGreenTireInformation(ext.barcode); if (itemBarcodeInfo != null) { itemBarcodeInfo.N_URGENT_FLAG = offLineRecord.N_IS_URGENT; // 计算生效时间、失效时间 var overage = WMSHelper.getOverage(itemBarcodeInfo.BARCODE); LogHelper.Info($"计算生效时间、失效时间,返回值:{JsonConvert.SerializeObject(overage)}", "WMS"); if (overage != null) { DateTime txndate = DateTime.Parse(itemBarcodeInfo.TXNDATE); DateTime minTime = txndate.AddHours(overage.MINHOUR); DateTime maxTime = txndate.AddDays(overage.OVERAGE); itemBarcodeInfo.S_EFFECTIVE_TIME = minTime.ToString("yyyy-MM-dd HH:mm:ss"); itemBarcodeInfo.S_EXPIRATION_TIME = maxTime.ToString("yyyy-MM-dd HH:mm:ss"); } else { response.code = 1; response.msg = $"未查询到物料存放时间配置信息,条形码:{itemBarcodeInfo.BARCODE}"; return response; } ContainerHelper.addCntrItemRel(rfid, itemBarcodeInfo); barcodeList.Add(ext); } else { // 记录查询条码信息异常 } } } } } } EndLocGroup endLocGroup = null; if (barcodeList.Count > 0) { string itemCode = null; var cntrItemRels = ContainerHelper.GetCntrItemRel(barcodeList[0].rfid); if (cntrItemRels.Count > 0) { itemCode = cntrItemRels[0].S_ITEM_CODE; } endLocGroup = WMSHelper.getInStockEndLoc(barcodeList.Count, itemCode); } foreach (var ext in extData) { Location endLoc = null; string groupNo = null; if (barcodeList.Contains(ext)) { // 满料入库 if (endLocGroup != null) { groupNo = endLocGroup.groupNo; endLoc = endLocGroup.endLocList[0]; endLocGroup.endLocList.Remove(endLoc); } if (endLoc != null) { var wmsTask = new WMSTask() { S_CNTR_CODE = ext.rfid, S_CODE = WMSHelper.GenerateTaskNo(), S_START_LOC = startLoc.S_CODE, S_START_AREA = startLoc.S_AREA_CODE, S_END_LOC = endLoc.S_CODE, S_END_AREA = endLoc.S_AREA_CODE, S_TYPE = "满料下线入库任务", S_OP_DEF_CODE = model.reqId, S_OP_DEF_NAME = "成型机满料下线入库", N_PRIORITY = 1, T_START_TIME = DateTime.Now, S_GROUP_NO = groupNo, }; if (WMSHelper.CreateWmsTask(wmsTask)) { // 创建一段入库任务 WCSTask wcsTask = new WCSTask() { S_OP_NAME = wmsTask.S_OP_DEF_NAME, S_OP_CODE = wmsTask.S_CODE, S_CODE = WCSHelper.GenerateTaskNo(), S_CNTR_CODE = wmsTask.S_CNTR_CODE, S_TYPE = wmsTask.S_TYPE, S_START_LOC = startLoc.S_CODE, S_START_AREA = startLoc.S_AREA_CODE, S_END_LOC = endLoc.S_CODE, S_END_AREA = endLoc.S_AREA_CODE, S_SCHEDULE_TYPE = "WCS", N_PRIORITY = 1, T_START_TIME = DateTime.Now, }; if (WCSHelper.CreateTask(wcsTask)) { // 起点、接驳点、终点加锁 LocationHelper.LockLoc(wcsTask.S_START_LOC, 2); LocationHelper.LockLoc(wcsTask.S_END_LOC, 1); // 更新作业任务状态 wmsTask.N_B_STATE = 1; WMSHelper.UpdateTaskState(wmsTask); /*// 绑定容器物料信息 var itemBarcodeInfo = WMSHelper.GetGreenTireInformation(ext.barcode); WMSHelper.bindBarcodeItemInfo(wmsTask.S_CNTR_CODE, itemBarcodeInfo);*/ } } } } else { // 异常托盘排除 var middleLoc = WMSHelper.getMinTaskMiddleLoc(1); // 1.排出位 endLoc = WMSHelper.getOnlneLoc(2); // 2.空托上线位(排出的托盘都出库到空托上线位进行处理) if (endLoc != null && middleLoc != null) { var wmsTask = new WMSTask() { S_CNTR_CODE = ext.rfid, S_CODE = WMSHelper.GenerateTaskNo(), S_START_LOC = startLoc.S_CODE, S_START_AREA = startLoc.S_AREA_CODE, S_END_LOC = endLoc.S_CODE, S_END_AREA = endLoc.S_AREA_CODE, S_TYPE = "异常托盘出库任务", S_OP_DEF_CODE = model.reqId, S_OP_DEF_NAME = "异常托盘出库检修", N_PRIORITY = 1, T_START_TIME = DateTime.Now, }; if (WMSHelper.CreateWmsTask(wmsTask)) { // 创建一段入库任务 WCSTask wcsTask = new WCSTask() { S_OP_NAME = wmsTask.S_OP_DEF_NAME, S_OP_CODE = wmsTask.S_CODE, S_CODE = WCSHelper.GenerateTaskNo(), S_CNTR_CODE = wmsTask.S_CNTR_CODE, S_TYPE = wmsTask.S_TYPE, S_START_LOC = startLoc.S_CODE, S_START_AREA = startLoc.S_AREA_CODE, S_END_LOC = middleLoc.S_CODE, S_END_AREA = middleLoc.S_AREA_CODE, S_SCHEDULE_TYPE = "WCS", N_PRIORITY = 1, T_START_TIME = DateTime.Now, }; if (WCSHelper.CreateTask(wcsTask)) { // 起点、接驳点、终点加锁 LocationHelper.LockLoc(wcsTask.S_START_LOC, 2); LocationHelper.LockLoc(wcsTask.S_END_LOC, 1); // 更新作业任务状态 wmsTask.N_B_STATE = 1; WMSHelper.UpdateTaskState(wmsTask); } } } else { LogHelper.Info("异常托盘排出,未获取异常排除接驳位", "WMS"); } } } } } } else { response.code = 1; response.msg = "入参缺少托盘和条码信息"; } } else { response.code = 1; response.msg = "起点货位不存在"; } return response; } /// /// 读码请求 /// 场景:1. /// public static ResponseResult readCodeRequest(NotifyDeviceSignalModel model) { ResponseResult response = new ResponseResult(); readCodeFeedbackResponse readCodeFeedbackResponse = new readCodeFeedbackResponse() { verifyResult = true }; var wcsTask = WCSHelper.GetTask(model.taskNo); var wmsTask = WMSHelper.GetWmsTask(wcsTask.S_OP_CODE); if (wcsTask != null && wmsTask != null) { Location endLoc = LocationHelper.GetLoc(wmsTask.S_END_LOC); // 原终点 if (wcsTask.S_TYPE == "满料下线入库任务") { // 判断rfid是否异常 if (model.cntrNo != wcsTask.S_CNTR_CODE) { // 查询排出口 Location middleLoc = WMSHelper.getMinTaskMiddleLoc(1, 0, endLoc.N_ROADWAY); // 查询新终点 endLoc = WMSHelper.getOnlneLoc(2); wcsTask.S_END_LOC = middleLoc.S_CODE; wcsTask.S_END_AREA = middleLoc.S_AREA_CODE; WCSHelper.updateTaskEnd(wcsTask); wmsTask.S_END_LOC = endLoc.S_CODE; wmsTask.S_END_AREA = endLoc.S_AREA_CODE; WMSHelper.UpdateTaskEnd(wmsTask); readCodeFeedbackResponse.verifyResult = false; readCodeFeedbackResponse.endLoc = middleLoc.S_CODE; } } else if (wcsTask.S_TYPE == "胚胎叫料出库任务") { var cntrItemRels = ContainerHelper.GetCntrItemRel(wcsTask.S_CNTR_CODE); if (model.cntrNo != wcsTask.S_CNTR_CODE || cntrItemRels.Count == 0 || cntrItemRels.Count > 0 && cntrItemRels[0].S_ITEM_STATE != "OK") { // 计算排出口 endLoc = WMSHelper.getCallOutLoc(endLoc.N_ROW); wcsTask.S_END_LOC = endLoc.S_CODE; wcsTask.S_END_AREA = endLoc.S_AREA_CODE; WCSHelper.updateTaskEnd(wcsTask); wmsTask.S_END_LOC = endLoc.S_CODE; wmsTask.S_END_AREA = endLoc.S_AREA_CODE; WMSHelper.UpdateTaskEnd(wmsTask); readCodeFeedbackResponse.verifyResult = false; readCodeFeedbackResponse.endLoc = endLoc.S_CODE; } } } else { response.code = 1; response.msg = $"任务号:{model.taskNo},未查询到执行中的任务"; } response.data = readCodeFeedbackResponse; return response; } /// /// 异常申请(取消任务) /// /// /// public static ResponseResult anomalyRequest(NotifyDeviceSignalModel model) { ResponseResult response = new ResponseResult(); readCodeFeedbackResponse readCodeFeedbackResponse = new readCodeFeedbackResponse() { verifyResult = true }; var wcsTask = WCSHelper.GetTask(model.taskNo); var wmsTask = WMSHelper.GetWmsTask(wcsTask.S_OP_CODE); if (wcsTask != null && wmsTask != null) { Location endLoc = LocationHelper.GetLoc(wmsTask.S_END_LOC); // 原终点 if (wcsTask.S_TYPE == "满料下线入库任务") { // 查询排出口 var middleLoc = WMSHelper.getMinTaskMiddleLoc(1, 0, endLoc.N_ROADWAY); wcsTask.S_END_LOC = middleLoc.S_CODE; wcsTask.S_END_AREA = middleLoc.S_AREA_CODE; WCSHelper.updateTaskEnd(wcsTask); readCodeFeedbackResponse.verifyResult = false; readCodeFeedbackResponse.endLoc = middleLoc.S_CODE; // 查询新终点 endLoc = WMSHelper.getOnlneLoc(2); } else if (wcsTask.S_TYPE == "胚胎叫料出库任务") { endLoc = WMSHelper.getCallOutLoc(endLoc.N_ROW); readCodeFeedbackResponse.verifyResult = false; readCodeFeedbackResponse.endLoc = endLoc.S_CODE; } wmsTask.S_END_LOC = endLoc.S_CODE; wmsTask.S_END_AREA = endLoc.S_AREA_CODE; WMSHelper.UpdateTaskEnd(wmsTask); } else { response.code = 1; response.msg = $"任务号:{model.taskNo},未查询到执行中的任务"; } response.data = readCodeFeedbackResponse; return response; } /// /// 申请新终点 /// /// /// public static ResponseResult applyDest(ApplyDestModel model) { ResponseResult response = new ResponseResult(); ApplyDest applyDest = new ApplyDest(); var wcsTask = WCSHelper.GetTask(model.taskNo); if (wcsTask != null) { var wmsTask = WMSHelper.GetWmsTask(wcsTask.S_OP_CODE); if (wcsTask != null) { string itemCode = null; var endLoc = LocationHelper.GetLoc(wcsTask.S_END_LOC); var cntrItemRels = ContainerHelper.GetCntrItemRel(wcsTask.S_CNTR_CODE); if (cntrItemRels.Count > 0) { itemCode = cntrItemRels[0].S_ITEM_CODE; } if (model.applyType == 1) { LocationHelper.LockLoc(wcsTask.S_END_LOC, 3); // 将原货位锁定(其他锁) var endLocGroup = WMSHelper.getInStockEndLoc(1, itemCode, endLoc.N_ROADWAY); if (endLocGroup.endLocList.Count > 0) { endLoc = endLocGroup.endLocList[0]; applyDest.endLoc = endLoc.S_CODE; } } else if (model.applyType == 2) { var endLocGroup = WMSHelper.getInStockEndLoc(1, cntrItemRels[0].S_ITEM_CODE, 0, endLoc.N_ROADWAY); if (endLocGroup.endLocList.Count > 0) { endLoc = endLocGroup.endLocList[0]; applyDest.endLoc = endLoc.S_CODE; } } } } else { response.code = 1; response.msg = $"任务:{model.taskNo}不存在"; } return response; } public class ApplyDest { public string endLoc { get; set; } } /// /// 4.硫化机呼叫胚胎出库 /// 逻辑: /// 1.根据机台号查询【硫化机工单表】、【胚胎已完成的条码中间表】筛选当前班次的生产计划数量是否满足,当预计生产数量 = 实际数+在途数量 ,则停止叫料 /// 2.查询机台号在【硫化机工单表】对应的物料编码, /// 开始计算(1.巷道不报警、2.物料状态OK、3.小于失效时间 大于等于生效时间 4.加急料先出、5.先入先出(生产时间))出库物料,生成任务 /// /// public static ResponseResult callItemOutStock(NotifyDeviceSignalModel model) { ResponseResult response = new ResponseResult(); var locCodes = model.loc.Split(',').ToList(); int locNum = locCodes.Count; if (locNum > 0) { Location prevLoc = null; Dictionary outLocDic = new Dictionary(); foreach (var mcn in locCodes) { // 1.一个硫化机工位只能同时存在一个正在执行中的任务 var existTask = WCSHelper.GetTaskByEnd(mcn); if (existTask.Count == 0) { // 2.根据当前时间,判断班次日期和班次 var currentTime = DateTime.Now; var shift = getShift(currentTime.TimeOfDay); // 班次 var dateShift = currentTime.ToString("dd/MM/yyyy"); TimeSpan shiftIII_Start = new TimeSpan(7, 00, 0); // 7:00:00 if (shift == "III" && currentTime.TimeOfDay < shiftIII_Start) { dateShift = DateTime.Now.AddDays(-1).ToString("dd/MM/yyyy"); } // 3.根据班次日期+班次+硫化机工位号查询 硫化机工单 中的物料编码、预计生产数量 var productionShedule = WMSHelper.getProductionShedule(dateShift, mcn, shift); if (productionShedule != null && productionShedule.QTY != 0) { // 4查询【胚胎已完成的条码中间表】并计算当前班次的已完成数量 int finishNum = WMSHelper.getEmbryoFinishNum(dateShift, mcn, shift); if (productionShedule.QTY > finishNum) { // 5.出库策略 1.优先查询前一拖货位的左右两边是否满足条件 2.计算(1.巷道不报警、2.物料状态OK、3.小于失效时间 大于等于生效时间 4.加急料先出、5.先入先出(生产时间))出库物料,生成任务 var startLoc = WMSHelper.getOutStockStartLoc(productionShedule.ITEMCODE, prevLoc); if (startLoc != null) { outLocDic.Add(mcn, startLoc); prevLoc = startLoc; } } } } } // 6.判断出库货位是否是同一巷道,同一巷道生成任务组号 string groupNo = null; if (outLocDic.Count > 1) { var groupNum = outLocDic.Select(a => a.Value).ToList().GroupBy(a => a.N_ROADWAY).Count(); if (groupNum == 1) { groupNo = GenerateTaskGroupNo(); } } // 7.生成出库任务 if (outLocDic.Count > 0) { foreach (var item in outLocDic) { Location endLoc = LocationHelper.GetLoc(item.Key); Location startLoc = item.Value; if (endLoc != null) { var locCntrRels = LocationHelper.GetLocCntr(startLoc.S_CODE); if (locCntrRels != null && locCntrRels.Count > 0) { var wmsTask = new WMSTask() { S_CNTR_CODE = locCntrRels[0].S_CNTR_CODE, S_CODE = WMSHelper.GenerateTaskNo(), S_START_LOC = startLoc.S_CODE, S_START_AREA = startLoc.S_AREA_CODE, S_END_LOC = endLoc.S_CODE, S_END_AREA = endLoc.S_AREA_CODE, S_TYPE = "胚胎叫料出库任务", S_OP_DEF_CODE = model.reqId, S_OP_DEF_NAME = "硫化机呼叫胚胎出库", N_PRIORITY = 1, T_START_TIME = DateTime.Now, S_GROUP_NO = groupNo, }; if (WMSHelper.CreateWmsTask(wmsTask)) { // 创建一段入库任务 WCSTask wcsTask = new WCSTask() { S_OP_NAME = wmsTask.S_OP_DEF_NAME, S_OP_CODE = wmsTask.S_CODE, S_CODE = WCSHelper.GenerateTaskNo(), S_CNTR_CODE = wmsTask.S_CNTR_CODE, S_TYPE = wmsTask.S_TYPE, S_START_LOC = startLoc.S_CODE, S_START_AREA = startLoc.S_AREA_CODE, S_END_LOC = endLoc.S_CODE, S_END_AREA = endLoc.S_AREA_CODE, S_SCHEDULE_TYPE = "WCS", N_PRIORITY = 1, T_START_TIME = DateTime.Now, }; if (WCSHelper.CreateTask(wcsTask)) { // 起点、接驳点、终点加锁 LocationHelper.LockLoc(wcsTask.S_START_LOC, 2); LocationHelper.LockLoc(wcsTask.S_END_LOC, 1); // 更新作业任务状态 wmsTask.N_B_STATE = 1; WMSHelper.UpdateTaskState(wmsTask); } } } } } } } return response; } /// /// 空托入库 /// /// /// public static ResponseResult emptyTrayInStock(NotifyDeviceSignalModel model) { ResponseResult response = new ResponseResult(); Location startLoc = LocationHelper.GetLoc(model.loc); var cntrCodeList = model.loc.Split(',').ToList(); if (cntrCodeList.Count > 0) { var endLocGroup = WMSHelper.getInStockEndLoc(cntrCodeList.Count, null); if (endLocGroup.endLocList.Count > 0) { foreach (var endLoc in endLocGroup.endLocList) { var wmsTask = new WMSTask() { S_CNTR_CODE = model.cntrNo, S_CODE = WMSHelper.GenerateTaskNo(), S_START_LOC = startLoc.S_CODE, S_START_AREA = startLoc.S_AREA_CODE, S_END_LOC = endLoc.S_CODE, S_END_AREA = endLoc.S_AREA_CODE, S_TYPE = "空托入库任务", S_OP_DEF_CODE = model.reqId, S_OP_DEF_NAME = "空托盘回库任务", N_PRIORITY = 1, T_START_TIME = DateTime.Now, S_GROUP_NO = endLocGroup.groupNo, }; if (WMSHelper.CreateWmsTask(wmsTask)) { // 创建一段入库任务 WCSTask wcsTask = new WCSTask() { S_OP_NAME = wmsTask.S_OP_DEF_NAME, S_OP_CODE = wmsTask.S_CODE, S_CODE = WCSHelper.GenerateTaskNo(), S_CNTR_CODE = wmsTask.S_CNTR_CODE, S_TYPE = wmsTask.S_TYPE, S_START_LOC = startLoc.S_CODE, S_START_AREA = startLoc.S_AREA_CODE, S_END_LOC = endLoc.S_CODE, S_END_AREA = endLoc.S_AREA_CODE, S_SCHEDULE_TYPE = "WCS", N_PRIORITY = 1, T_START_TIME = DateTime.Now, }; if (WCSHelper.CreateTask(wcsTask)) { // 起点、接驳点、终点加锁 LocationHelper.LockLoc(wcsTask.S_START_LOC, 2); LocationHelper.LockLoc(wcsTask.S_END_LOC, 1); // 更新作业任务状态 wmsTask.N_B_STATE = 1; WMSHelper.UpdateTaskState(wmsTask); } } } } else { response.code = 1; response.msg = "库区没有可入的空货位"; } } return response; } /// /// 呼叫空托出库 /// /// public static ResponseResult callEmptyTrayOutStock(NotifyDeviceSignalModel model) { ResponseResult responseResult = new ResponseResult(); int executeNum = 0; string startLocCode = null; for (int i = 1; i <= 2; i++) { Location startLoc = WMSHelper.getOutStockStartLoc(startLocCode); if (startLoc != null) { startLocCode = startLoc.S_CODE; Location endLoc = WMSHelper.getMinTaskMiddleLoc(1, 0, startLoc.N_ROADWAY); if (endLoc != null) { var locCntrRels = LocationHelper.GetLocCntr(startLoc.S_CODE); if (locCntrRels != null && locCntrRels.Count > 0) { var wmsTask = new WMSTask() { S_CNTR_CODE = locCntrRels[0].S_CNTR_CODE, S_CODE = WMSHelper.GenerateTaskNo(), S_START_LOC = startLoc.S_CODE, S_START_AREA = startLoc.S_AREA_CODE, S_END_LOC = endLoc.S_CODE, S_END_AREA = endLoc.S_AREA_CODE, S_TYPE = "呼叫空托出库", S_OP_DEF_CODE = model.reqId, S_OP_DEF_NAME = "呼叫空托出库", N_PRIORITY = 1, T_START_TIME = DateTime.Now }; if (WMSHelper.CreateWmsTask(wmsTask)) { // 创建一段入库任务 WCSTask wcsTask = new WCSTask() { S_OP_NAME = wmsTask.S_OP_DEF_NAME, S_OP_CODE = wmsTask.S_CODE, S_CODE = WCSHelper.GenerateTaskNo(), S_CNTR_CODE = wmsTask.S_CNTR_CODE, S_TYPE = wmsTask.S_TYPE, S_START_LOC = startLoc.S_CODE, S_START_AREA = startLoc.S_AREA_CODE, S_END_LOC = endLoc.S_CODE, S_END_AREA = endLoc.S_AREA_CODE, S_SCHEDULE_TYPE = "WCS", N_PRIORITY = 1, T_START_TIME = DateTime.Now, }; if (WCSHelper.CreateTask(wcsTask)) { // 起点、接驳点、终点加锁 LocationHelper.LockLoc(wcsTask.S_START_LOC, 2); LocationHelper.LockLoc(wcsTask.S_END_LOC, 1); // 更新作业任务状态 wmsTask.N_B_STATE = 1; WMSHelper.UpdateTaskState(wmsTask); executeNum += 1; } } } } } } if (executeNum < 1) { responseResult.code = 1; responseResult.msg = "立库内空托盘数量不足"; } return responseResult; } /// /// 胚胎抽检出库 /// /// public static SimpleResult embryoCheckOutStock(EmbryoCheckOutStockModel model) { SimpleResult result = new SimpleResult(); var locCntrs = LocationHelper.GetLocCntrRelByCntr(model.trayCode); if (locCntrs.Count == 1) { Location startLoc = LocationHelper.GetLoc(locCntrs[0].S_LOC_CODE); var connectLoc = Settings.connectLocList.Where(a => a.roadway == startLoc.N_ROADWAY).First(); Location middleLoc = LocationHelper.GetLoc(connectLoc.locCode); Location endLoc = LocationHelper.GetLoc(""); if (endLoc != null) { var wmsTask = new WMSTask() { S_CNTR_CODE = model.trayCode, S_CODE = WMSHelper.GenerateTaskNo(), S_START_LOC = startLoc.S_CODE, S_START_AREA = startLoc.S_AREA_CODE, S_END_LOC = endLoc.S_CODE, S_END_AREA = endLoc.S_AREA_CODE, S_TYPE = "胚胎抽检出库任务", S_OP_DEF_CODE = model.reqId, S_OP_DEF_NAME = "胚胎抽检出库出库任务", N_PRIORITY = 1, T_START_TIME = DateTime.Now, }; if (WMSHelper.CreateWmsTask(wmsTask)) { // 创建一段入库任务 WCSTask wcsTask = new WCSTask() { S_OP_NAME = wmsTask.S_OP_DEF_NAME, S_OP_CODE = wmsTask.S_CODE, S_CODE = WCSHelper.GenerateTaskNo(), S_CNTR_CODE = wmsTask.S_CNTR_CODE, S_TYPE = wmsTask.S_TYPE, S_START_LOC = startLoc.S_CODE, S_START_AREA = startLoc.S_AREA_CODE, S_END_LOC = middleLoc.S_CODE, S_END_AREA = middleLoc.S_AREA_CODE, S_SCHEDULE_TYPE = "WCS", N_PRIORITY = 1, T_START_TIME = DateTime.Now, }; if (WCSHelper.CreateTask(wcsTask)) { // 起点、接驳点、终点加锁 LocationHelper.LockLoc(wcsTask.S_START_LOC, 2); LocationHelper.LockLoc(wcsTask.S_END_LOC, 1); // 更新作业任务状态 wmsTask.N_B_STATE = 1; WMSHelper.UpdateTaskState(wmsTask); } } } } return result; } /// /// 异常托盘回库流程 /// /// /// public static ResponseResult anomalyTrayInStock(NotifyDeviceSignalModel model) { ResponseResult responseResult = new ResponseResult(); LocationHelper.UnBindingLoc(model.loc, new List() { model.cntrNo }); ContainerHelper.deleteCntrItemRelByCntr(model.cntrNo); return responseResult; } /// /// 任务状态回报 /// 任务状态 1:开始/执行中;完成;3:准备取货;4:取货完成;5:准备卸货;6:卸货完成;7:异常取消;8:强制完成 /// 1.根据任务状态回报更新货位状态、任务状态 /// 2.更新任务中间表状态 /// 4.更新出库任务中间表状态 /// /// /// public static ReturnResult taskStatusFeedback(TaskStatusFeedbackModel model) { ReturnResult responseResult = new ReturnResult(); WCSTask cst = WCSHelper.GetTask(model.taskNo); if (cst != null) { bool isExist = WCSHelper.CheckActionRecordExist(cst.S_CODE, model.status); if (!isExist) { WMSTask mst = WMSHelper.GetWmsTask(cst.S_OP_CODE); if (mst != null) { switch (model.status) { case 1: WCSHelper.Begin(cst); break; case 2: WCSHelper.End(cst); break; case 3: WCSHelper.UpdateStatus(cst, "准备取货"); break; case 4: WCSHelper.UpdateStatus(cst, "取货完成"); TaskProcess.OperateStatus(cst, 4); break; case 5: WCSHelper.UpdateStatus(cst, "准备卸货"); break; case 6: WCSHelper.UpdateStatus(cst, "卸货完成"); TaskProcess.OperateStatus(cst, 6); break; case 7: WCSHelper.Cancel(cst); WCSHelper.UpdateStatus(cst, "取消"); TaskProcess.OperateStatus(cst, 7); break; case 8: WCSHelper.UpdateStatus(cst, "强制完成"); WCSHelper.End(cst); break; } // 添加WCS动作记录 WCSHelper.AddActionRecord(model.taskNo, model.status, model.deviceNo, model.loc); if (model.status == 2 || model.status == 8) { if (mst != null && mst.N_B_STATE != 2) { if (mst.S_END_LOC != cst.S_END_LOC) { WCSCore.createLastTask(cst.S_END_LOC, mst); } else { mst.N_B_STATE = 2; WMSHelper.UpdateTaskState(mst); } if (mst.S_TYPE == "呼叫空托出库") { LocationHelper.UnBindingLoc(mst.S_END_LOC, new List() { mst.S_CNTR_CODE }); } } } } } } return responseResult; } /// /// 查询班次 /// /// /// public static string getShift(TimeSpan time) { TimeSpan shiftI_Start = new TimeSpan(07, 00, 0); // 07:00:00 TimeSpan shiftI_End = new TimeSpan(14, 59, 59); // 14:59:59 TimeSpan shiftII_Start = new TimeSpan(15, 00, 0); // 15:00:00 TimeSpan shiftII_End = new TimeSpan(22, 59, 59); // 22:59:59 TimeSpan shiftIII_Start = new TimeSpan(23, 00, 0); // 23:00:00 TimeSpan shiftIII_End = new TimeSpan(06, 59, 59); // 06:59:59 // 判断是否在 Shift III(跨天需特殊处理) bool isShiftIII = time >= shiftIII_Start || time <= shiftIII_End; // 返回结果 if (time >= shiftI_Start && time <= shiftI_End) return "I"; else if (time >= shiftII_Start && time <= shiftII_End) return "II"; else if (isShiftIII) return "III"; else return "No shift"; // 理论上不会触发 } /// /// 空托解绑 /// public static ReturnResult emptyTrayUnBind(EmptyTrayUnBindModel model) { ReturnResult responseResult = new ReturnResult(); ContainerHelper.deleteCntrItemRelByCntr(model.rfid); return responseResult; } public class readCodeFeedbackResponse { public bool verifyResult { get; set; } public string endLoc { get; set; } } /// /// 创建任务 /// /// internal static void AddTask(AddTaskModel model) { if (!WCSHelper.CheckExist(model.No)) { if (LocationHelper.CheckExist(model.From) && LocationHelper.CheckExist(model.To)) { WCSHelper.CreateTask(model.No, model.From, model.To, "搬运", 99, ""); } } } /// /// 创建入库单主子表 /// /// /// internal static SimpleResult Putaway_Order_In(Putaway_Order_In model) { var result = new SimpleResult(); //创建入库单主子表 var po = WMSHelper.GetPutawayOrder(model.Data.arrival_no); if (po == null) { po = new PutawayOrder { S_NO = model.Data.arrival_no, S_BS_TYPE = model.Data.op_type }; po.Details = new List(); if (model.Data.items.Count > 0) { model.Data.items.ForEach(a => { po.Details.Add(new PutawayDetail { S_PUTAWAY_NO = model.Data.arrival_no, N_ROW_NO = po.Details.Count + 1, S_ITEM_CODE = a.item_code, F_QTY = a.qty, S_BATCH_NO = a.batch_no, }); }); WMSHelper.CreatePutawayOrder(po); } } return result; } /// /// 创建发货单主子表 /// /// /// internal static SimpleResult OutboundOrder(OutboundOrder model) { var result = new SimpleResult(); //创建发货单,人工点确认后生成分拣单,没有缺货的自动更新为失败,有货的更新为执行中 //创建出库单主子表 var po = WMSHelper.GetShippingOrder(model.Data.out_no); if (po == null) { po = new ShippingOrder { S_NO = model.Data.out_no, S_BS_TYPE = model.Data.op_type }; po.Details = new List(); if (model.Data.items.Count > 0) { model.Data.items.ForEach(a => { po.Details.Add(new ShippingDetail { S_SHIPPING_NO = model.Data.out_no, N_ROW_NO = po.Details.Count + 1, S_ITEM_CODE = a.item_code, F_QTY = a.qty, S_BATCH_NO = a.batch_no, }); }); WMSHelper.CreateShippingOrder(po); } } return result; } public static List> cacheInstockInfos = new List>(); public static void addKeyValuePair(string ip , InstockInfo instockInfo) { KeyValuePair pair = new KeyValuePair(ip,instockInfo); LogHelper.Info("添加缓存信号,缓存信息:" + JsonConvert.SerializeObject(pair), "TSSG"); // 查找并替换键值对 bool replaced = false; for (int i = 0; i < cacheInstockInfos.Count; i++) { if (cacheInstockInfos[i].Key == pair.Key) { cacheInstockInfos[i] = pair; replaced = true; LogHelper.Info("存在相同IP的缓存信号,替换缓存信息:" + JsonConvert.SerializeObject(pair), "TSSG"); break; // 如果只需要替换第一个匹配的项,就跳出循环 } } // 如果没有找到要替换的项,可以选择添加新的键值对或执行其他操作 if (!replaced) { cacheInstockInfos.Add(pair); } } internal static CodeInfo GetCodeInfo(string code, string org) { //return new CodeInfo { Fitemid_XK=code, FSourceNo="123456"}; CodeInfo result = null; try { var db = new SqlHelper().GetInstance(Settings.SqlServer1); var nameP = new SugarParameter("@FBarCode", code); var orgP = new SugarParameter("@Forg", org); //var ageP = new SugarParameter("@age", null, true);//设置为output //var dt = db.Ado.UseStoredProcedure().GetDataTable("sp_school", nameP, ageP);//返回dt result = db.Ado.UseStoredProcedure().SqlQuery("WMS_FBarCode", nameP, orgP).First();//返回List Console.WriteLine($"读存储过程成功,result={result}"); } catch (Exception ex) { Console.WriteLine(ex.Message); } return result; } /// /// agv 车辆报警 /// /// /// /// /// public static void agvCarAlarm(string forkliftNo, string errCode , string errCode2 , string failCode) { bool turnLight = false; } public class OffLineModel { public int isUrgent { get; set; } // N_IS_URGENT 是否加急(0.否 1.是) public int isFull { get; set; } // 是否满拖 0.否 1.是 public int needPair { get; set; } // 0.否 1.是(当前空托盘为配对托盘) } public class AddTaskModel { public string From { get; set; } public string To { get; set; } public string No { get; set; } } public class TN_LocationModel { public string TN_Location { get; set; } } public class CodeInfo { /// /// 生产订单内码 /// public string FInterID { get; set; } /// /// 生产订单编号 /// public string FSourceNo { get; set; } /// /// 批号 /// public string FGMPBatchNo { get; set; } public string FState { get; set; } /// /// 物料编码(内码就是编码) /// public string Fitemid_XK { get; set; } /// /// 分录id /// public string Fentryid { get; set; } } public class NoteInfo : CodeInfo { public string WmsBillNo { get; set; } } } }