123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611 |
- using Microsoft.AspNetCore.Mvc;
- using Newtonsoft.Json;
- using PlcSiemens.Core.Extension;
- using ServiceCenter;
- using ServiceCenter.Attributes;
- using ServiceCenter.Extensions;
- using ServiceCenter.Redis;
- using ServiceCenter.SqlSugars;
- using System.Net.NetworkInformation;
- using System.Text;
- using WCS.Core;
- using WCS.Entity;
- using WCS.Entity.Protocol.DataStructure;
- using WCS.Entity.Protocol.SRM;
- using WCS.WorkEngineering.Extensions;
- using WCS.WorkEngineering.Systems;
- using WCS.WorkEngineering.WebApi.Models.WCS.Request;
- using WCS.WorkEngineering.WebApi.Models.WCS.Response;
- using WCS.WorkEngineering.WebApi.Models.WMS.Response;
- namespace WCS.WorkEngineering.WebApi.Controllers
- {
- public interface IDeviceWriter
- {
- [HttpPost]
- void Write(DeviceTypeEnum deviceType, string devCode, string protocol, string propName, string value);
- }
- /// <summary>
- /// 设备Ip通讯检测结构
- /// </summary>
- public class DeviceIpTestResults
- {
- public string Ip { get; set; }
- public bool Result { get; set; }
- }
- /// <summary>
- /// WCS相关接口控制器
- /// </summary>
- [ApiController]
- [Route("api/[controller]/[action]")]
- public class WcsController : ControllerBase, IDeviceWriter
- {
- /// <summary>
- /// 获取设备信息
- /// </summary>
- /// <param name="type"></param>
- /// <param name="name">设备名称</param>
- /// <returns></returns>
- [HttpGet]
- public object GetDeviceInfo(string type, string name)
- {
- var obj = World.GetSystemInstance<GetDeviceSystem>().Invoke(new Tuple<string, string>(type, name));
- return obj;
- }
- /// <summary>
- /// 获取设备配置信息接口
- /// </summary>
- /// <returns></returns>
- [HttpGet]
- public List<Device> GetDeviceList()
- {
- return Device.All.ToList();
- }
- /// <summary>
- /// 设备信息写入接口
- /// </summary>
- [HttpPost]
- public void GetDevList()
- {
- var a = RedisHub.Monitor.LRange("Packs", 0, 80000);
- var packs = a.Select(JsonConvert.DeserializeObject<DeviceDataPack>).ToList();
- }
- /// <summary>
- /// 任务处理接口
- /// </summary>
- /// <param name="req"></param>
- /// <returns></returns>
- [HttpPost, Log("任务处理接口")]
- public SRes<HandleTaskResponse> HandleTask([FromBody] HandleTaskRequest req)
- {
- var response = new SRes<HandleTaskResponse>() { ResCode = ResponseStatusCodeEnum.Sucess, ResDataList = new List<HandleTaskResponse>() };
- switch (req.Type)
- {
- //取消任务
- case HandleTaskTypeEnum.取消任务:
- SqlSugarHelper.Do(db =>
- {
- foreach (var item in req.TaskIds)
- {
- var task = db.Default.Queryable<WCS_TaskInfo>().Where(t => t.ID == item).First();
- if (task != null)
- {
- //验证wms是否能取消
- var res = WmsApi.HandleTaskVerify(response, item, 106);
- if (res == null) continue;
- switch (task.Type)
- {
- case TaskType.SetPlate:
- if (task.Status != Entity.TaskStatus.WaitingToExecute)
- {
- response.ResDataList.Add(new HandleTaskResponse()
- {
- IsSuccess = false,
- TaskNo = item,
- Message = $"只能取消待执行状态组盘任务",
- });
- continue;
- }
- break;
- case TaskType.EnterDepot:
- if (task.Status > Entity.TaskStatus.WaitingToExecute && task.Status > Entity.TaskStatus.AGVExecution)
- {
- response.ResDataList.Add(new HandleTaskResponse()
- {
- IsSuccess = false,
- TaskNo = item,
- Message = $"只能取消待执行状态入库任务",
- });
- continue;
- }
- break;
- case TaskType.OutDepot:
- if (task.Status > Entity.TaskStatus.WaitingToExecute)
- {
- response.ResDataList.Add(new HandleTaskResponse()
- {
- IsSuccess = false,
- TaskNo = item,
- Message = $"只能取消待执行状态出库任务",
- });
- continue;
- }
- break;
- case TaskType.TransferDepot:
- if (task.Status > Entity.TaskStatus.WaitingToExecute)
- {
- response.ResDataList.Add(new HandleTaskResponse()
- {
- IsSuccess = false,
- TaskNo = item,
- Message = $"无法取消{task.Status.GetDescription()}的移库任务,只能取消新建/待执行的移库任务",
- });
- continue;
- }
- break;
- case TaskType.Delivery:
- break;
- case TaskType.EmptyInit:
- if (task.Status != Entity.TaskStatus.WaitingToExecute)
- {
- response.ResDataList.Add(new HandleTaskResponse()
- {
- IsSuccess = false,
- TaskNo = item,
- Message = $"只能取消待执行状态空轮初始化任务",
- });
- continue;
- }
- break;
- default:
- throw new ArgumentOutOfRangeException();
- }
- var cancelRes = WmsApi.CarryTaskInfo(response, item, 106);
- if (cancelRes == null) continue;
- //找到对应的AGV任务
- var agv = db.Default.Queryable<WCS_AgvTaskInfo>().Where(v => v.ID == task.AgvTaskID && v.AgvStatus < AGVTaskStatus.MissionCompleted).SplitTable(v => v.Take(2)).First();
- if (agv != null)
- {
- if (!agv.AgvID.IsNullOrEmpty())
- {
- var cancelTaskUpdateRes = AgvApi.CancelAgvTask(response, item, agv.AgvID);
- //if (cancelTaskUpdateRes == null) continue;
- }
- agv.Status = AGVTaskStatus.Cancel;
- agv.AgvStatus = AGVTaskStatus.Cancel;
- db.Default.Updateable(agv).SplitTable(x=>x.Take(2)).ExecuteCommand();
- }
- //更新任务状态
- task.Status = Entity.TaskStatus.Cancel;
- task.EedTime = DateTime.Now;
- task.EditWho = req.User;
- task.ManualRemarks = req.ManualRemarks;
- db.Default.Updateable(task).ExecuteCommand();
- task.AddWCS_TASK_DTL(db.Default, "未知", "任务取消");
- }
- else
- {
- response.ResDataList.Add(new HandleTaskResponse()
- {
- IsSuccess = false,
- TaskNo = item,
- Message = $"未找到对应任务{item}"
- });
- }
- }
- });
- break;
- // 完成任务
- case HandleTaskTypeEnum.完成任务:
- SqlSugarHelper.Do(db =>
- {
- foreach (var item in req.TaskIds)
- {
- var task = db.Default.Queryable<WCS_TaskInfo>().Where(t => t.ID == item).First();
- if (task == null) continue;
- switch (task.Type)
- {
- case TaskType.OutDepot:
- {
- var res = WmsApi.HandleTaskVerify(response, item, 99);
- if (res == null) continue;
- switch (task.Type)
- {
- case TaskType.OutDepot:
- if (task.Status >= Entity.TaskStatus.Finish)
- {
- response.ResDataList.Add(new HandleTaskResponse()
- {
- IsSuccess = false,
- TaskNo = item,
- Message = $"只能完成未完成状态的任务",
- });
- continue;
- }
- break;
- case TaskType.SetPlate:
- break;
- case TaskType.EnterDepot:
- break;
- case TaskType.TransferDepot:
- break;
- case TaskType.Delivery:
- break;
- case TaskType.EmptyInit:
- break;
- default:
- throw new ArgumentOutOfRangeException();
- }
- var cancelRes = WmsApi.CarryTaskInfo(response, item, 99);
- if (cancelRes == null) continue;
- //找到对应的AGV任务
- var agv = db.Default.Queryable<WCS_AgvTaskInfo>().Where(v => v.ID == task.AgvTaskID && v.AgvStatus < AGVTaskStatus.MissionCompleted).SplitTable(v => v.Take(2)).First();
- if (agv != null)
- {
- //if (!agv.AgvID.IsNullOrEmpty())
- //{
- // var cancelTaskUpdateRes = CancelAgvTask(response, item, agv.AgvID);
- // if (cancelTaskUpdateRes == null) continue;
- //}
- agv.Status = AGVTaskStatus.MissionCompleted;
- agv.AgvStatus = AGVTaskStatus.MissionCompleted;
- db.Default.Updateable(agv).SplitTable(x=>x.Take(2)).ExecuteCommand();
- }
- //更新任务状态
- task.Status = Entity.TaskStatus.Finish;
- task.EedTime = DateTime.Now;
- task.EditWho = req.User;
- task.ManualRemarks = req.ManualRemarks;
- db.Default.Updateable(task).ExecuteCommand();
- task.AddWCS_TASK_DTL(db.Default, "未知", "任务完成");
- break;
- }
- case TaskType.EnterDepot:
- {
- var res = WmsApi.HandleTaskVerify(response, item, 99);
- if (res == null) continue;
- switch (task.Type)
- {
- case TaskType.EnterDepot:
- if (task.Status >= Entity.TaskStatus.Finish)
- {
- response.ResDataList.Add(new HandleTaskResponse()
- {
- IsSuccess = false,
- TaskNo = item,
- Message = $"只能完成未完成状态的任务",
- });
- continue;
- }
- if (task.AddrTo.Length < 6)
- {
- response.ResDataList.Add(new HandleTaskResponse()
- {
- IsSuccess = false,
- TaskNo = item,
- Message = $"只能完成已分配货位的任务",
- });
- continue;
- }
- break;
- case TaskType.SetPlate:
- break;
- case TaskType.OutDepot:
- break;
- case TaskType.TransferDepot:
- break;
- case TaskType.Delivery:
- break;
- case TaskType.EmptyInit:
- break;
- default:
- throw new ArgumentOutOfRangeException();
- }
- var cancelRes = WmsApi.CarryTaskInfo(response, item, 99);
- if (cancelRes == null) continue;
- //找到对应的AGV任务
- var agv = db.Default.Queryable<WCS_AgvTaskInfo>().Where(v => v.ID == task.AgvTaskID && v.AgvStatus < AGVTaskStatus.MissionCompleted).SplitTable(v => v.Take(2)).First();
- if (agv != null)
- {
- //if (!agv.AgvID.IsNullOrEmpty())
- //{
- // var cancelTaskUpdateRes = CancelAgvTask(response, item, agv.AgvID);
- // if (cancelTaskUpdateRes == null) continue;
- //}
- agv.Status = AGVTaskStatus.MissionCompleted;
- agv.AgvStatus = AGVTaskStatus.MissionCompleted;
- db.Default.Updateable(agv).SplitTable(x=>x.Take(2)).ExecuteCommand();
- }
- //更新任务状态
- task.Status = Entity.TaskStatus.Finish;
- task.EedTime = DateTime.Now;
- task.EditWho = req.User;
- task.ManualRemarks = req.ManualRemarks;
- db.Default.Updateable(task).ExecuteCommand();
- task.AddWCS_TASK_DTL(db.Default, "未知", "任务完成");
- break;
- }
- case TaskType.SetPlate:
- case TaskType.TransferDepot:
- case TaskType.Delivery:
- case TaskType.EmptyInit:
- default:
- response.ResDataList.Add(new HandleTaskResponse()
- {
- IsSuccess = false,
- TaskNo = item,
- Message = $"未找到对应任务{item}"
- });
- break;
- }
- }
- });
- break;
- case HandleTaskTypeEnum.重新下发AGV任务:
- SqlSugarHelper.Do(db =>
- {
- foreach (var item in req.TaskIds)
- {
- var task = db.Default.Queryable<WCS_TaskInfo>().Where(t => t.ID == item).First();
- if (task != null)
- {
- switch (task.Type)
- {
- //组盘任务
- case TaskType.SetPlate:
- response.ResDataList.Add(new HandleTaskResponse()
- {
- IsSuccess = false,
- TaskNo = item,
- Message = $"组盘任务无AGV执行流程",
- });
- continue;
- //入库任务
- //一楼入库
- case TaskType.EnterDepot when task.Floor == 1:
- break;
- //二楼入库
- case TaskType.EnterDepot when task.Floor == 2:
- response.ResDataList.Add(new HandleTaskResponse()
- {
- IsSuccess = false,
- TaskNo = item,
- Message = $"二楼入库任务重新下发AGV未实现",
- });
- continue;
- //出库
- case TaskType.OutDepot:
- break;
- //移库
- case TaskType.TransferDepot:
- response.ResDataList.Add(new HandleTaskResponse()
- {
- IsSuccess = false,
- TaskNo = item,
- Message = $"组盘任务无AGV执行流程",
- });
- continue;
- //搬运
- case TaskType.Delivery when task.Floor == 1:
- break;
- case TaskType.Delivery when task.Floor == 2:
- response.ResDataList.Add(new HandleTaskResponse()
- {
- IsSuccess = false,
- TaskNo = item,
- Message = $"二楼搬运任务重新下发AGV未实现",
- });
- continue;
- //空轮初始化
- case TaskType.EmptyInit:
- response.ResDataList.Add(new HandleTaskResponse()
- {
- IsSuccess = false,
- TaskNo = item,
- Message = $"空轮初始化无AGV执行流程",
- });
- continue;
- }
- //找到对应的AGV任务
- var agv = db.Default.Queryable<WCS_AgvTaskInfo>().Where(v => v.ID == task.AgvTaskID).SplitTable(v => v.Take(2)).First();
- if (agv != null)
- {
- agv.Status = AGVTaskStatus.NewBuild;
- agv.AgvStatus = AGVTaskStatus.NewBuild;
- db.Default.Updateable(agv).SplitTable(x=>x.Take(2)).ExecuteCommand();
- }
- task.Status = task.Floor switch
- {
- 1 => Entity.TaskStatus.WaitingToExecute,
- 2 => Entity.TaskStatus.ConveyorExecution,
- _ => task.Status
- };
- task.AddWCS_TASK_DTL(db.Default, "AGV", "重新下发AGV任务");
- db.Default.Updateable(task).ExecuteCommand();
- }
- else
- {
- response.ResDataList.Add(new HandleTaskResponse()
- {
- IsSuccess = false,
- TaskNo = item,
- Message = $"未找到对应任务{item}"
- });
- }
- }
- });
- break;
- case HandleTaskTypeEnum.调整优先级:
- break;
- default:
- throw new ArgumentOutOfRangeException();
- }
- return response;
- }
- /// <summary>
- /// 堆垛机测试
- /// </summary>
- /// <param name="srmcod">堆垛机编号</param>
- /// <param name="typeEnum">任务类型</param>
- /// <param name="value1">起始行</param>
- /// <param name="value2">起始列</param>
- /// <param name="value3">起始层</param>
- /// <param name="value4">目标行</param>
- /// <param name="value5">目标列</param>
- /// <param name="value6">目标层</param>
- [HttpPost]
- public void SrmDeBug(string srmcod, SrmTaskType typeEnum, short value1, short value2, short value3, short value4, short value5, short value6)
- {
- World.GetSystemInstance<SrmDebugSystem>().Invoke(new SrmDebugInfo
- {
- SrmCode = srmcod,
- srmTaskType = typeEnum,
- SLine = value1,
- SCol = value2,
- SLayer = value3,
- ELine = value4,
- ECol = value5,
- ELayer = value6
- });
- }
- /// <summary>
- /// 设备信息写入接口
- /// </summary>
- /// <param name="deviceType">需要写入信息的设备类型</param>
- /// <param name="devCode">设备编号</param>
- /// <param name="protocol">设备协议类名</param>
- /// <param name="propName">写入字段名</param>
- /// <param name="value">值</param>
- [HttpPost]
- public void Write(DeviceTypeEnum deviceType, string devCode, string protocol, string propName, string value)
- {
- World.GetSystemInstance<DeviceWriteSystem>().Invoke(new DeviceWriteInfo
- {
- DeviceType = deviceType,
- Code = devCode,
- Protocol = protocol,
- Property = propName,
- Value = value
- });
- }
- #region 设备IP相关
- /// <summary>
- /// 检查Ip是否正常联通
- /// </summary>
- /// <param name="strIpOrDName">输入参数,表示IP地址或域名</param>
- /// <returns></returns>
- [HttpGet]
- public static bool PingIpOrDomainName(string strIpOrDName)
- {
- try
- {
- var objPingSender = new Ping();
- var objPinOptions = new PingOptions
- {
- DontFragment = true
- };
- const string data = "";
- var buffer = Encoding.UTF8.GetBytes(data);
- const int intTimeout = 120;
- var objPinReply = objPingSender.Send(strIpOrDName, intTimeout, buffer, objPinOptions);
- var strInfo = objPinReply.Status.ToString();
- return strInfo == "Success";
- }
- catch (Exception)
- {
- return false;
- }
- }
- /// <summary>
- /// 获取设备IP检测结果
- /// </summary>
- /// <returns>设备IP检测结果</returns>
- [HttpGet]
- public List<DeviceIpTestResults> DeviceIpTest()
- {
- if (!ServiceHub.DeviceIPList.Any()) throw new Exception("未配置任何Ip");
- var deviceIpTestResults = new List<DeviceIpTestResults>();
- ServiceHub.DeviceIPList.ForEach(ip =>
- {
- deviceIpTestResults.Add(new DeviceIpTestResults
- {
- Ip = ip,
- Result = PingIpOrDomainName(ip)
- });
- });
- return deviceIpTestResults;
- }
- /// <summary>
- /// 获取设备Ip集合
- /// </summary>
- /// <returns>设备Ip集合</returns>
- [HttpGet]
- public List<string> GetDeviceIpList()
- {
- if (!ServiceHub.DeviceIPList.Any()) throw new Exception("未配置任何Ip");
- return ServiceHub.DeviceIPList;
- }
- #endregion 设备IP相关
- }
- }
|