林豪 左 3 rokov pred
rodič
commit
b985013fce
51 zmenil súbory, kde vykonal 2630 pridanie a 47 odobranie
  1. 22 8
      WCS Pedestal.sln
  2. 237 0
      WCS.BaseExtensions/TypeExtension.cs
  3. 15 0
      WCS.BaseExtensions/WCS.BaseExtensions.csproj
  4. 237 0
      WCS.Core/Expands/TypeExtension.cs
  5. 2 2
      WCS.Core/Properties/PublishProfiles/FolderProfile.pubxml
  6. 1 1
      WCS.Core/WCS.Core.csproj
  7. 1 1
      WCS.Entity.Protocol/Properties/PublishProfiles/FolderProfile.pubxml
  8. 1 1
      WCS.Entity.Protocol/WCS.Entity.Protocol.csproj
  9. 1 1
      WCS.Entity/Properties/PublishProfiles/FolderProfile.pubxml
  10. 0 1
      WCS.Log/Properties/PublishProfiles/FolderProfile.pubxml
  11. 1 1
      WCS.Log/WCS.Log.csproj
  12. 1 2
      WCS.Service/DeviceExtentions.cs
  13. 1 1
      WCS.Service/PLCAccessors/SiemensS7PLC.cs
  14. 0 5
      WCS.Service/Program.cs
  15. 2 5
      WCS.Service/ProtocolProxy.cs
  16. 2 3
      WCS.Service/Uploader.cs
  17. 19 2
      WCS.Service/WCS.Service.csproj
  18. 4 13
      WCS.Service/Worker.cs
  19. 109 0
      WCS.WebApi/APICaller.cs
  20. 51 0
      WCS.WebApi/Startup.cs
  21. 49 0
      WCS.WebApi/ViewModels/DeviceStatusViewModel.cs
  22. 9 0
      WCS.WebApi/ViewModels/KeyValueViewModel.cs
  23. 15 0
      WCS.WebApi/WCS.WebApi.csproj
  24. 247 0
      WCS.WebApi/WCSApi.cs
  25. 83 0
      WCS.WebApi/WMS/PushCreateWcsTaskRequest.cs
  26. 13 0
      WCS.WebApi/WMS/Request/GetProductInfoRequest.cs
  27. 31 0
      WCS.WebApi/WMS/Request/I_WCS_GetExcTaskRequest.cs
  28. 54 0
      WCS.WebApi/WMS/Request/I_WCS_GetInTaskRequest.cs
  29. 24 0
      WCS.WebApi/WMS/Request/I_WCS_GetMoveTaskRequest.cs
  30. 51 0
      WCS.WebApi/WMS/Request/I_WCS_GetOutTaskRequest.cs
  31. 27 0
      WCS.WebApi/WMS/Request/I_WCS_GetTunnelListRequest.cs
  32. 51 0
      WCS.WebApi/WMS/Request/I_WCS_GetWareCellRequest.cs
  33. 32 0
      WCS.WebApi/WMS/Request/I_WCS_GetWeightRequest.cs
  34. 25 0
      WCS.WebApi/WMS/Request/I_WCS_PutDevInfoRequest.cs
  35. 125 0
      WCS.WebApi/WMS/Request/I_WCS_PutTaskStepRequest.cs
  36. 68 0
      WCS.WebApi/WMS/Request/I_WMS_CreateTasksRequest.cs
  37. 16 0
      WCS.WebApi/WMS/Request/PVCSemiFinishedProductReBackRequest.cs
  38. 45 0
      WCS.WebApi/WMS/Response/GetProductInfoResponse.cs
  39. 33 0
      WCS.WebApi/WMS/Response/I_WCS_GetExcTaskResponse.cs
  40. 68 0
      WCS.WebApi/WMS/Response/I_WCS_GetInTaskResponse.cs
  41. 86 0
      WCS.WebApi/WMS/Response/I_WCS_GetMoveTaskResponse.cs
  42. 136 0
      WCS.WebApi/WMS/Response/I_WCS_GetOutTaskResponse.cs
  43. 39 0
      WCS.WebApi/WMS/Response/I_WCS_GetTunnelListResponse.cs
  44. 53 0
      WCS.WebApi/WMS/Response/I_WCS_GetWareCellResponse.cs
  45. 30 0
      WCS.WebApi/WMS/Response/I_WCS_GetWeightResponse.cs
  46. 33 0
      WCS.WebApi/WMS/Response/I_WCS_PutDevInfoResponse.cs
  47. 38 0
      WCS.WebApi/WMS/Response/I_WCS_PutTaskStepResponse.cs
  48. 41 0
      WCS.WebApi/WMS/Response/Result.cs
  49. 12 0
      WCS.WebApi/WMS/Response/TunnelCountTemp.cs
  50. 15 0
      WCS.WebApi/WMS/Response/WcsContractApiResponse.cs
  51. 374 0
      WCS.WebApi/WMS/WMS.cs

+ 22 - 8
WCS Pedestal.sln

@@ -7,21 +7,25 @@ Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "框架", "框架", "{43005E
 EndProject
 Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "项目", "项目", "{9D01B749-E4C4-4AD4-82E1-5C3CA65295E5}"
 EndProject
-Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "WCS.DbHelper", "WCS.DbHelper\WCS.DbHelper.csproj", "{5178BC6C-A3BF-4B36-A1C6-1B7DC5937474}"
+Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "WCS.DbHelper", "WCS.DbHelper\WCS.DbHelper.csproj", "{5178BC6C-A3BF-4B36-A1C6-1B7DC5937474}"
 EndProject
-Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "WCS.Log", "WCS.Log\WCS.Log.csproj", "{B0A743B0-881E-4997-BE75-B5C4ED4A9BE4}"
+Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "WCS.Log", "WCS.Log\WCS.Log.csproj", "{B0A743B0-881E-4997-BE75-B5C4ED4A9BE4}"
 EndProject
-Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "WCS.Redis", "WCS.RedisHelper\WCS.Redis.csproj", "{A93E66D2-2A49-410C-BDA6-AF0EF230A958}"
+Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "WCS.Redis", "WCS.RedisHelper\WCS.Redis.csproj", "{A93E66D2-2A49-410C-BDA6-AF0EF230A958}"
 EndProject
-Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "WCS.Entity", "WCS.Entity\WCS.Entity.csproj", "{E20F0C8A-619A-4D78-835C-909E81338458}"
+Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "WCS.Entity", "WCS.Entity\WCS.Entity.csproj", "{E20F0C8A-619A-4D78-835C-909E81338458}"
 EndProject
-Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "WCS.Core", "WCS.Core\WCS.Core.csproj", "{17CF21B9-84AC-4FB3-9BC1-EF96CF8381CA}"
+Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "WCS.Core", "WCS.Core\WCS.Core.csproj", "{17CF21B9-84AC-4FB3-9BC1-EF96CF8381CA}"
 EndProject
-Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "WCS.Entity.Protocol", "WCS.Entity.Protocol\WCS.Entity.Protocol.csproj", "{300F18EA-128F-45EE-AE54-51AE8D2E0B57}"
+Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "WCS.Entity.Protocol", "WCS.Entity.Protocol\WCS.Entity.Protocol.csproj", "{300F18EA-128F-45EE-AE54-51AE8D2E0B57}"
 EndProject
-Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "WCS.Service", "WCS.Service\WCS.Service.csproj", "{54AF53DB-5A76-48D4-BD5F-F79D123DE1CB}"
+Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "WCS.Service", "WCS.Service\WCS.Service.csproj", "{54AF53DB-5A76-48D4-BD5F-F79D123DE1CB}"
 EndProject
-Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "WCS.Virtual_PLC", "WCS.Virtual_PLC\WCS.Virtual_PLC.csproj", "{A8557AE8-BDBE-4508-AA58-C7E7F90EFDD2}"
+Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "WCS.Virtual_PLC", "WCS.Virtual_PLC\WCS.Virtual_PLC.csproj", "{A8557AE8-BDBE-4508-AA58-C7E7F90EFDD2}"
+EndProject
+Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "WCS.WebApi", "WCS.WebApi\WCS.WebApi.csproj", "{6FE23C07-7FFC-4CF7-A889-9B62957E0BA5}"
+EndProject
+Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "WCS.BaseExtensions", "WCS.BaseExtensions\WCS.BaseExtensions.csproj", "{CDF091B2-2A9C-4A2A-BCB7-C1E7C1B62F79}"
 EndProject
 Global
 	GlobalSection(SolutionConfigurationPlatforms) = preSolution
@@ -61,6 +65,14 @@ Global
 		{A8557AE8-BDBE-4508-AA58-C7E7F90EFDD2}.Debug|Any CPU.Build.0 = Debug|Any CPU
 		{A8557AE8-BDBE-4508-AA58-C7E7F90EFDD2}.Release|Any CPU.ActiveCfg = Release|Any CPU
 		{A8557AE8-BDBE-4508-AA58-C7E7F90EFDD2}.Release|Any CPU.Build.0 = Release|Any CPU
+		{6FE23C07-7FFC-4CF7-A889-9B62957E0BA5}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+		{6FE23C07-7FFC-4CF7-A889-9B62957E0BA5}.Debug|Any CPU.Build.0 = Debug|Any CPU
+		{6FE23C07-7FFC-4CF7-A889-9B62957E0BA5}.Release|Any CPU.ActiveCfg = Release|Any CPU
+		{6FE23C07-7FFC-4CF7-A889-9B62957E0BA5}.Release|Any CPU.Build.0 = Release|Any CPU
+		{CDF091B2-2A9C-4A2A-BCB7-C1E7C1B62F79}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+		{CDF091B2-2A9C-4A2A-BCB7-C1E7C1B62F79}.Debug|Any CPU.Build.0 = Debug|Any CPU
+		{CDF091B2-2A9C-4A2A-BCB7-C1E7C1B62F79}.Release|Any CPU.ActiveCfg = Release|Any CPU
+		{CDF091B2-2A9C-4A2A-BCB7-C1E7C1B62F79}.Release|Any CPU.Build.0 = Release|Any CPU
 	EndGlobalSection
 	GlobalSection(SolutionProperties) = preSolution
 		HideSolutionNode = FALSE
@@ -74,6 +86,8 @@ Global
 		{300F18EA-128F-45EE-AE54-51AE8D2E0B57} = {9D01B749-E4C4-4AD4-82E1-5C3CA65295E5}
 		{54AF53DB-5A76-48D4-BD5F-F79D123DE1CB} = {9D01B749-E4C4-4AD4-82E1-5C3CA65295E5}
 		{A8557AE8-BDBE-4508-AA58-C7E7F90EFDD2} = {43005E7B-7FC3-407D-B098-E58D0B5B465F}
+		{6FE23C07-7FFC-4CF7-A889-9B62957E0BA5} = {9D01B749-E4C4-4AD4-82E1-5C3CA65295E5}
+		{CDF091B2-2A9C-4A2A-BCB7-C1E7C1B62F79} = {43005E7B-7FC3-407D-B098-E58D0B5B465F}
 	EndGlobalSection
 	GlobalSection(ExtensibilityGlobals) = postSolution
 		SolutionGuid = {BF8ACC41-E6AD-46E2-8A85-2BD2AE0990C0}

+ 237 - 0
WCS.BaseExtensions/TypeExtension.cs

