using Newtonsoft.Json.Serialization; using Newtonsoft.Json; using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks; using WIDESEA_Common.APIEnum; using WIDESEA_Common.CommonEnum; using WIDESEA_Common.LocationEnum; using WIDESEA_Common.OtherEnum; using WIDESEA_Common.StockEnum; using WIDESEA_Common.TaskEnum; using WIDESEA_Common.WareHouseEnum; using WIDESEA_Core; using WIDESEA_Core.BaseServices; using WIDESEA_Core.Enums; using WIDESEA_Core.Helper; using WIDESEA_DTO; using WIDESEA_DTO.ERP; using WIDESEA_DTO.MES; using WIDESEA_ITaskInfoRepository; using WIDESEA_ITaskInfoService; using WIDESEA_Model.Models; using WIDESEA_Common.OrderEnum; namespace WIDESEA_TaskInfoService { public partial class TaskService { static object lock_out = new object(); /// /// 测试架出仓 /// /// /// public MesResponseContent TestToolOut(TestToolOutModel model) { lock (lock_out) { MesResponseContent responseContent = new MesResponseContent(); try { Dt_Task exsit = Repository.QueryFirst(x => x.TargetAddress == model.TargetAddressCode); if (exsit != null) { return responseContent.Error($"目标地址重复"); } Dt_Warehouse warehouse = _basicRepository.WarehouseRepository.QueryFirst(x => x.WarehouseCode == WarehouseEnum.HA64.ToString()); //获取库存记录 List stockInfos = _stockRepository.StockInfoRepository.Db.Queryable().Where(x => x.WarehouseId == warehouse.WarehouseId && x.StockStatus == (int)StockStatusEmun.入库完成).Includes(x => x.Details).ToList(); Dt_StockInfo? stockInfo = stockInfos.FirstOrDefault(x => x.Details.Any(x => x.BatchNo == model.ToolCode)); if (stockInfo == null) { return responseContent.Error($"测试架:{model.ToolCode}无可用库存"); } Dt_Task exsit2 = Repository.QueryFirst(x => x.PalletCode == stockInfo.PalletCode); if (exsit2 != null) { return responseContent.Error($"测试架批次号重复"); } Dt_LocationInfo locationInfo = _basicService.LocationInfoService.Repository.QueryFirst(x => x.LocationCode == stockInfo.LocationCode && x.WarehouseId == stockInfo.WarehouseId && x.LocationStatus == (int)LocationStatusEnum.InStock && (x.EnableStatus == (int)EnableStatusEnum.Normal || x.EnableStatus == (int)EnableStatusEnum.OnlyOut)); if (locationInfo == null) { return responseContent.Error($"测试架货位:{stockInfo.LocationCode}出库条件不满足"); } //生成测试架出库任务 锁定库存 更改货位状态 Dt_Task taskOut = new() { CurrentAddress = stockInfo.LocationCode, Grade = 0, PalletCode = stockInfo.PalletCode, NextAddress = "", Roadway = locationInfo.RoadwayNo, SourceAddress = stockInfo.LocationCode, TargetAddress = model.TargetAddressCode, TaskStatus = (int)TaskStatusEnum.New, TaskType = (int)TaskTypeEnum.Outbound, TaskNum = BaseDal.GetTaskNum(nameof(SequenceEnum.SeqTaskNum)), PalletType = stockInfo.PalletType, WarehouseId = stockInfo.WarehouseId, }; stockInfo.StockStatus = (int)StockStatusEmun.出库锁定; LocationStatusEnum locationStatus = (LocationStatusEnum)locationInfo.LocationStatus; locationInfo.LocationStatus = (int)LocationStatusEnum.Lock; //判断是否有出库单信息 _unitOfWorkManage.BeginTran(); //更新库存状态 _stockRepository.StockInfoRepository.UpdateData(stockInfo); //更新货位状态 _basicService.LocationInfoService.UpdateLocationStatus(locationInfo, stockInfo.PalletType, LocationStatusEnum.Lock, stockInfo.WarehouseId); //新建任务 BaseDal.AddData(taskOut); //加入货位变动记录 _recordService.LocationStatusChangeRecordSetvice.AddLocationStatusChangeRecord(locationInfo, locationStatus, LocationStatusEnum.Lock, LocationChangeType.OutboundAssignLocation, stockInfo.Details.FirstOrDefault()?.OrderNo ?? "", taskOut.TaskNum); _unitOfWorkManage.CommitTran(); //将任务推送到WCS PushTasksToWCS(new List() { taskOut }, "AGV_CSJ"); responseContent.OK(); } catch (Exception ex) { _unitOfWorkManage.RollbackTran(); responseContent.Error(ex.Message); } return responseContent; } } /// /// 测试架退库 /// /// public MesResponseContent TestToolBack(TestToolBackModel backModel) { MesResponseContent responseContent = new MesResponseContent(); try { //获取测试架原库存信息 Dt_Warehouse warehouse = _basicRepository.WarehouseRepository.QueryFirst(x => x.WarehouseCode == WarehouseEnum.HA64.ToString()); //获取库存记录 List stockInfos = _stockRepository.StockInfoRepository.Db.Queryable().Where(x => x.WarehouseId == warehouse.WarehouseId && x.StockStatus == (int)StockStatusEmun.出库完成).Includes(x => x.Details).ToList(); Dt_StockInfo? stockInfo = stockInfos.FirstOrDefault(x => x.Details.Any(x => x.BatchNo == backModel.TestToolCode)); if (stockInfo == null) { return responseContent.Error($"{backModel.TestToolCode}库存信息不存在"); } //生成退库任务 Dt_Task taskIn = new() { CurrentAddress = backModel.SourceAddressCode, Grade = 0, PalletCode = stockInfo.PalletCode, NextAddress = "", Roadway = "", SourceAddress = backModel.SourceAddressCode, TargetAddress = "", TaskStatus = (int)TaskStatusEnum.New, TaskType = (int)TaskTypeEnum.ProductionReturn, TaskNum = BaseDal.GetTaskNum(nameof(SequenceEnum.SeqTaskNum)), PalletType = stockInfo.PalletType, WarehouseId = stockInfo.WarehouseId, }; //更改库存状态 stockInfo.StockStatus = StockStatusEmun.退库.ObjToInt(); BaseDal.AddData(taskIn); _stockRepository.StockInfoRepository.UpdateData(stockInfo); //将任务推送到WCS PushTasksToWCS(new List() { taskIn }, "AGV_CSJ"); ; responseContent.OK(); } catch (Exception ex) { _unitOfWorkManage.RollbackTran(); responseContent.Error(ex.Message); } return responseContent; } /// /// 测试架报废 /// /// public MesResponseContent TestScrap(TestToolScrap toolScraps) { MesResponseContent responseContent = new MesResponseContent(); try { //获取测试架批次号库存 Dt_Warehouse warehouse = _basicRepository.WarehouseRepository.QueryFirst(x => x.WarehouseCode == WarehouseEnum.HA64.ToString()); //获取库存记录 List stockInfos = _stockRepository.StockInfoRepository.Db.Queryable().Where(x => x.WarehouseId == warehouse.WarehouseId && x.StockStatus == (int)StockStatusEmun.出库完成).Includes(x => x.Details).ToList(); List stockInfoUpdates = new List(); List stockInfoDetails = new List(); foreach (var item in toolScraps.ToolCodes) { Dt_StockInfo? stockInfo = stockInfos.FirstOrDefault(x => x.Details.Any(x => x.BatchNo == item)); if (stockInfo == null) { return responseContent.Error($"{item}库存信息不存在"); } stockInfoUpdates.Add(stockInfo); stockInfoDetails.Add(stockInfo.Details.FirstOrDefault()); } //清除库存信息 _unitOfWorkManage.BeginTran(); _stockRepository.StockInfoRepository.DeleteAndMoveIntoHty(stockInfoUpdates, OperateTypeEnum.自动删除); _stockService.StockInfoDetailService.Repository.DeleteAndMoveIntoHty(stockInfoDetails, OperateTypeEnum.自动删除); _unitOfWorkManage.CommitTran(); responseContent.OK($"报废成功"); } catch (Exception ex) { _unitOfWorkManage.RollbackTran(); responseContent.Error(ex.Message); } return responseContent; } /// /// 同步测试架寿命 /// /// /// public WebResponseContent TestSynStock(TestToolSynInfo toolSynInfo) { WebResponseContent content = new WebResponseContent(); try { Dt_ApiInfo apiInfo = _apiInfoRepository.QueryFirst(x => x.ApiCode == APIEnum.WMS_MES_TestToolSync.ToString()); MESRoot root = new MESRoot() { From = "WMS", DateTime = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss"), Content = toolSynInfo }; JsonSerializerSettings settings = new JsonSerializerSettings { ContractResolver = new CamelCasePropertyNamesContractResolver() }; string request = JsonConvert.SerializeObject(root, settings); string response = HttpMesHelper.Post(apiInfo.ApiAddress, request); MesResponseContent mesResponseContent = response.DeserializeObject(); //调用接口 if (mesResponseContent.BSucc == true) { content.OK(mesResponseContent.StrMsg); } else { content.Error(mesResponseContent.StrMsg); } } catch (Exception ex) { content.Error(ex.Message); } return content; } /// /// 物料出库,WMS同步出库物料批次至MES /// /// /// public WebResponseContent UploadMesMaterialLotaAcept(MesMaterialLotaAceptModel model) { WebResponseContent content = new WebResponseContent(); try { Dt_ApiInfo apiInfo = _apiInfoRepository.QueryFirst(x => x.ApiCode == APIEnum.WMS_MES_MaterialLotaAcept.ToString()); MESRoot root = new MESRoot() { From = "WMS", DateTime = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss"), Content = model }; JsonSerializerSettings settings = new JsonSerializerSettings { ContractResolver = new CamelCasePropertyNamesContractResolver() }; string request = JsonConvert.SerializeObject(root, settings); string response = HttpMesHelper.Post(apiInfo.ApiAddress, request); MesResponseContent mesResponseContent = response.DeserializeObject(); //调用接口 if (mesResponseContent.BSucc == true) { content.OK(mesResponseContent.StrMsg); } else { content.Error(mesResponseContent.StrMsg); } } catch (Exception ex) { content.Error(ex.Message); } return content; } /// /// /// /// /// /// /// /// /// /// /// public MesMaterialLotaAceptModel GetMesMaterialLotaAceptModel(Dt_StockInfo stockInfo, Dt_StockInfoDetail stockInfoDetail, string taskNo, string warehouseCode, float quantity, string cutedType = "", float ppWidth = 0) { MesMaterialLotaAceptModel model = new MesMaterialLotaAceptModel() { CarrierCode = stockInfo.PalletCode, CutedType = cutedType, ExpirationDate = stockInfoDetail.EffectiveDate, MaterialBarCode = stockInfoDetail.SerialNumber, MaterialCode = stockInfoDetail.MaterielCode, MaterialLot = stockInfoDetail.MaterielCode + "," + stockInfoDetail.BatchNo, MaterialName = stockInfoDetail.MaterielName, PPWidth = ppWidth, ProductionDate = stockInfoDetail.ProductionDate, Quantity = quantity, Supplier = "", TaskNo = taskNo, Type = 1, WarehouseArea = warehouseCode, WarehouseLocation = warehouseCode }; return model; } /// /// 基板出库 /// /// /// public MesResponseContent SubstrateOut(SubstrateOutModel model) { try { Dt_Warehouse warehouse = _basicRepository.WarehouseRepository.QueryFirst(x => x.WarehouseCode == WarehouseEnum.HA57.ToString()); if (warehouse == null) { return MesResponseContent.Instance.Error($"仓库基础信息未配置"); } Dt_MaterielInfo materielInfo = _basicRepository.MaterielInfoRepository.QueryFirst(x => x.MaterielCode == model.MaterialCode); if (materielInfo == null) { return MesResponseContent.Instance.Error($"未找到该物料信息"); } Dt_MesOutboundOrder mesOutboundOrder = new Dt_MesOutboundOrder() { CreateType = OrderCreateTypeEnum.UpperSystemPush.ObjToInt(), Line = model.Line, MaterialCode = model.MaterialCode, MaterialName = model.MaterialName, OrderQuantity = model.RequiredQuantity, TaskNo = model.TaskNo, Unit = model.Unit, OrderType = MesOutboundOrderTypeEnum.SubstrateOut.ObjToInt(), OrderStatus = OutOrderStatusEnum.未开始.ObjToInt(), WarehouseId = warehouse.WarehouseId }; List tasks = new List(); List? stockInfos = null; List? outStockLockInfos = null; List? locationInfos = null; { (List, Dt_MesOutboundOrder, List, List) result = _outboundService.MesOutboundOrderService.AssignStockOutbound(mesOutboundOrder); if (result.Item1 != null && result.Item1.Count > 0) { tasks = GetTasks(result.Item1, TaskTypeEnum.MesOutbound); result.Item2.OrderStatus = OrderDetailStatusEnum.Outbound.ObjToInt(); result.Item3.ForEach(x => { x.Status = OutLockStockStatusEnum.出库中.ObjToInt(); }); stockInfos = result.Item1; mesOutboundOrder = result.Item2; outStockLockInfos = result.Item3; locationInfos = result.Item4; } else { throw new Exception("无库存"); } } tasks.ForEach(x => { x.TargetAddress = model.Line; }); _unitOfWorkManage.BeginTran(); int id = BaseDal.AddData(tasks); outStockLockInfos.ForEach(x => { x.OrderNo = mesOutboundOrder.TaskNo; x.OrderDetailId = id; }); _outboundService.MesOutboundOrderService.Repository.AddData(mesOutboundOrder); if (stockInfos != null && stockInfos.Count > 0 && outStockLockInfos != null && outStockLockInfos.Count > 0 && locationInfos != null && locationInfos.Count > 0) { WebResponseContent content = _outboundService.MesOutboundOrderService.LockOutboundStockDataUpdate(stockInfos, outStockLockInfos, locationInfos, tasks: tasks); if (!content.Status) { _unitOfWorkManage.RollbackTran(); return MesResponseContent.Instance.Error(content.Message); } } _unitOfWorkManage.CommitTran(); PushTasksToWCS(tasks); return MesResponseContent.Instance.OK(); } catch (Exception ex) { return MesResponseContent.Instance.Error(ex.Message); } } /// /// 基板余料退库 /// /// /// public MesResponseContent SubstrateBack(SubstrateBackModel model) { try { Dt_PalletTypeInfo palletTypeInfo = _palletTypeInfoRepository.QueryFirst(x => model.CarrierCode.Contains(x.CodeStartStr)); if (palletTypeInfo == null) { return MesResponseContent.Instance.Error($"未识别该托盘类型,请确认托盘号"); } Dt_Warehouse warehouse = _basicRepository.WarehouseRepository.QueryFirst(x=>x.WarehouseCode == WarehouseEnum.HA57.ToString()); Dt_StockInfo_Hty stockInfo_Hty = _stockRepository.StockInfo_HtyRepository.QueryData(x=>x.PalletCode== model.CarrierCode).OrderByDescending(x=>x.SourceId).First(); Dt_StockInfoDetail_Hty stockInfoDetail_Hty = _stockRepository.StockInfoDetail_HtyRepository.QueryFirst(x => x.StockId==stockInfo_Hty.SourceId); Dt_StockInfoDetail stockInfoDetail = new Dt_StockInfoDetail() { BatchNo = stockInfoDetail_Hty?.BatchNo ?? "", EffectiveDate = model.ExpirationDate, MaterielCode = model.MaterialCode, InboundOrderRowNo = stockInfoDetail_Hty?.InboundOrderRowNo ?? 0, MaterielName = model.MaterialCode, ProductionDate = model.ProductionDate, OrderNo = stockInfoDetail_Hty?.OrderNo ?? "", OutboundQuantity = 0, SerialNumber = stockInfoDetail_Hty?.SerialNumber ?? "0", StockQuantity = model.Quantity, Status = StockStatusEmun.MES退库.ObjToInt(), Unit = model.Unit }; Dt_StockInfo stockInfo = new Dt_StockInfo() { PalletCode = model.CarrierCode, PalletType = palletTypeInfo.PalletType, WarehouseId = warehouse.WarehouseId, StockStatus = StockStatusEmun.MES退库.ObjToInt(), Details=new List { stockInfoDetail } }; //Dt_Task task = new Dt_Task() //{ // PalletCode = stockInfo.PalletCode, // CurrentAddress = "", // NextAddress = "", // PalletType = stockInfo.PalletType, // Roadway = "RGV01_BC", // SourceAddress = "RGV01_BC", // TargetAddress = "", // TaskStatus = TaskStatusEnum.New.ObjToInt(), // TaskType = TaskTypeEnum.MesMatReturn.ObjToInt(), // WarehouseId = warehouse.WarehouseId //}; _unitOfWorkManage.BeginTran(); Db.InsertNav(stockInfo).Include(x => x.Details).ExecuteCommand(); //BaseDal.AddData(task); _unitOfWorkManage.CommitTran(); return MesResponseContent.Instance.OK(); } catch (Exception ex) { _unitOfWorkManage.RollbackTran(); return MesResponseContent.Instance.Error(ex.Message); } } } }