@@ -0,0 +1,237 @@
+using Log;
+using SqlSugar;
+using System;
+using System.Collections.Generic;
+using System.ComponentModel;
+using System.Data;
+using System.Linq;
+using System.Reflection;
+using System.Security.Cryptography;
+
+namespace WCS.BaseExtensions
+{
+    /// <summary>
+    ///
+    /// </summary>
+    public static class TypeExtension
+    {
+        /// <summary>
+        /// 将字符串转换为short
+        /// </summary>
+        /// <param name="value">需要转换的字符串</param>
+        /// <returns></returns>
+        public static short ToShort(this string value)
+        {
+            return Convert.ToInt16(value);
+        }
+
+        /// <summary>
+        /// 将int转换为short
+        /// </summary>
+        /// <param name="value">需要转换的字符串</param>
+        /// <returns></returns>
+        public static short ToShort(this int value)
+        {
+            return Convert.ToInt16(value);
+        }
+
+        /// <summary>
+        /// 将decimal转换为short
+        /// </summary>
+        /// <param name="value">需要转换的字符串</param>
+        /// <returns></returns>
+        public static short ToShort(this decimal value)
+        {
+            return Convert.ToInt16(value);
+        }
+
+        /// <summary>
+        /// 将字符串转换为int
+        /// </summary>
+        /// <param name="value">需要转换的字符串</param>
+        /// <returns></returns>
+        public static int ToInt(this string value)
+        {
+            return Convert.ToInt32(value);
+        }
+
+        /// <summary>
+        /// 判断值为奇数/偶数
+        /// </summary>
+        /// <param name="value">需要判断的值</param>
+        /// <returns> true:是奇数   false:是偶数</returns>
+        public static bool OddNumberOrEven(this short value)
+        {
+            return value % 2 != 0;
+        }
+
+        /// <summary>
+        /// 获取short类型Code,只限设备组
+        /// </summary>
+        /// <param name="value"></param>
+        /// <returns></returns>
+        public static short GetShortCode(this string value)
+        {
+            return value.Replace("G", "").ToShort();
+        }
+
+        /// <summary>
+        /// 数据映射
+        /// </summary>
+        /// <typeparam name="D"></typeparam>
+        /// <typeparam name="S"></typeparam>
+        /// <param name="s"></param>
+        /// <returns></returns>
+        public static D Mapper<D, S>(S s)
+        {
+            D d = Activator.CreateInstance<D>();
+
+            var sType = s.GetType();
+            var dType = typeof(D);
+            foreach (PropertyInfo sP in sType.GetProperties())
+            {
+                foreach (PropertyInfo dP in dType.GetProperties())
+                {
+                    if (dP.Name == sP.Name)
+                    {
+                        dP.SetValue(d, sP.GetValue(s));
+                        break;
+                    }
+                }
+            }
+            return d;
+        }
+
+        /// <summary>
+        /// 获取字典
+        /// </summary>
+        /// <typeparam name="T1"></typeparam>
+        /// <typeparam name="T2"></typeparam>
+        /// <typeparam name="T3"></typeparam>
+        /// <param name="t3"></param>
+        /// <returns></returns>
+        public static Dictionary<string, object> EntityClassToDictionary<T>(T t)
+        {
+            Type type = typeof(SugarColumn);
+            Dictionary<string, object> d = new Dictionary<string, object>();
+
+            var sType = t.GetType();
+            foreach (PropertyInfo sP in sType.GetProperties())
+            {
+                if (sP.CustomAttributes.Any(v => v.AttributeType == type) && sP.Name != "VER" && sP.Name != "ID")
+                {
+                    d.Add(sP.Name, sP.GetValue(t));
+                }
+            }
+
+            return d;
+        }
+
+        /// <summary>
+        /// 获取MD5字符串
+        /// </summary>
+        /// <param name="myString"></param>
+        /// <returns></returns>
+        public static string GetMD5(this string myString)
+        {
+            MD5 md5 = MD5.Create();
+            byte[] fromData = System.Text.Encoding.Unicode.GetBytes(myString);
+            byte[] targetData = md5.ComputeHash(fromData);
+            string byte2String = null;
+
+            for (int i = 0; i < targetData.Length; i++)
+            {
+                byte2String += targetData[i].ToString("x");
+            }
+
+            return byte2String;
+        }
+
+        /// <summary>
+        /// DataTable转换成实体类
+        /// </summary>
+        /// <typeparam name="T"></typeparam>
+        /// <param name="dt"></param>
+        /// <returns></returns>
+        public static List<object> TableToEntity(this DataTable dt, string typeName)
+        {
+            List<object> list = new List<object>();
+            try
+            {
+                foreach (DataRow row in dt.Rows)
+                {
+                    Type entity = Type.GetType(typeName);
+                    PropertyInfo[] pArray = entity.GetType().GetProperties();
+
+                    foreach (PropertyInfo p in pArray)
+                    {
+                        if (dt.Columns.Contains(p.Name))
+                        {
+                            if (!p.CanWrite) continue;
+                            var value = row[p.Name];
+                            if (value != DBNull.Value)
+                            {
+                                Type targetType = p.PropertyType;
+                                Type convertType = targetType;
+                                if (targetType.IsGenericType && targetType.GetGenericTypeDefinition().Equals(typeof(Nullable<>)))
+                                {
+                                    //可空类型
+                                    NullableConverter nullableConverter = new NullableConverter(targetType);
+                                    convertType = nullableConverter.UnderlyingType;
+                                }
+                                if (!string.IsNullOrEmpty(convertType.FullName) && !string.IsNullOrEmpty(value.ToString()))
+                                {
+                                    value = Convert.ChangeType(value, convertType);
+                                }
+                                switch (convertType.FullName)
+                                {
+                                    case "System.Decimal":
+                                        p.SetValue(entity, Convert.ToDecimal(value), null);
+                                        break;
+
+                                    case "System.String":
+                                        p.SetValue(entity, Convert.ToString(value), null);
+                                        break;
+
+                                    case "System.Int32":
+                                        p.SetValue(entity, Convert.ToInt32(value), null);
+                                        break;
+
+                                    case "System.Int64":
+                                        p.SetValue(entity, Convert.ToInt64(value), null);
+                                        break;
+
+                                    case "System.Int16":
+                                        p.SetValue(entity, Convert.ToInt16(value), null);
+                                        break;
+
+                                    case "System.Double":
+                                        p.SetValue(entity, Convert.ToDouble(value), null);
+                                        break;
+
+                                    case "System.Single":
+                                        p.SetValue(entity, Convert.ToSingle(value), null);
+                                        break;
+
+                                    case "System.DateTime":
+                                        p.SetValue(entity, Convert.ToDateTime(value), null);
+                                        break;
+
+                                    default:
+                                        p.SetValue(entity, value, null);
+                                        break;
+                                }
+                            }
+                        }
+                    }
+                    list.Add(entity);
+                }
+            }
+            catch (Exception ex)
+            {
+                InfoLog.INFO_ERROR("Table转换实体类失败:" + ex.Message);
+            }
+            return list;
+        }
+    }
+}

+ 15 - 0
WCS.BaseExtensions/WCS.BaseExtensions.csproj

@@ -0,0 +1,15 @@
+<Project Sdk="Microsoft.NET.Sdk">
+
+  <PropertyGroup>
+    <TargetFramework>netstandard2.1</TargetFramework>
+    <Nullable>enable</Nullable>
+    <GenerateDocumentationFile>True</GenerateDocumentationFile>
+    <Description>基础扩展</Description>
+  </PropertyGroup>
+
+  <ItemGroup>
+    <PackageReference Include="SqlSugarCore" Version="5.1.2.4" />
+    <PackageReference Include="WCS.Log" Version="1.0.1" />
+  </ItemGroup>
+
+</Project>

+ 237 - 0
WCS.Core/Expands/TypeExtension.cs

@@ -0,0 +1,237 @@
+using Log;
+using SqlSugar;
+using System;
+using System.Collections.Generic;
+using System.ComponentModel;
+using System.Data;
+using System.Linq;
+using System.Reflection;
+using System.Security.Cryptography;
+
+namespace WCS.Core.Expands
+{
+    /// <summary>
+    ///
+    /// </summary>
+    public static class TypeExtension
+    {
+        /// <summary>
+        /// 将字符串转换为short
+        /// </summary>
+        /// <param name="value">需要转换的字符串</param>
+        /// <returns></returns>
+        public static short ToShort(this string value)
+        {
+            return Convert.ToInt16(value);
+        }
+
+        /// <summary>
+        /// 将int转换为short
+        /// </summary>
+        /// <param name="value">需要转换的字符串</param>
+        /// <returns></returns>
+        public static short ToShort(this int value)
+        {
+            return Convert.ToInt16(value);
+        }
+
+        /// <summary>
+        /// 将decimal转换为short
+        /// </summary>
+        /// <param name="value">需要转换的字符串</param>
+        /// <returns></returns>
+        public static short ToShort(this decimal value)
+        {
+            return Convert.ToInt16(value);
+        }
+
+        /// <summary>
+        /// 将字符串转换为int
+        /// </summary>
+        /// <param name="value">需要转换的字符串</param>
+        /// <returns></returns>
+        public static int ToInt(this string value)
+        {
+            return Convert.ToInt32(value);
+        }
+
+        /// <summary>
+        /// 判断值为奇数/偶数
+        /// </summary>
+        /// <param name="value">需要判断的值</param>
+        /// <returns> true:是奇数   false:是偶数</returns>
+        public static bool OddNumberOrEven(this short value)
+        {
+            return value % 2 != 0;
+        }
+
+        /// <summary>
+        /// 获取short类型Code,只限设备组
+        /// </summary>
+        /// <param name="value"></param>
+        /// <returns></returns>
+        public static short GetShortCode(this string value)
+        {
+            return value.Replace("G", "").ToShort();
+        }
+
+        /// <summary>
+        /// 数据映射
+        /// </summary>
+        /// <typeparam name="D"></typeparam>
+        /// <typeparam name="S"></typeparam>
+        /// <param name="s"></param>
+        /// <returns></returns>
+        public static D Mapper<D, S>(S s)
+        {
+            D d = Activator.CreateInstance<D>();
+
+            var sType = s.GetType();
+            var dType = typeof(D);
+            foreach (PropertyInfo sP in sType.GetProperties())
+            {
+                foreach (PropertyInfo dP in dType.GetProperties())
+                {
+                    if (dP.Name == sP.Name)
+                    {
+                        dP.SetValue(d, sP.GetValue(s));
+                        break;
+                    }
+                }
+            }
+            return d;
+        }
+
+        /// <summary>
+        /// 获取字典
+        /// </summary>
+        /// <typeparam name="T1"></typeparam>
+        /// <typeparam name="T2"></typeparam>
+        /// <typeparam name="T3"></typeparam>
+        /// <param name="t3"></param>
+        /// <returns></returns>
+        public static Dictionary<string, object> EntityClassToDictionary<T>(T t)
+        {
+            Type type = typeof(SugarColumn);
+            Dictionary<string, object> d = new Dictionary<string, object>();
+
+            var sType = t.GetType();
+            foreach (PropertyInfo sP in sType.GetProperties())
+            {
+                if (sP.CustomAttributes.Any(v => v.AttributeType == type) && sP.Name != "VER" && sP.Name != "ID")
+                {
+                    d.Add(sP.Name, sP.GetValue(t));
+                }
+            }
+
+            return d;
+        }
+
+        /// <summary>
+        /// 获取MD5字符串
+        /// </summary>
+        /// <param name="myString"></param>
+        /// <returns></returns>
+        public static string GetMD5(this string myString)
+        {
+            MD5 md5 = MD5.Create();
+            byte[] fromData = System.Text.Encoding.Unicode.GetBytes(myString);
+            byte[] targetData = md5.ComputeHash(fromData);
+            string byte2String = null;
+
+            for (int i = 0; i < targetData.Length; i++)
+            {
+                byte2String += targetData[i].ToString("x");
+            }
+
+            return byte2String;
+        }
+
+        /// <summary>
+        /// DataTable转换成实体类
+        /// </summary>
+        /// <typeparam name="T"></typeparam>
+        /// <param name="dt"></param>
+        /// <returns></returns>
+        public static List<object> TableToEntity(this DataTable dt, string typeName)
+        {
+            List<object> list = new List<object>();
+            try
+            {
+                foreach (DataRow row in dt.Rows)
+                {
+                    Type entity = Type.GetType(typeName);
+                    PropertyInfo[] pArray = entity.GetType().GetProperties();
+
+                    foreach (PropertyInfo p in pArray)
+                    {
+                        if (dt.Columns.Contains(p.Name))
+                        {
+                            if (!p.CanWrite) continue;
+                            var value = row[p.Name];
+                            if (value != DBNull.Value)
+                            {
+                                Type targetType = p.PropertyType;
+                                Type convertType = targetType;
+                                if (targetType.IsGenericType && targetType.GetGenericTypeDefinition().Equals(typeof(Nullable<>)))
+                                {
+                                    //可空类型
+                                    NullableConverter nullableConverter = new NullableConverter(targetType);
+                                    convertType = nullableConverter.UnderlyingType;
+                                }
+                                if (!string.IsNullOrEmpty(convertType.FullName) && !string.IsNullOrEmpty(value.ToString()))
+                                {
+                                    value = Convert.ChangeType(value, convertType);
+                                }
+                                switch (convertType.FullName)
+                                {
+                                    case "System.Decimal":
+                                        p.SetValue(entity, Convert.ToDecimal(value), null);
+                                        break;
+
+                                    case "System.String":
+                                        p.SetValue(entity, Convert.ToString(value), null);
+                                        break;
+
+                                    case "System.Int32":
+                                        p.SetValue(entity, Convert.ToInt32(value), null);
+                                        break;
+
+                                    case "System.Int64":
+                                        p.SetValue(entity, Convert.ToInt64(value), null);
+                                        break;
+
+                                    case "System.Int16":
+                                        p.SetValue(entity, Convert.ToInt16(value), null);
+                                        break;
+
+                                    case "System.Double":
+                                        p.SetValue(entity, Convert.ToDouble(value), null);
+                                        break;
+
+                                    case "System.Single":
+                                        p.SetValue(entity, Convert.ToSingle(value), null);
+                                        break;
+
+                                    case "System.DateTime":
+                                        p.SetValue(entity, Convert.ToDateTime(value), null);
+                                        break;
+
+                                    default:
+                                        p.SetValue(entity, value, null);
+                                        break;
+                                }
+                            }
+                        }
+                    }
+                    list.Add(entity);
+                }
+            }
+            catch (Exception ex)
+            {
+                InfoLog.INFO_ERROR("Table转换实体类失败:" + ex.Message);
+            }
+            return list;
+        }
+    }
+}

+ 2 - 2
WCS.Core/Properties/PublishProfiles/FolderProfile.pubxml

@@ -8,7 +8,7 @@ https://go.microsoft.com/fwlink/?LinkID=208121.
     <Platform>Any CPU</Platform>
     <PublishDir>D:\XM\Release\DLL</PublishDir>
     <PublishProtocol>FileSystem</PublishProtocol>
-    <VersionPrefix>1.0.0</VersionPrefix>
-    <describe>第一版</describe>
+    <VersionPrefix>1.0.4</VersionPrefix>
+    <describe>新增类型扩展支持类型转换</describe>
   </PropertyGroup>
 </Project>

+ 1 - 1
WCS.Core/WCS.Core.csproj

@@ -13,7 +13,7 @@
   <ItemGroup>
     <PackageReference Include="HslCommunication" Version="6.2.2" />
     <PackageReference Include="WCS.DbHelper" Version="1.0.0" />
-    <PackageReference Include="WCS.Entity" Version="1.0.2" />
+    <PackageReference Include="WCS.Entity" Version="1.0.3" />
     <PackageReference Include="WCS.Redis" Version="1.0.2" />
   </ItemGroup>
 

+ 1 - 1
WCS.Entity.Protocol/Properties/PublishProfiles/FolderProfile.pubxml

@@ -8,7 +8,7 @@ https://go.microsoft.com/fwlink/?LinkID=208121.
     <Platform>Any CPU</Platform>
     <PublishDir>D:\XM\Release\DLL</PublishDir>
     <PublishProtocol>FileSystem</PublishProtocol>
-    <VersionPrefix>1.0.0</VersionPrefix>
+    <VersionPrefix>1.0.1</VersionPrefix>
     <describe>第一版</describe>
   </PropertyGroup>
 </Project>

+ 1 - 1
WCS.Entity.Protocol/WCS.Entity.Protocol.csproj

@@ -8,7 +8,7 @@
   </PropertyGroup>
 
   <ItemGroup>
-    <PackageReference Include="WCS.Entity" Version="1.0.2" />
+    <PackageReference Include="WCS.Entity" Version="1.0.3" />
   </ItemGroup>
 
 </Project>

+ 1 - 1
WCS.Entity/Properties/PublishProfiles/FolderProfile.pubxml

@@ -8,7 +8,7 @@ https://go.microsoft.com/fwlink/?LinkID=208121.
     <Platform>Any CPU</Platform>
     <PublishDir>D:\XM\Release\DLL</PublishDir>
     <PublishProtocol>FileSystem</PublishProtocol>
-    <VersionPrefix>1.0.2</VersionPrefix>
+    <VersionPrefix>1.0.3</VersionPrefix>
     <describe>优化引用</describe>
   </PropertyGroup>
 </Project>

+ 0 - 1
WCS.Log/Properties/PublishProfiles/FolderProfile.pubxml

@@ -7,7 +7,6 @@ https://go.microsoft.com/fwlink/?LinkID=208121.
     <Configuration>Release</Configuration>
     <Platform>Any CPU</Platform>
     <VersionPrefix>1.0.1</VersionPrefix>
-    <describe>新增注释</describe>
     <PublishDir>D:\XM\Release\DLL</PublishDir>
     <PublishProtocol>FileSystem</PublishProtocol>
   </PropertyGroup>

+ 1 - 1
WCS.Log/WCS.Log.csproj

@@ -5,7 +5,7 @@
     <Nullable>enable</Nullable>
     <Version>$(VersionPrefix)</Version>
     <GenerateDocumentationFile>True</GenerateDocumentationFile>
-    <Description>$(describe)</Description>
+    <Description>日志库</Description>
   </PropertyGroup>
 
   <ItemGroup>

+ 1 - 2
WCS.Service/DeviceExtentions.cs

@@ -1,5 +1,4 @@
-using DBHelper_SqlSugar;
-using System.Linq;
+using DbHelper;
 using WCS.Entity;
 using WCS.Entity.Protocol;
 using WCS.Entity.Protocol.Station;

+ 1 - 1
WCS.Service/PLCAccessors/SiemensS7PLC.cs

@@ -1,7 +1,7 @@
 using HslCommunication.Profinet.Siemens;
-using Virtual_PLC;
 using WCS.Core;
 using WCS.Core.DataTrans;
+using WCS.Virtual_PLC;
 
 namespace WCS.Service.PLCAccessors
 {

+ 0 - 5
WCS.Service/Program.cs

@@ -1,10 +1,5 @@
 using Microsoft.AspNetCore.Hosting;
-using Microsoft.Extensions.DependencyInjection;
-using Microsoft.Extensions.Hosting;
-using System;
 using System.Runtime.InteropServices;
-using System.Threading;
-using System.Threading.Tasks;
 using WCS.Core;
 
 namespace WCS.Service

+ 2 - 5
WCS.Service/ProtocolProxy.cs

@@ -1,20 +1,17 @@
-using DBHelper_SqlSugar;
+using DbHelper;
 using FreeRedis;
 using MessagePack;
 using MessagePack.Resolvers;
 using SqlSugar;
-using System;
 using System.Collections.Concurrent;
-using System.Collections.Generic;
 using System.Diagnostics;
-using System.Linq;
 using System.Linq.Dynamic.Core;
 using System.Reflection;
 using WCS.Core;
 using WCS.Core.DataTrans;
+using WCS.Core.Expands;
 using WCS.Entity;
 using WCS.Entity.Protocol;
-using WCS.Service.Extensions;
 
 namespace WCS.Service
 {

+ 2 - 3
WCS.Service/Uploader.cs

@@ -1,6 +1,5 @@
-using DBHelper_SqlSugar;
-using Logs;
-using System;
+using DbHelper;
+using Log;
 using WCS.Entity;
 
 namespace WCS.Service

+ 19 - 2
WCS.Service/WCS.Service.csproj

@@ -8,8 +8,25 @@
   </PropertyGroup>
 
   <ItemGroup>
+    <PackageReference Include="MessagePack" Version="2.4.35" />
+    <PackageReference Include="Microsoft.AspNetCore.Mvc.Core" Version="2.2.5" />
+    <PackageReference Include="Microsoft.EntityFrameworkCore.Design" Version="6.0.8">
+      <PrivateAssets>all</PrivateAssets>
+      <IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
+    </PackageReference>
+    <PackageReference Include="Microsoft.EntityFrameworkCore.DynamicLinq" Version="6.2.19" />
+    <PackageReference Include="Microsoft.EntityFrameworkCore.Relational" Version="6.0.8" />
+    <PackageReference Include="Microsoft.EntityFrameworkCore.Tools" Version="6.0.8">
+      <PrivateAssets>all</PrivateAssets>
+      <IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
+    </PackageReference>
     <PackageReference Include="Microsoft.Extensions.Hosting" Version="6.0.1" />
-    <PackageReference Include="WCS.Core" Version="1.0.0" />
-    <PackageReference Include="WCS.Entity.Protocol" Version="1.0.0" />
+    <PackageReference Include="Microsoft.Extensions.Hosting.Systemd" Version="6.0.0" />
+    <PackageReference Include="Microsoft.Extensions.Hosting.WindowsServices" Version="6.0.0" />
+    <PackageReference Include="Microsoft.VisualStudio.Web.CodeGeneration.Design" Version="6.0.8" />
+    <PackageReference Include="Swashbuckle.AspNetCore" Version="6.4.0" />
+    <PackageReference Include="WCS.Core" Version="1.0.4" />
+    <PackageReference Include="WCS.Entity.Protocol" Version="1.0.1" />
+    <PackageReference Include="WCS.Virtual_PLC" Version="1.0.0" />
   </ItemGroup>
 </Project>

+ 4 - 13
WCS.Service/Worker.cs

@@ -1,25 +1,16 @@
-using DBHelper_SqlSugar;
-using Logs;
-using Microsoft.Extensions.Configuration;
-using Microsoft.Extensions.Hosting;
-using Microsoft.Extensions.Logging;
+using DbHelper;
+using Log;
 using Newtonsoft.Json;
 using SqlSugar;
-using System;
-using System.Collections.Generic;
-using System.IO;
-using System.Linq;
 using System.Reflection;
 using System.Text;
-using System.Threading;
-using Virtual_PLC;
 using WCS.Core;
 using WCS.Core.DataTrans;
 using WCS.Entity;
 using WCS.Entity.Protocol;
 using WCS.Entity.Protocol.BCR;
 using WCS.Entity.Protocol.Station;
-using WCS.Service.Extensions;
+using WCS.Virtual_PLC;
 
 namespace WCS.Service
 {
@@ -77,7 +68,7 @@ namespace WCS.Service
                 db.Default.CodeFirst.InitTables(typeof(WCS_AGVTask));
                 db.Default.CodeFirst.InitTables(typeof(WCS_DEVICEPROTOCOL));
                 db.Default.CodeFirst.InitTables(typeof(WCS_GROUPMEMBER));
-                db.Default.CodeFirst.InitTables(typeof(WCS_MAPPINGENTRY));
+                db.Default.CodeFirst.InitTables(typeof(Entity.WCS_MAPPINGENTRY));
                 db.Default.CodeFirst.InitTables(typeof(WCS_USERS));
                 db.Default.CodeFirst.InitTables(typeof(WCS_StatusLog));
                 db.Default.CodeFirst.InitTables(typeof(WCS_BCR80));

+ 109 - 0
WCS.WebApi/APICaller.cs

@@ -0,0 +1,109 @@
+using Logs;
+using Newtonsoft.Json;
+using System;
+using System.Collections.Concurrent;
+using System.Diagnostics;
+using System.IO;
+using System.Net;
+using System.Text;
+using static System.Net.WebRequest;
+
+namespace WCS.Service
+{
+    public class APICaller
+    {
+        private class Result
+        {
+            public bool Succsess;
+            public string Exception;
+            public object Data;
+        }
+
+        private static ConcurrentDictionary<string, Result> Results = new ConcurrentDictionary<string, Result>();
+
+        public static T CallApi2<T>(string url, object parameter, string type = "POST")
+        {
+            var content = JsonConvert.SerializeObject(parameter);
+            var result = HttpApi(url, content, type);
+            return JsonConvert.DeserializeObject<T>(result);
+        }
+
+        public static T CallApi<T>(string url, object parameter, string type = "Post")
+        {
+            var content = JsonConvert.SerializeObject(parameter);
+            //var key = url + content;
+            // if (Results.ContainsKey(key))
+            //{
+            //    var res = Results[key];
+            //    if (res == null)
+            //        throw new WarnException("接口调用中");
+            //    try
+            //    {
+            //        if (!res.Succsess)
+            //            throw new WarnException(res.Exception);
+            //        return (T)res.Data;
+            //    }
+            //    finally
+            //    {
+            //        Results.Remove(key, out res);
+            //    }
+            //}
+            //else
+            //{
+            //    Results[key] = null;
+            //    var task = Task.Run(() =>
+            //     {
+            var res = new Result();
+            try
+            {
+                var result = HttpApi(url, content, type);
+                res.Data = JsonConvert.DeserializeObject<T>(result);
+                //res.Succsess = true;
+            }
+            catch (Exception ex)
+            {
+                res.Exception = ex.Message;
+            }
+            return (T)res.Data;
+            //finally
+            //{
+            //    Results[key] = res;
+            //}
+            // });
+            //task.Wait(50);
+            //if (task.IsCompleted)
+            //{
+            //    return CallApi<T>(url, parameter, type);
+            //}
+            //else
+            //{
+            //    throw new WarnException("接口调用中");
+            //}
+        }
+
+        private static string HttpApi(string url, string jsonstr, string type)
+        {
+            var sw = new Stopwatch();
+            sw.Start();
+            var encoding = Encoding.UTF8;
+#pragma warning disable SYSLIB0014
+            var request = (HttpWebRequest)Create(url);//webrequest请求api地址
+#pragma warning restore SYSLIB0014
+            request.Timeout = 60000;//连接超时
+            request.ReadWriteTimeout = 3600000;//读写超时
+            request.Accept = "text/html,application/xhtml+xml,*/*";
+            request.ContentType = "application/json";
+            request.Method = type.ToUpper().ToString();//get或者post
+            var buffer = encoding.GetBytes(jsonstr);
+            request.ContentLength = buffer.Length;
+            request.GetRequestStream().Write(buffer, 0, buffer.Length);
+            var response = (HttpWebResponse)request.GetResponse();
+            using var reader = new StreamReader(response.GetResponseStream()!, Encoding.UTF8);
+            var res = reader.ReadToEnd();
+            sw.Stop();
+            if (sw.ElapsedMilliseconds > 500)
+                InfoLog.INFO_TIMING($"接口{url}调用耗时{sw.ElapsedMilliseconds}---------{JsonConvert.SerializeObject(res)}");
+            return res;
+        }
+    }
+}

+ 51 - 0
WCS.WebApi/Startup.cs

@@ -0,0 +1,51 @@
+using Microsoft.AspNetCore.Builder;
+using Microsoft.AspNetCore.Hosting;
+using Microsoft.Extensions.Configuration;
+using Microsoft.Extensions.DependencyInjection;
+using Microsoft.Extensions.Hosting;
+using Microsoft.OpenApi.Models;
+
+namespace WCS.Service
+{
+    public class Startup
+    {
+        public Startup(IConfiguration configuration)
+        {
+            Configuration = configuration;
+        }
+
+        public IConfiguration Configuration { get; }
+
+        // This method gets called by the runtime. Use this method to add services to the container.
+        public void ConfigureServices(IServiceCollection services)
+        {
+            services.AddControllers();
+            services.AddSwaggerGen(c =>
+            {
+                c.SwaggerDoc("v1", new OpenApiInfo { Title = "WCSAPI", Version = "v1" });
+            });
+        }
+
+        // This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
+        public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
+        {
+            if (env.IsDevelopment())
+            {
+                app.UseDeveloperExceptionPage();
+                app.UseSwagger();
+                app.UseSwaggerUI(c => c.SwaggerEndpoint("/swagger/v1/swagger.json", "WebApplication1 v1"));
+            }
+
+            app.UseHttpsRedirection();
+
+            app.UseRouting();
+
+            app.UseAuthorization();
+
+            app.UseEndpoints(endpoints =>
+            {
+                endpoints.MapControllers();
+            });
+        }
+    }
+}

+ 49 - 0
WCS.WebApi/ViewModels/DeviceStatusViewModel.cs

@@ -0,0 +1,49 @@
+#nullable enable
+using WCS.Entity;
+
+namespace WCS.Service.WebApi.ViewModels
+{
+    public class DeviceStatusViewModel
+    {
+        /// <summary>
+        /// 设备号
+        /// </summary>
+        public string? CODE { get; set; }
+
+        /// <summary>
+        /// 任务号
+        /// </summary>
+        public int? TASKNUM { get; set; }
+
+        /// <summary>
+        /// 任务类型
+        /// </summary>
+        public TaskType? TYPE { get; set; } = null;
+
+        /// <summary>
+        /// 货物条码
+        /// </summary>
+        public string? BARCODE { get; set; }
+
+        /// <summary>
+        /// 起始地址
+        /// </summary>
+        public string? ADDRFROM { get; set; }
+
+        /// <summary>
+        /// 目标地址
+        /// </summary>
+        public string? ADDRTO { get; set; }
+
+        /// <summary>
+        /// 请求信号
+        /// </summary>
+        public bool? REQUEST { get; set; } = null;
+
+        /// <summary>
+        /// 光电信号
+        /// </summary>
+        public bool? PH_STATUS { get; set; } = null;
+    }
+
+}

+ 9 - 0
WCS.WebApi/ViewModels/KeyValueViewModel.cs

@@ -0,0 +1,9 @@
+namespace WCS.Service.WebApi
+{
+    public class KeyValueViewModel<key, value>
+    {
+        public key Key { get; set; }
+
+        public value Value { get; set; }
+    }
+}

+ 15 - 0
WCS.WebApi/WCS.WebApi.csproj

@@ -0,0 +1,15 @@
+<Project Sdk="Microsoft.NET.Sdk">
+
+  <PropertyGroup>
+    <TargetFramework>net6.0</TargetFramework>
+    <Nullable>enable</Nullable>
+  </PropertyGroup>
+
+  <ItemGroup>
+    <PackageReference Include="Microsoft.AspNetCore.Mvc.Core" Version="2.2.5" />
+    <PackageReference Include="Microsoft.VisualStudio.Web.CodeGeneration.Design" Version="6.0.8" />
+    <PackageReference Include="Swashbuckle.AspNetCore" Version="6.4.0" />
+    <PackageReference Include="WCS.Entity.Protocol" Version="1.0.1" />
+  </ItemGroup>
+
+</Project>

+ 247 - 0
WCS.WebApi/WCSApi.cs

@@ -0,0 +1,247 @@
+using DBHelper_SqlSugar;
+using Microsoft.AspNetCore.Mvc;
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using WCS.Entity;
+using WCS.Entity.Protocol;
+using WCS.Service.Entity;
+
+namespace WCS.Service.WebApi
+{
+    [ApiController]
+    [Route("[controller]/[action]")]
+    public class WCSApi : ControllerBase
+    {
+        [HttpPost]
+        public WcsContractApiResponse I_WMS_CreateTasks(List<PushCreateWcsTaskRequest> list)
+        {
+            var res = new WcsContractApiResponse();
+            try
+            {
+                Db.Do(db =>
+                {
+                    foreach (var obj in list)
+                    {
+                        if (obj.TaskType == "3")//移库任务
+                        {
+                            var wmstaskid = int.Parse(obj.WMSTaskNo);
+                            if (db.Default.Queryable<WCS_TASK>().Any(v => v.WMSTASK == wmstaskid))
+                                throw new Exception("任务号" + wmstaskid + "重复下发");
+
+                            var scid = int.Parse(obj.SRMNo.Last().ToString());
+                            var tunnel = "TY" + obj.StartTunnel;
+                            var task = new WCS_TASK
+                            {
+                                TYPE = TaskType.移库,
+                                STATUS = WCS.Entity.TaskStatus.新建,
+                                DEVICE = "SRM" + obj.SRMNo.Last(),
+                                BARCODE = obj.PalletCode,
+                                ADDRFROM = obj.StartLocation,
+                                ADDRTO = obj.EndLocation,
+                                UPDATETIME = DateTime.Now,
+                                UPDATEUSER = "WMS",
+                                TUNNEL = tunnel,
+                                WMSTASK = int.Parse(obj.WMSTaskNo),
+                                TaskGroupKey = obj.TaskGroupKey
+                            };
+                            db.Default.Insertable(task).ExecuteCommand();
+                        }
+                        else if (obj.TaskType == "2")
+                        {  //出库任务
+                            var wmstaskid = int.Parse(obj.WMSTaskNo);
+                            if (db.Default.Queryable<WCS_TASK>().Any(v => v.WMSTASK == wmstaskid))
+                                throw new Exception("任务号" + wmstaskid + "重复下发");
+
+                            var tunnel = "TY" + obj.SRMNo.Last();
+
+                            var task = new WCS_TASK
+                            {
+                                TYPE = TaskType.出库,
+                                STATUS = WCS.Entity.TaskStatus.新建,
+                                DEVICE = "SRM" + obj.SRMNo.Last(),
+                                BARCODE = obj.PalletCode,
+                                ADDRFROM = string.Format("{0}-{1}-{2}", obj.StartRow, obj.StartCol, obj.StartLayer),
+                                ADDRTO = obj.EndLocation,
+                                UPDATETIME = DateTime.Now,
+                                UPDATEUSER = "WMS",
+                                TUNNEL = tunnel,
+                                WMSTASK = int.Parse(obj.WMSTaskNo),
+                                ADDRNEXT = obj.EndLocation,
+                                Length = obj.Length,
+                                MaterialCode = obj.MaterialCode,
+                                FLOOR = 1,
+                            };
+
+                            db.Default.Insertable(task).ExecuteCommand();
+                        }
+                        else if (obj.TaskType == "1")
+                        {//入库任务
+                            var wmstaskid = int.Parse(obj.WMSTaskNo);
+                            if (db.Default.Queryable<WCS_TASK>().Any(v => v.WMSTASK == wmstaskid))
+                                throw new Exception("任务号" + wmstaskid + "重复下发");
+
+                            if (obj.StartLocation.Contains("_Back_"))
+                            {//生成AGV入库任务
+                                var ws = int.Parse(obj.StartLocation.Split('_')[1]);
+                                var agvtask = new WCS_AGVTask
+                                {
+                                    AGVStatus = AGVTaskStatus.新建,
+                                    Status = AGVTaskStatus.新建,
+                                    Position = obj.StartLocation,
+                                    TaskType = AGVTaskType.入库,
+                                    CreateTime = DateTime.Now,
+                                    UpdateTime = DateTime.Now,
+                                    Workshop = ws,
+                                };
+                                if (ws == 13 || ws == 14)
+                                {
+                                    agvtask.Station = "2088";
+                                    agvtask.Workshop = 1314;
+                                }
+                                else if (ws == 1)
+                                {
+                                    agvtask.Station = "2122";
+                                }
+                                else if (ws == 2)
+                                    agvtask.Station = "2131";
+                                else if (ws == 3)
+                                    agvtask.Station = "2143";
+
+                                db.Default.Insertable(agvtask).ExecuteCommand();
+                            }
+                            else
+                            {
+                                var task = new WCS_TASK
+                                {
+                                    TYPE = TaskType.入库,
+                                    STATUS = WCS.Entity.TaskStatus.新建,
+                                    BARCODE = obj.PalletCode,
+                                    ADDRFROM = obj.StartLocation,
+                                    ADDRTO = obj.EndLocation,
+                                    UPDATETIME = DateTime.Now,
+                                    UPDATEUSER = "WMS",
+                                    WMSTASK = int.Parse(obj.WMSTaskNo)
+                                };
+                                db.Default.Insertable(task).ExecuteCommand();
+                            }
+                        }
+                    }
+                });
+                res.ResType = true;
+            }
+            catch (Exception ex)
+            {
+                res.ResMessage = ex.GetBaseException().Message;
+            }
+            return res;
+        }
+
+        [HttpPost]
+        public WcsContractApiResponse I_WMS_CreateAGVTask(PushCreateAGVTaskRequest obj)
+        {
+            var res = new WcsContractApiResponse();
+            try
+            {
+                Db.Do(db =>
+                {
+                    if (obj.Type == 1)
+                    {
+                        var ws = int.Parse(obj.StartPos.Split('_')[1]);
+                        var agvtask = new WCS_AGVTask
+                        {
+                            AGVStatus = AGVTaskStatus.新建,
+                            Status = AGVTaskStatus.新建,
+                            Position = obj.StartPos,
+                            TaskType = AGVTaskType.入库,
+                            CreateTime = DateTime.Now,
+                            UpdateTime = DateTime.Now,
+                            Workshop = ws,
+                        };
+                        if (ws == 13 || ws == 14)
+                        {
+                            agvtask.Station = "2088";
+                            agvtask.Workshop = 1314;
+                        }
+                        else if (ws == 1)
+                        {
+                            agvtask.Station = "2122";
+                        }
+                        else if (ws == 2)
+                            agvtask.Station = "2131";
+                        else if (ws == 3)
+                            agvtask.Station = "2143";
+
+                        db.Default.Insertable(agvtask).ExecuteCommand();
+                    }
+                    else
+                        throw new Exception($"类型{obj.Type}不支持");
+                });
+
+                res.ResType = true;
+            }
+            catch (Exception ex)
+            {
+                res.ResMessage = ex.GetBaseException().Message;
+            }
+            return res;
+        }
+
+        [HttpPost]
+        public WcsContractApiResponse I_CancelWCSTaskByCode(string code)
+        {
+            var res = new WcsContractApiResponse();
+            try
+            {
+                Db.Do(db =>
+                {
+                    var task = db.Default.Queryable<WCS_TASK>().First(v => v.BARCODE == code && v.STATUS < WCS.Entity.TaskStatus.已完成 && v.TYPE == TaskType.组盘);
+                    if (task == null)
+                        throw new Exception("WCS任务不存在");
+                    task.STATUS = WCS.Entity.TaskStatus.已取消;
+                    task.UPDATETIME = DateTime.Now;
+                    task.UPDATEUSER = "RF";
+                    db.Default.Updateable(task).ExecuteCommand();
+                });
+                res.ResType = true;
+            }
+            catch (Exception ex)
+            {
+                res.ResMessage = ex.GetBaseException().Message;
+            }
+            return res;
+        }
+
+        [HttpPost]
+        public WcsContractApiResponse I_CancelWCSTaskByID(int wmstaskId)
+        {
+            var res = new WcsContractApiResponse();
+            try
+            {
+                Db.Do(db =>
+                {
+                    var task = db.Default.Queryable<WCS_TASK>().First(v => v.WMSTASK == wmstaskId);
+                    if (task == null)
+                        throw new Exception("WCS任务不存在");
+                    if (task.STATUS != WCS.Entity.TaskStatus.新建)
+                        throw new Exception("WCS任务当前状态不允许取消");
+                    task.STATUS = WCS.Entity.TaskStatus.已取消;
+                    task.UPDATETIME = DateTime.Now;
+                    task.UPDATEUSER = "WMS";
+                    db.Default.Updateable(task).ExecuteCommand();
+                    if (task.TYPE != TaskType.出库 || task.AGVTASKID <= 0) return;
+                    var agvtask = db.Default.Queryable<WCS_AGVTask>().InSingle(task.AGVTASKID);
+                    agvtask.Status = AGVTaskStatus.取消;
+                    agvtask.UpdateTime = DateTime.Now;
+                    db.Default.Updateable(agvtask).ExecuteCommand();
+                });
+                res.ResType = true;
+            }
+            catch (Exception ex)
+            {
+                res.ResMessage = ex.GetBaseException().Message;
+            }
+            return res;
+        }
+    }
+}

+ 83 - 0
WCS.WebApi/WMS/PushCreateWcsTaskRequest.cs

@@ -0,0 +1,83 @@
+namespace WCS.Service.Entity
+{
+    public class PushCreateWcsTaskRequest
+    {
+        public string WMSTaskNo { get; set; }//WMS任务号
+        public string TaskGroupKey { get; set; } //任务组ID
+        public string StartLocation { get; set; }//起点地址
+        public string EndLocation { get; set; }//目标地址
+        public string Warehouse { get; set; }//仓库名称
+        public string PalletCode { get; set; }//托盘条码
+        public string TaskState { get; set; }//任务状态
+        public string StartRow { get; set; }//起点行
+        public string StartCol { get; set; }//起点列
+        public string StartLayer { get; set; }//起点层
+        public string EndRow { get; set; }//目标行
+        public string EndCol { get; set; }//目标列
+        public string EndLayer { get; set; }//目标层
+        public string StartTunnel { get; set; }//起点巷道
+        public string EndTunnel { get; set; }//终点巷道
+        public string WMSSendName { get; set; }//WMS下发人名称
+        public string TaskType { get; set; }//任务类型
+        public string Priority { get; set; }//优先级
+        public string SRMNo { get; set; }//堆垛机编号
+        public bool IsIceBox { get; set; } = false;//是否冰箱
+
+        /// <summary>
+        /// 分组编号
+        /// </summary>
+        public string TASK_ITEM1 { get; set; } = "";
+
+        /// <summary>
+        /// 托盘类型(1.原膜托盘 2.熟化架 3.成品托盘 4.空托盘组)
+        /// </summary>
+        public string TASK_ITEM2 { get; set; } = "";
+
+        /// <summary>
+        /// 是否空盘(1.空盘 2.非空盘)
+        /// </summary>
+        public string TASK_ITEM3 { get; set; } = "";
+
+        /// <summary>
+        /// outId
+        /// </summary>
+        public string TASK_ITEM4 { get; set; } = "";
+
+        /// <summary>
+        /// 熟化类型(0=不需熟化、1=熟化房熟化、2=小烘房熟化)
+        /// </summary>
+        public int TASK_MatureType { get; set; }
+
+        /// <summary>
+        /// 熟化时间(小时:10,16)
+        /// </summary>
+        public decimal TASK_MatureDate { get; set; }
+
+        /// <summary>
+        /// 熟化温度(小数)
+        /// </summary>
+        public decimal TASK_MatureTemperat { get; set; }
+
+        /// <summary>
+        /// 卷长度
+        /// </summary>
+        public decimal Length { get; set; }
+
+        /// <summary>
+        /// 产品编码
+        /// </summary>
+        public string MaterialCode { get; set; }
+    }
+
+    public class PushCreateAGVTaskRequest
+    {
+        public string StartPos { get; set; }
+
+        public string EndPos { get; set; }
+
+        /// <summary>
+        /// 1:缓存位退料
+        /// </summary>
+        public int Type { get; set; }
+    }
+}

+ 13 - 0
WCS.WebApi/WMS/Request/GetProductInfoRequest.cs

@@ -0,0 +1,13 @@
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Threading.Tasks;
+
+namespace WCS.Service.Entity
+{
+    public class GetProductInfoRequest
+    {
+        public string BarCode { get; set; }
+    }
+}

+ 31 - 0
WCS.WebApi/WMS/Request/I_WCS_GetExcTaskRequest.cs

@@ -0,0 +1,31 @@
+using System;
+using System.Collections.Generic;
+using System.ComponentModel.DataAnnotations;
+using System.Text;
+
+namespace WCS.Service.Entity
+{
+    /// <summary>
+    /// 获取异常任务请求实体
+    /// </summary>
+    public class I_WCS_GetExcTaskRequest
+    {
+        /// <summary>
+        /// 设备编号
+        /// </summary>
+        [Required(ErrorMessage = "{0} 不可为空")]
+        public string EquipmentNo { get; set; }
+        /// <summary>
+        /// 异常代码
+        /// </summary>
+        [Required(ErrorMessage = "{0} 不可为空")]
+        public string ExcCode { get; set; }
+        /// <summary>
+        /// 异常消息
+        /// </summary>
+        [Required(ErrorMessage = "{0} 不可为空")]
+        public string ExcMessage { get; set; }
+        public string Memo1 { get; set; }
+        public string Memo2 { get; set; }
+    }
+}

+ 54 - 0
WCS.WebApi/WMS/Request/I_WCS_GetInTaskRequest.cs

@@ -0,0 +1,54 @@
+using System.ComponentModel.DataAnnotations;
+
+namespace WCS.Service.Entity
+{
+    /// <summary>
+    /// 获取入库任务请求实体
+    /// </summary>
+    public class I_WCS_GetInTaskRequest
+    {
+        /// <summary>
+        /// 容器编号
+        /// </summary>
+        [Required(ErrorMessage = "{0} 不可为空")]
+        public string ContainerBarCode { get; set; }
+
+        /// <summary>
+        /// 容器类型
+        /// </summary>
+        [Required(ErrorMessage = "{0} 不可为空")]
+        public int ContainerType { get; set; }
+
+        /// <summary>
+        /// 物料条码
+        /// </summary>
+        public string MatBarCode { get; set; }
+
+        /// <summary>
+        /// 仓库编码
+        /// </summary>
+        [Required(ErrorMessage = "{0} 不可为空")]
+        public string WareHouseId { get; set; }
+
+        /// <summary>
+        /// 设备编号
+        /// </summary>
+        [Required(ErrorMessage = "{0} 不可为空")]
+        public string EquipmentNo { get; set; }
+
+        /// <summary>
+        /// 目标位置
+        /// </summary>
+        public string EndPostion { get; set; }
+
+        /// <summary>
+        /// 货叉(直接申请货位使用)
+        /// </summary>
+        public int ForkNum { get; set; }
+
+        public string Memo1 { get; set; }
+        public string Memo2 { get; set; }
+        public string Memo3 { get; set; }
+        public string Memo4 { get; set; }
+    }
+}

+ 24 - 0
WCS.WebApi/WMS/Request/I_WCS_GetMoveTaskRequest.cs

@@ -0,0 +1,24 @@
+using System;
+using System.Collections.Generic;
+using System.ComponentModel.DataAnnotations;
+using System.Text;
+
+namespace WCS.Service.Entity
+{
+    public class I_WCS_GetMoveTaskRequest
+    {
+        /// <summary>
+        /// WMS任务号
+        /// </summary>
+        [Required(ErrorMessage = "{0} 不可为空")]
+        public string WMSTaskNum { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public string Memo1 { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public string Memo2 { get; set; }
+    }
+}

+ 51 - 0
WCS.WebApi/WMS/Request/I_WCS_GetOutTaskRequest.cs

@@ -0,0 +1,51 @@
+using System;
+using System.Collections.Generic;
+using System.ComponentModel.DataAnnotations;
+using System.Text;
+
+namespace WCS.Service.Entity
+{
+    /// <summary>
+    /// 获取出库任务请求实体
+    /// </summary>
+    public class I_WCS_GetOutTaskRequest
+    {
+        /// <summary>
+        /// 出库位置
+        /// </summary>
+        [Required(ErrorMessage = "{0} 不可为空")]
+        public string OutEndPostion { get; set; }
+        /// <summary>
+        /// 出库类型(0.无效参数;1.物料出库;2.空托盘出库;3.空铁架出库;)
+        /// </summary>
+        [Required(ErrorMessage = "{0} 不可为空")]
+        public int OutType { get; set; }
+        /// <summary>
+        /// 仓库编码
+        /// </summary>
+        [Required(ErrorMessage = "{0} 不可为空")]
+        public string WareHouseId { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public string Memo1 { get; set; }
+        /// <summary>
+        /// 备用 空托盘类型0,1,2,3
+        /// </summary>
+        public string Memo2 { get; set; } 
+       
+
+        /// <summary>
+        /// OutId
+        /// </summary>
+        public string OutId { get; set; }
+        /// <summary>
+        /// 熟化时间(小时:10,16)
+        /// </summary>
+        public decimal TASK_MatureDate { get; set; }
+        /// <summary>
+        /// 熟化温度(小数)
+        /// </summary>
+        public decimal TASK_MatureTemperat { get; set; }
+    }
+}

+ 27 - 0
WCS.WebApi/WMS/Request/I_WCS_GetTunnelListRequest.cs

@@ -0,0 +1,27 @@
+using System.Collections.Generic;
+using System.ComponentModel.DataAnnotations;
+
+namespace WCS.Service.Entity
+{
+    /// <summary>
+    /// 获取产品巷道信息请求参数
+    /// </summary>
+    public class I_WCS_GetTunnelListRequest
+    {
+        /// <summary>
+        /// 任务组标识
+        /// </summary>
+        [Required(ErrorMessage = "{0} 不可为空")]
+        public List<string> WMSTaskNum { get; set; }
+
+        /// <summary>
+        /// 备用
+        /// </summary>s
+        public string Memo1 { get; set; }
+
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public string Memo2 { get; set; }
+    }
+}

+ 51 - 0
WCS.WebApi/WMS/Request/I_WCS_GetWareCellRequest.cs

@@ -0,0 +1,51 @@
+using System.ComponentModel.DataAnnotations;
+
+namespace WCS.Service.Entity
+{
+    /// <summary>
+    /// 分配货位请求实体
+    /// </summary>
+    public class I_WCS_GetWareCellRequest
+    {
+        /// <summary>
+        /// WMS任务号
+        /// </summary>
+        [Required(ErrorMessage = "{0} 不可为空")]
+        public string WMSTaskNum { get; set; }
+
+        /// <summary>
+        /// 巷道号
+        /// </summary>
+        public string TunnelNum { get; set; }
+
+        /// <summary>
+        /// 取货地点设备编号
+        /// </summary>
+        [Required(ErrorMessage = "{0} 不可为空")]
+        public string PickUpEquipmentNo { get; set; }
+
+        /// <summary>
+        /// 货叉(1,货叉1(左);2,货叉2(右))
+        /// </summary>
+        public WareCellForkNum ForkNum { get; set; }
+
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public string Memo1 { get; set; }
+
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public string Memo2 { get; set; }
+    }
+
+    /// <summary>
+    /// 申请货位任务对应的货叉
+    /// </summary>
+    public enum WareCellForkNum : int
+    {
+        货叉1 = 1,
+        货叉2 = 2,
+    }
+}

+ 32 - 0
WCS.WebApi/WMS/Request/I_WCS_GetWeightRequest.cs

@@ -0,0 +1,32 @@
+using System;
+using System.Collections.Generic;
+using System.ComponentModel.DataAnnotations;
+using System.Text;
+
+namespace WCS.Service.Entity
+{
+    /// <summary>
+    /// 称重信息上传请求参数
+    /// </summary>
+    public class I_WCS_GetWeightRequest
+    {
+        /// <summary>
+        /// WMS任务号
+        /// </summary>
+        [Required(ErrorMessage = "{0} 不可为空")]
+        public string WMSTaskNum { get; set; }
+        /// <summary>
+        /// 重量
+        /// </summary>
+        [Required(ErrorMessage = "{0} 不可为空")]
+        public decimal Weight { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public string Memo1 { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public string Memo2 { get; set; }
+    }
+}

+ 25 - 0
WCS.WebApi/WMS/Request/I_WCS_PutDevInfoRequest.cs

@@ -0,0 +1,25 @@
+using System;
+using System.Collections.Generic;
+using System.Text;
+
+namespace WCS.Service.Entity
+{
+    /// <summary>
+    /// 传递设备信息请求实体
+    /// </summary>
+    public class I_WCS_PutDevInfoRequest
+    {
+        //设备编号
+        public string STA_EQUIPMENTNO { get; set; }
+        //故障代码
+        public string STA_ALARMS { get; set; }
+        //故障信息
+        public string STA_ALARMSMSG { get; set; }
+        //PLC信息
+        public string STA_DATA { get; set; }
+    }
+    public class I_WCS_PutDevInfoRequestDto : I_WCS_PutDevInfoRequest
+    {
+ 
+    }
+}

+ 125 - 0
WCS.WebApi/WMS/Request/I_WCS_PutTaskStepRequest.cs

@@ -0,0 +1,125 @@
+using System;
+using System.ComponentModel.DataAnnotations;
+
+namespace WCS.Service.Entity
+{
+    public class I_WCS_PutTaskStepRequest
+    {
+        /// <summary>
+        /// WMS任务号
+        /// </summary>
+        [Required(ErrorMessage = "{0} 不可为空")]
+        public string WMSTaskNum { get; set; }
+
+        /// <summary>
+        /// 任务状态
+        /// </summary>
+        [Required(ErrorMessage = "{0} 不可为空")]
+        public int TaskStatus { get; set; }
+
+        /// <summary>
+        /// WCS操作人名称
+        /// </summary>
+        [Required(ErrorMessage = "{0} 不可为空")]
+        public string WCSUpdateName { get; set; }
+
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public string Memo1 { get; set; }
+
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public string Memo2 { get; set; }
+    }
+
+    public class I_WCS_TASKRequest
+    {
+        public int TASK_NO { get; set; }
+
+        /// <summary>
+        /// WMS任务号
+        /// </summary>
+        public string TASK_WMSNO { get; set; }
+
+        public int TASK_COMTYPE { get; set; }
+        public string TASK_SYSTYPE { get; set; }
+        public string TASK_POSIDFROM { get; set; }
+        public string TASK_POSIDCUR { get; set; }
+
+        public string TASK_POSIDNEXT { get; set; }
+        public string TASK_POSIDTO { get; set; }
+        public string TASK_POSIDMOVE { get; set; }
+        public int TASK_PRIORITY { get; set; }
+        public int TASK_WKSTATUS { get; set; }
+        public string TASK_WHID { get; set; }
+        public string TASK_ADDUSERNO { get; set; }
+        public DateTime TASK_ADDDATETIME { get; set; }
+        public string TASK_EDITUSERNO { get; set; }
+        public DateTime TASK_EDITDATETIME { get; set; }
+        public string TASK_NOTES { get; set; }
+        public string TASK_SRMNO { get; set; }
+
+        /// <summary>
+        /// rgv编号
+        /// </summary>
+        public string TASK_RGVNO { get; set; }
+
+        public int TASK_ORDERTYPE { get; set; }
+        public string TASK_BOXBARCODE { get; set; }
+
+        /// <summary>
+        /// 起始巷道号
+        /// </summary>
+        public string TASK_FromTunnelNum { get; set; }
+
+        /// <summary>
+        /// 目标巷道号
+        /// </summary>
+        public string TASK_EndTunnelNum { get; set; }
+
+        /// <summary>
+        /// 进入熟化房时间
+        /// </summary>
+        public DateTime? TASK_InMatureRoomDate { get; set; }
+
+        /// <summary>
+        /// 离开熟化房时间
+        /// </summary>
+        public DateTime? TASK_OutMatureRoomDate { get; set; }
+
+        /// <summary>
+        /// 预分配堆垛机出口输送线编号
+        /// </summary>
+        //public string TASK_SRMOUTCONVNO { get; set; }
+        public string TASK_ITEM1 { get; set; }
+
+        public string TASK_ITEM2 { get; set; }
+        public string TASK_ITEM3 { get; set; }
+        public string TASK_ITEM4 { get; set; }
+        public string TASK_ITEM5 { get; set; }
+        public string TASK_ITEM6 { get; set; }
+        public string TASK_ITEM7 { get; set; }
+        public string TASK_ITEM8 { get; set; }
+        public string TASK_ITEM9 { get; set; }
+        public string TASK_ITEM10 { get; set; }
+        public string TASK_ITEM11 { get; set; }
+        public string TASK_ITEM12 { get; set; }
+        public string TASK_ITEM13 { get; set; }
+        public string TASK_ITEM14 { get; set; }
+        public string TASK_ITEM15 { get; set; }
+
+        /// <summary>
+        /// 重量
+        /// </summary>
+        public decimal TASK_GrossWeight { get; set; }
+
+        /// <summary>
+        /// 是否缠膜(1.缠膜;0.不缠膜)
+        /// </summary>
+        public bool TASK_IsWrapFilm { get; set; }
+
+        public int Size { get; set; }
+    }
+}

+ 68 - 0
WCS.WebApi/WMS/Request/I_WMS_CreateTasksRequest.cs

@@ -0,0 +1,68 @@
+using System;
+using System.Collections.Generic;
+using System.Text;
+
+namespace WCS.Service.Entity
+{
+    public class I_WMS_CreateTasksRequest
+    {
+        public string WMSTaskNum { get; set; }
+        /// <summary>
+        /// 任务类型
+        /// </summary>
+        public int TaskType { get; set; }
+        /// <summary>
+        /// 任务状态
+        /// </summary>
+        public int TaskState { get; set; }
+        /// <summary>
+        /// 起点地址
+        /// </summary>
+        public string FromLocation { get; set; }
+        /// <summary>
+        /// 行
+        /// </summary>
+        public int FromRow { get; set; }
+        /// <summary>
+        /// 列
+        /// </summary>
+        public int FromColomn { get; set; }
+        /// <summary>
+        /// 层
+        /// </summary>
+        public int FromLayer { get; set; }
+        /// <summary>
+        /// 巷道号
+        /// </summary>
+        public string FromTunnelNum { get; set; }
+        /// <summary>
+        /// 目标地址
+        /// </summary>
+        public string EndLocation { get; set; }
+        /// <summary>
+        /// 行
+        /// </summary>
+        public int EndRow { get; set; }
+        /// <summary>
+        /// 列
+        /// </summary>
+        public int EndColomn { get; set; }
+        /// <summary>
+        /// 层
+        /// </summary>
+        public int EndLayer { get; set; }
+        /// <summary>
+        /// 巷道号
+        /// </summary>
+        public string EndTunnelNum { get; set; }
+        /// <summary>
+        /// 仓库名称
+        /// </summary>
+        public string WareHouseName { get; set; }
+        /// <summary>
+        /// 容器条码
+        /// </summary>
+        public string ContainerBarCode { get; set; }
+        public string UserName { get; set; }
+    }
+}

+ 16 - 0
WCS.WebApi/WMS/Request/PVCSemiFinishedProductReBackRequest.cs

@@ -0,0 +1,16 @@
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Threading.Tasks;
+
+namespace WCS.Service.Entity
+{
+    public class PVCSemiFinishedProductReBackRequest
+    {
+        public string ContainerCode { get; set; }
+        public decimal Quantity { get; set; }
+        public string Remark { get; set; }
+        public string BarCode { get; set; }
+    }
+}

+ 45 - 0
WCS.WebApi/WMS/Response/GetProductInfoResponse.cs

@@ -0,0 +1,45 @@
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Threading.Tasks;
+
+namespace WCS.Service.Entity
+{
+    public class GetProductInfoResponse : WcsContractApiResponse
+    {
+
+        public string BarCode { get; set; }
+        /// <summary>
+        /// 直径
+        /// </summary>
+        public decimal Diameter { get; set; }
+
+        /// <summary>
+        /// 重量
+        /// </summary>
+        public decimal Weight { get; set; }
+
+        /// <summary>
+        /// 高度
+        /// </summary>
+        public decimal Height { get; set; }
+
+        /// <summary>
+        /// 子托盘类型(0无需自托盘 1 子托盘1 2子托盘2 3子托盘3)
+        /// </summary>
+        public short ChildContainerType { get; set; }
+        /// <summary>
+        /// 载重卷数
+        /// </summary>
+        public short LoadCount { get; set; }
+
+        public int DocId { get; set; }
+
+        public short ProLine { get; set; }
+        /// <summary>
+        /// 是否尾盘(0否,1是)
+        /// </summary>
+        public int IsLeft { get; set; }
+    }
+}

+ 33 - 0
WCS.WebApi/WMS/Response/I_WCS_GetExcTaskResponse.cs

@@ -0,0 +1,33 @@
+using System;
+using System.Collections.Generic;
+using System.Text;
+
+namespace WCS.Service.Entity
+{
+    /// <summary>
+    /// 获取异常任务响应实体
+    /// </summary>
+    public class I_WCS_GetExcTaskResponse: WcsContractApiResponse
+    {
+        /// <summary>
+        /// 结果
+        /// </summary>
+        public new bool ResType { get; set; }
+        /// <summary>
+        /// 消息
+        /// </summary>
+        public new string ResMessage { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public new string Memo1 { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public new string Memo2 { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public new string Memo3 { get; set; }
+    }
+}

+ 68 - 0
WCS.WebApi/WMS/Response/I_WCS_GetInTaskResponse.cs

@@ -0,0 +1,68 @@
+using System.Collections.Generic;
+
+namespace WCS.Service.Entity
+{
+    public class I_WCS_GetInTaskResponse : WcsContractApiResponse
+    {
+        /// <summary>
+        /// 结果
+        /// </summary>
+        public new bool ResType { get; set; }
+
+        /// <summary>
+        ///
+        /// </summary>
+        public new string ResMessage { get; set; } = "";
+
+        public List<I_WCS_GetInTaskResponseItem> TaskList { get; set; }
+    }
+
+    public class I_WCS_GetInTaskResponseItem
+    {
+        /// <summary>
+        /// WMS任务号
+        /// </summary>
+        public string WMSTaskNum { get; set; } = "0";
+
+        /// <summary>
+        /// 任务组标识
+        /// </summary>
+        public string TaskGroupKey { get; set; } = "0";
+
+        /// <summary>
+        /// 任务类型(1:入库2:出库3:移库4:移动(搬运) 5:异常)
+        /// </summary>
+        public int TaskType { get; set; }
+
+        /// <summary>
+        /// 仓库名称
+        /// </summary>
+        public string WareHouseName { get; set; } = "";
+
+        /// <summary>
+        /// 入库巷道(集合巷道,由WCS自行判断入到哪一个巷道,最前面的最优先。)
+        /// </summary>
+        public string TunnelNum { get; set; } = "";
+
+        /// <summary>
+        /// 目标位置(入库该地址为srm.如果是移动任务,该地址为WCS传递的目标位置。)
+        /// </summary>
+        public string EndPostion { get; set; } = "";
+
+        public int Priority { get; set; } = 0;
+
+        /// <summary>
+        /// 产品编码(半成品入库使用)
+        /// </summary>
+        public string ContainerCode { get; set; } = "";
+
+        /// <summary>
+        /// 0默认值  1载货  2空盘(包含一个托盘或一摞两种情况)
+        /// </summary>
+        public int ContainerType { get; set; } = 0;
+
+        public string Memo1 { get; set; } = "";
+        public string Memo2 { get; set; } = "";
+        public string Memo3 { get; set; } = "";
+    }
+}

+ 86 - 0
WCS.WebApi/WMS/Response/I_WCS_GetMoveTaskResponse.cs

@@ -0,0 +1,86 @@
+using System;
+using System.Collections.Generic;
+using System.Text;
+
+namespace WCS.Service.Entity
+{
+    public class I_WCS_GetMoveTaskResponse : WcsContractApiResponse
+    {
+        /// <summary>
+        /// 结果
+        /// </summary>
+        public new int ResType { get; set; }
+        /// <summary>
+        /// 消息
+        /// </summary>
+        public new string ResMessage { get; set; }
+        /// <summary>
+        /// WMS任务号
+        /// </summary>
+        public string WMSTaskNum { get; set; }
+        /// <summary>
+        /// 任务类型
+        /// </summary>
+        public int TaskType { get; set; }
+        /// <summary>
+        /// 移库起始货位
+        /// </summary>
+        public string MoveStartWareCell { get; set; }
+        /// <summary>
+        /// 行
+        /// </summary>
+        public int FromRow { get; set; }
+        /// <summary>
+        /// 列
+        /// </summary>
+        public int FromColomn { get; set; }
+        /// <summary>
+        /// 层
+        /// </summary>
+        public int FromLayer { get; set; }
+        /// <summary>
+        /// 巷道号
+        /// </summary>
+        public string FromTunnelNum { get; set; }
+        /// <summary>
+        /// 移库目标货位
+        /// </summary>
+        public string MoveEndWareCell { get; set; }
+        /// <summary>
+        /// 行
+        /// </summary>
+        public int EndRow { get; set; }
+        /// <summary>
+        /// 列
+        /// </summary>
+        public int EndColomn { get; set; }
+        /// <summary>
+        /// 层
+        /// </summary>
+        public int EndLayer { get; set; }
+        /// <summary>
+        /// 巷道号
+        /// </summary>
+        public string EndTunnelNum { get; set; }
+        /// <summary>
+        /// 仓库名称
+        /// </summary>
+        public string WareHouseName { get; set; }
+        /// <summary>
+        /// 容器条码
+        /// </summary>
+        public string ContainerBarCode { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public new string Memo1 { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public new string Memo2 { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public new string Memo3 { get; set; }
+    }
+}

+ 136 - 0
WCS.WebApi/WMS/Response/I_WCS_GetOutTaskResponse.cs

@@ -0,0 +1,136 @@
+using System.Collections.Generic;
+
+namespace WCS.Service.Entity
+{
+    /// <summary>
+    /// 获取出库任务返回结果
+    /// </summary>
+    public class I_WCS_GetOutTaskResponse : WcsContractApiResponse
+    {
+        /// <summary>
+        /// 结果
+        /// </summary>
+        public new bool ResType { get; set; }
+
+        /// <summary>
+        /// 消息
+        /// </summary>
+        public new string ResMessage { get; set; }
+
+        /// <summary>
+        /// 返回任务
+        /// </summary>
+        public List<I_WCS_GetOutTaskResponseSingle> WMSTasks { get; set; }
+    }
+
+    /// <summary>
+    /// 返回任务项
+    /// </summary>
+    public class I_WCS_GetOutTaskResponseSingle
+    {
+        /// <summary>
+        /// WMS任务号
+        /// </summary>
+        public string WMSTaskNum { get; set; }
+
+        /// <summary>
+        /// 任务类型(1:入库2:出库3:移库4:移动(搬运) 5:异常)
+        /// </summary>
+        public int TaskType { get; set; }
+
+        /// <summary>
+        /// 出库货位
+        /// </summary>
+        public string OutWareCellNo { get; set; }
+
+        /// <summary>
+        /// 仓库名称
+        /// </summary>
+        public string WareHouseName { get; set; }
+
+        /// <summary>
+        /// 容器条码
+        /// </summary>
+        public string ContainerBarCode { get; set; }
+
+        /// <summary>
+        /// 行
+        /// </summary>
+        public int Row { get; set; }
+
+        /// <summary>
+        /// 列
+        /// </summary>
+        public int Colomn { get; set; }
+
+        /// <summary>
+        /// 层
+        /// </summary>
+        public int Layer { get; set; }
+
+        /// <summary>
+        /// 巷道号
+        /// </summary>
+        public string TunnelNum { get; set; }
+
+        /// <summary>
+        /// 站台号  堆垛机放货站台
+        /// </summary>
+        public string Memo1 { get; set; } = "";
+
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public string Memo2 { get; set; } = "";
+
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public string Memo3 { get; set; } = "";
+
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public string Memo4 { get; set; } = "";
+
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public string Memo5 { get; set; } = "";
+
+        /// <summary>
+        /// 机械手:子托盘的尺寸编码
+        /// </summary>
+        public string PalletizingSonTraySize { get; set; }
+
+        /// <summary>
+        /// 机械手:码垛的箱子尺寸编码
+        /// </summary>
+        public string PalletizingBoxSize { get; set; }
+
+        /// <summary>
+        /// 子托盘颜色编号(1蓝:,2:白,3:绿)
+        /// </summary>
+        public int SonTrayColorNo { get; set; }
+
+        /// <summary>
+        /// 垛型代码
+        /// </summary>
+        public int TASK_STACKINGTYPE { get; set; }
+
+        /// <summary>
+        /// 整箱毛重
+        /// </summary>
+        public decimal TASK_WEIGHT { get; set; }
+
+        /// <summary>
+        /// 熟化时长
+        /// </summary>
+        public decimal MatureDateLength { get; set; }
+
+        /// <summary>
+        /// 卷长度
+        /// </summary>
+        public decimal Length { get; set; }
+    }
+}

+ 39 - 0
WCS.WebApi/WMS/Response/I_WCS_GetTunnelListResponse.cs

@@ -0,0 +1,39 @@
+using System;
+using System.Collections.Generic;
+using System.Text;
+
+namespace WCS.Service.Entity
+{
+    public class I_WCS_GetTunnelListResponse : WcsContractApiResponse
+    {
+        /// <summary>
+        /// 任务组ID
+        /// </summary>
+        public string WMSTaskGroupKey { get; set; }
+
+        /// <summary>
+        /// 结果
+        /// </summary>
+        public new bool ResType { get; set; }
+        /// <summary>
+        /// 消息
+        /// </summary>
+        public new string ResMessage { get; set; }
+        /// <summary>
+        /// 巷道号集合
+        /// </summary>
+        public string TunnelNum { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public new string Memo1 { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public new string Memo2 { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public new string Memo3 { get; set; }
+    }
+}

+ 53 - 0
WCS.WebApi/WMS/Response/I_WCS_GetWareCellResponse.cs

@@ -0,0 +1,53 @@
+using System;
+using System.Collections.Generic;
+using System.Text;
+
+namespace WCS.Service.Entity
+{
+    /// <summary>
+    /// 分配货位响应实体
+    /// </summary>
+    public class I_WCS_GetWareCellResponse : WcsContractApiResponse
+    {
+        /// <summary>
+        /// 结果
+        /// </summary>
+        public new bool ResType { get; set; }
+        /// <summary>
+        /// 消息
+        /// </summary>
+        public new string ResMessage { get; set; }
+        /// <summary>
+        /// 货位号
+        /// </summary>
+        public string CellNo { get; set; }
+        /// <summary>
+        /// 巷道号
+        /// </summary>
+        public string TunnelNum { get; set; }
+        /// <summary>
+        /// 行
+        /// </summary>
+        public short Row { get; set; }
+        /// <summary>
+        /// 列
+        /// </summary>
+        public short Colomn { get; set; }
+        /// <summary>
+        /// 层
+        /// </summary>
+        public short Layer { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public new string Memo1 { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public new string Memo2 { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public new string Memo3 { get; set; }
+    }
+}

+ 30 - 0
WCS.WebApi/WMS/Response/I_WCS_GetWeightResponse.cs

@@ -0,0 +1,30 @@
+using System;
+using System.Collections.Generic;
+using System.Text;
+
+namespace WCS.Service.Entity
+{
+    public class I_WCS_GetWeightResponse : WcsContractApiResponse
+    {
+        /// <summary>
+        /// 结果
+        /// </summary>
+        public new bool ResType { get; set; }
+        /// <summary>
+        /// 消息
+        /// </summary>
+        public new string ResMessage { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public new string Memo1 { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public new string Memo2 { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public new string Memo3 { get; set; }
+    }
+}

+ 33 - 0
WCS.WebApi/WMS/Response/I_WCS_PutDevInfoResponse.cs

@@ -0,0 +1,33 @@
+using System;
+using System.Collections.Generic;
+using System.Text;
+
+namespace WCS.Service.Entity
+{
+    /// <summary>
+    /// 传递设备信息响应实体
+    /// </summary>
+    public class I_WCS_PutDevInfoResponse : WcsContractApiResponse
+    {
+        /// <summary>
+        /// 结果
+        /// </summary>
+        public new bool ResType { get; set; }
+        /// <summary>
+        /// 消息
+        /// </summary>
+        public new string ResMessage { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public new string Memo1 { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public new string Memo2 { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public new string Memo3 { get; set; }
+    }
+}

+ 38 - 0
WCS.WebApi/WMS/Response/I_WCS_PutTaskStepResponse.cs

@@ -0,0 +1,38 @@
+using System;
+using System.Collections.Generic;
+using System.Text;
+
+namespace WCS.Service.Entity
+{
+    /// <summary>
+    /// 更新任务进程响应实体
+    /// </summary>
+    public class I_WCS_PutTaskStepResponse : WcsContractApiResponse
+    {
+        /// <summary>
+        /// 结果
+        /// </summary>
+        public new bool ResType { get; set; }
+        /// <summary>
+        /// 消息
+        /// </summary>
+        public new string ResMessage { get; set; }
+        /// <summary>
+        /// WMS任务号
+        /// </summary>
+        public string WMSTaskNum { get; set; } = "0";
+
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public new string Memo1 { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public new string Memo2 { get; set; }
+        /// <summary>
+        /// 备用
+        /// </summary>
+        public new string Memo3 { get; set; }
+    }
+}

+ 41 - 0
WCS.WebApi/WMS/Response/Result.cs

@@ -0,0 +1,41 @@
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Threading.Tasks;
+
+namespace WCS.Service.Entity
+{
+    public class Result
+    {
+        public const int Success = 200;
+        public const int Error = 500;
+
+        public int StatusCode { get; set; }
+
+        public string Message { get; set; }
+
+        public string Exception { get; set; }
+
+        public Result()
+        {
+            this.StatusCode = Success;
+            this.Message = "操作成功";
+        }
+    }
+
+    public class Result<T> : Result
+    {
+        public T ReturnValue { get; set; }
+
+        public Result()
+        {
+        }
+
+        public Result(T result)
+            : base()
+        {
+            this.ReturnValue = result;
+        }
+    }
+}

+ 12 - 0
WCS.WebApi/WMS/Response/TunnelCountTemp.cs

@@ -0,0 +1,12 @@
+using System;
+using System.Collections.Generic;
+using System.Text;
+
+namespace WCS.Service.Entity
+{
+    public class TunnelCountTemp
+    {
+        public string Tunnel { get; set; }
+        public int Count { get; set; }
+    }
+}

+ 15 - 0
WCS.WebApi/WMS/Response/WcsContractApiResponse.cs

@@ -0,0 +1,15 @@
+using System;
+using System.Collections.Generic;
+using System.Text;
+
+namespace WCS.Service.Entity
+{
+    public class WcsContractApiResponse
+    {
+        public bool ResType { get; set; }
+        public string ResMessage { get; set; }
+        public string Memo1 { get; set; }
+        public string Memo2 { get; set; }
+        public string Memo3 { get; set; }
+    }
+}

+ 374 - 0
WCS.WebApi/WMS/WMS.cs

@@ -0,0 +1,374 @@
+using Logs;
+using Newtonsoft.Json;
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using WCS.Service.Entity;
+
+namespace WCS.Service
+{
+    public class WMS
+    {
+        private const string Url = "http://192.168.249.150:8026";
+
+        //private static string Url = "http://127.0.0.1:8026";
+        private const string WareHouseId = "opphouse";
+
+        /// <summary>
+        /// 向WMS获取入库任务 一次单卷
+        /// </summary>
+        /// <param name="barcode">产品条码</param>
+        /// <param name="devCode">设备条码</param>
+        /// <param name="getTunnel"></param>
+        /// <returns></returns>
+        /// <exception cref="Exception"></exception>
+        public static List<I_WCS_GetInTaskResponseItem> I_WCS_GetInTask(string barcode, string devCode, bool getTunnel = false)
+        {
+            var data = JsonConvert.SerializeObject(new List<I_WCS_GetInTaskRequest>()
+            {
+                new I_WCS_GetInTaskRequest(){
+                     ContainerBarCode = barcode,
+                     WareHouseId = WareHouseId,
+                     EquipmentNo = devCode,
+                     Memo1 = getTunnel ? "1" : "" //1:分巷道  2:分货位
+                }
+            });
+            var res = APICaller.CallApi<I_WCS_GetInTaskResponse>(Url + "/api/Task/I_WCS_UnifiedInterface", new InterfaceParameters
+            {
+                Name = "I_WCS_GetInTask",
+                Parameters = data,
+                ParametersMD5 = data.GetMD5()
+            });
+            if (res.ResType) return res.TaskList;
+            TaskException(devCode, res.ResMessage);
+            throw new WarnException(res.ResMessage);
+        }
+
+        /// <summary>
+        ///  向WMS获取入库任务 一次双卷
+        /// </summary>
+        /// <param name="barcode1">产品1条码</param>
+        /// <param name="devCode1">设备1编号</param>
+        /// <param name="getTunnel1">产品1是否直接分配巷道</param>
+        /// <param name="barcode2">产品2条码</param>
+        /// <param name="devCode2">设备2编号</param>
+        /// <param name="getTunnel2">产品2是否直接分配巷道</param>
+        /// <exception cref="WarnException"></exception>
+        /// <returns></returns>
+        public static List<I_WCS_GetInTaskResponseItem> I_WCS_GetInTask(string barcode1, string devCode1, string barcode2, string devCode2, bool getTunnel1 = false, bool getTunnel2 = false)
+        {
+            if (!Configs.Any(SystemMode.虚拟PLC))
+            {
+                var data = JsonConvert.SerializeObject(new List<I_WCS_GetInTaskRequest>()
+            {
+                new(){
+                     ContainerBarCode = barcode1,
+                     WareHouseId = WareHouseId,
+                     EquipmentNo = devCode1,
+                     Memo1 = getTunnel1 ? "1" : "" //1:分巷道  2:分货位
+                },
+                new(){
+                     ContainerBarCode = barcode2,
+                     WareHouseId = WareHouseId,
+                     EquipmentNo = devCode2,
+                     Memo1 = getTunnel2 ? "1" : "" //1:分巷道  2:分货位
+                },
+            });
+                var res = APICaller.CallApi<I_WCS_GetInTaskResponse>(Url + "/api/Task/I_WCS_UnifiedInterface", new InterfaceParameters
+                {
+                    Name = "I_WCS_GetInTask",
+                    Parameters = data,
+                    ParametersMD5 = data.GetMD5()
+                });
+                if (res.ResType) return res.TaskList;
+                TaskException($"G{devCode1}", res.ResMessage);
+                throw new WarnException(res.ResMessage);
+            }
+            return new List<I_WCS_GetInTaskResponseItem>()
+            {
+                new I_WCS_GetInTaskResponseItem(){
+                    WMSTaskNum="315199",
+                    TaskType=1,
+                    WareHouseName="OPP立库",
+                    TunnelNum="",
+                    EndPostion="srm",
+                    ContainerCode=barcode1,
+                    ContainerType=0
+                },
+                new I_WCS_GetInTaskResponseItem() {
+                    WMSTaskNum="315200",
+                    TaskType=1,
+                    WareHouseName="OPP立库",
+                    TunnelNum="",
+                    EndPostion="srm",
+                    ContainerCode=barcode2,
+                    ContainerType=0
+                },
+            };
+        }
+
+        /// <summary>
+        /// 分配货位
+        /// </summary>
+        /// <param name="wmstaskid">WMS任务ID</param>
+        /// <param name="tunnel">巷道</param>
+        /// <param name="device">设备号</param>
+        /// <param name="ForkNum">申请任务对应的货叉</param>
+        /// <exception cref="WarnException"></exception>
+        /// <returns></returns>
+        public static I_WCS_GetWareCellResponse GetLocalIn(int wmstaskid, string tunnel, string device, WareCellForkNum ForkNum)
+        {
+            var data = JsonConvert.SerializeObject(new I_WCS_GetWareCellRequest
+            {
+                PickUpEquipmentNo = device,
+                TunnelNum = tunnel.Last().ToString(),
+                WMSTaskNum = wmstaskid.ToString(),
+                ForkNum = ForkNum
+            });
+            var res = APICaller.CallApi<I_WCS_GetWareCellResponse>(Url + "/api/Task/I_WCS_UnifiedInterface", new InterfaceParameters
+            {
+                Name = "I_WCS_GetWareCell",
+                Parameters = data,
+                ParametersMD5 = data.GetMD5()
+            });
+            if (res.ResType) return res;
+            TaskException(device, res.ResMessage);
+            throw new WarnException(res.ResMessage);
+        }
+
+        public static void UpdateTask(string POSIDNEXT, int wmstaskid, int status, int size = -1)
+        {
+            if (Configs.Any(SystemMode.虚拟PLC)) return;
+
+            var data = JsonConvert.SerializeObject(new List<I_WCS_TASKRequest>
+            {
+                new()
+                {
+                    TASK_WKSTATUS = status,
+                    TASK_WMSNO = wmstaskid.ToString(),
+                    TASK_POSIDNEXT=POSIDNEXT,
+                    Size=size
+                }
+            });
+            var res = APICaller.CallApi<List<I_WCS_PutTaskStepResponse>>(Url + "/api/Task/I_WCS_UnifiedInterface", new InterfaceParameters
+            {
+                Name = "I_WCS_PutTaskStep",
+                Parameters = data,
+                ParametersMD5 = data.GetMD5()
+            });
+            if (res == null || res.Count == 0)
+            {
+                throw new WarnException("I_WCS_PutTaskStep调用失败");
+            }
+            if (!res.First().ResType)
+                throw new WarnException(res.First().ResMessage);
+        }
+
+        public static GetProductInfoResponse GetProductInfo(string barcode, string dev)
+        {
+            var data = JsonConvert.SerializeObject(new GetProductInfoRequest
+            {
+                BarCode = barcode
+            });
+            var res = APICaller.CallApi<GetProductInfoResponse>(Url + "/api/Task/I_WCS_UnifiedInterface", new InterfaceParameters
+            {
+                Name = "GetProductInfo",
+                Parameters = data,
+                ParametersMD5 = data.GetMD5()
+            });
+            try
+            {
+                if (!res.ResType)
+                    throw new WarnException(res.ResMessage);
+                if (res.ChildContainerType is <= 0 or > 9)
+                    throw new WarnException("托盘类型错误");
+                if (res.LoadCount <= 0)
+                    throw new WarnException("最大组盘数量错误");
+                if (res.DocId == 0)
+                    throw new WarnException("单据ID错误");
+                if (res.ProLine is < 1 or > 9)
+                    throw new WarnException("产线编号" + res.ProLine + "错误");
+            }
+            catch (Exception ex)
+            {
+                TaskException(dev, ex.Message);
+                throw;
+            }
+            return res;
+        }
+
+        /// <summary>
+        /// 获取出库任务
+        /// </summary>
+        /// <param name="position">出库位置</param>
+        /// <param name="devCode">调用方法的设备号</param>
+        /// <returns></returns>
+        /// <exception cref="Exception"></exception>
+        public static List<I_WCS_GetOutTaskResponseSingle> GetOutTask(string position, string devCode)
+        {
+            var data = JsonConvert.SerializeObject(new I_WCS_GetOutTaskRequest
+            {
+                OutType = 1,
+                WareHouseId = WareHouseId,
+                OutEndPostion = position
+            });
+            var res = APICaller.CallApi<I_WCS_GetOutTaskResponse>(Url + "/api/Task/I_WCS_UnifiedInterface", new InterfaceParameters
+            {
+                Name = "I_WCS_GetOutTask",
+                Parameters = data,
+                ParametersMD5 = data.GetMD5()
+            });
+            if (!res.ResType)
+            {
+                TaskException(position, res.ResMessage);
+                throw new WarnException(res.ResMessage);
+            }
+
+            res.WMSTasks.ForEach(v =>
+            {
+                var tcode = "TY" + v.TunnelNum;
+
+                var tunnel = Device.Find(tcode);
+                //var next = tunnel.GetPath(devCode);
+                //v.Memo1 = next.CODE;
+                v.TunnelNum = tunnel.CODE;
+            });
+            return res.WMSTasks;
+        }
+
+        public static WcsContractApiResponse AutoBuildUpGroupStock(string containerCode, string barcode, string dev)
+        {
+            var res = APICaller.CallApi<WcsContractApiResponse>(Url + "/api/Task/AutoBuildUpGroupStock", new
+            {
+                ContainerCode = containerCode,
+                BarCode = barcode
+            });
+            if (res.ResType) return res;
+            TaskException(dev, res.ResMessage);
+            throw new WarnException(res.ResMessage);
+        }
+
+        /// <summary>
+        /// 获取巷道
+        /// </summary>
+        /// <param name="WMSTaskId">WMS任务号集合</param>
+        /// <param name="dev">请求设备号</param>
+        /// <returns></returns>
+        /// <exception cref="Exception"></exception>
+        public static I_WCS_GetTunnelListResponse GetTunnelList(List<string> WMSTaskId, string dev)
+        {
+            var data = JsonConvert.SerializeObject(new I_WCS_GetTunnelListRequest
+            {
+                WMSTaskNum = WMSTaskId
+            });
+            var res = APICaller.CallApi<I_WCS_GetTunnelListResponse>(Url + "/api/Task/I_WCS_UnifiedInterface", new InterfaceParameters
+            {
+                Name = "I_WCS_GetTunnelList",
+                Parameters = data,
+                ParametersMD5 = data.GetMD5()
+            });
+            if (res.ResType) return res;
+            TaskException(dev, res.ResMessage);
+            throw new WarnException(res.ResMessage);
+        }
+
+        public static void TaskException(string device, string exMsg)
+        {
+            if (exMsg == "接口调用中")
+                return;
+            System.Threading.Tasks.Task.Run(() =>
+            {
+                try
+                {
+                    var data = JsonConvert.SerializeObject(new I_WCS_GetExcTaskRequest
+                    {
+                        ExcCode = exMsg,
+                        EquipmentNo = device,
+                        ExcMessage = exMsg,
+                    });
+                    Console.WriteLine(device + ":" + exMsg);
+                    var res = APICaller.CallApi2<I_WCS_GetExcTaskResponse>(Url + "/api/Task/I_WCS_UnifiedInterface", new InterfaceParameters
+                    {
+                        Name = "I_WCS_GetExcTask",
+                        Parameters = data,
+                        ParametersMD5 = data.GetMD5()
+                    });
+                    InfoLog.INFO_I_WCS_GetExcTask(device + ":" + exMsg);
+                    if (!res.ResType) throw new WarnException(res.ResMessage);
+                }
+                catch (Exception)
+                {
+                }
+            });
+        }
+
+        private static List<I_WCS_PutDevInfoRequest> DevInfoList = new();
+
+        public static void DevInfo(string device, string exMsg)
+        {
+            DevInfoList.Add(new I_WCS_PutDevInfoRequest
+            {
+                STA_EQUIPMENTNO = device,
+                STA_ALARMSMSG = exMsg
+            });
+        }
+
+        public static void UploadDevInfo()
+        {
+            return;
+            try
+            {
+                var data = JsonConvert.SerializeObject(DevInfoList);
+                var res = APICaller.CallApi<I_WCS_PutDevInfoResponse>(Url + "/api/Task/I_WCS_UnifiedInterface", new InterfaceParameters
+                {
+                    Name = "I_WCS_GetExcTask",
+                    Parameters = data,
+                    ParametersMD5 = data.GetMD5()
+                });
+                if (!res.ResType)
+                    throw new WarnException(res.ResMessage);
+            }
+            catch (Exception ex)
+            {
+                InfoLog.INFO_WARN($"I_WCS_PutDevInfo接口调用失败:{ex.Message}");
+            }
+            finally
+            {
+                DevInfoList.Clear();
+            }
+        }
+
+        public static void UnBound(string barcode)
+        {
+            try
+            {
+                var res = APICaller.CallApi<I_WCS_GetTunnelListResponse>(Url + "/api/PDA/UnboundMwGroupStock", new
+                {
+                    containerCode = barcode
+                });
+            }
+            catch { }
+        }
+    }
+
+    /// <summary>
+    /// 调用接口传入参数
+    /// </summary>
+    public class InterfaceParameters
+    {
+        /// <summary>
+        /// 业务名 例:I_WCS_GetInTask
+        /// </summary>
+        public string Name { get; set; }
+
+        /// <summary>
+        /// 传入参数为Json
+        /// </summary>
+        public string Parameters { get; set; }
+
+        /// <summary>
+        /// 传入参数的唯一值
+        /// </summary>
+        public string ParametersMD5 { get; set; }
+    }
+}