using Admin.NET.Core.Service; using Admin.NET.Application.Entity; using Microsoft.AspNetCore.Http; using System.Data; using System.Web; using System.Text; using Furion.DatabaseAccessor; using MaxMind.GeoIP2.Responses; using Newtonsoft.Json; using static SKIT.FlurlHttpClient.Wechat.Api.Events.NotifyThirdFastRegisterBetaAppEvent.Types; namespace Admin.NET.Application; /// /// 适配记录服务 /// [ApiDescriptionSettings(ApplicationConst.SoftwareAdapterServiceGroupName, Order = 100)] public class RecordAdapterService : IDynamicApiController, ITransient { private readonly SqlSugarRepository _rep; private readonly SqlSugarRepository _repAdapterManagement; private readonly SqlSugarRepository _repAdapterCategories; private readonly SqlSugarRepository _repWmsRecordReceivingDelivery; private readonly SqlSugarRepository _repWmsStockQuanRep; public RecordAdapterService(SqlSugarRepository rep, SqlSugarRepository repAdapterManagement, SqlSugarRepository repAdapterCategories, SqlSugarRepository repWmsRecordReceivingDelivery, SqlSugarRepository repWmsStockQuanRep) { _rep = rep; _repAdapterManagement = repAdapterManagement; _repAdapterCategories = repAdapterCategories; _repWmsRecordReceivingDelivery = repWmsRecordReceivingDelivery; _repWmsStockQuanRep = repWmsStockQuanRep; } /// /// 分页查询适配记录 /// /// /// [HttpPost] [ApiDescriptionSettings(Name = "Page")] [Description("RecordAdapter/Page")] public async Task> Page(RecordAdapterInput input) { var query = CommonPageFilter(input); return await query.OrderBuilder(input, "", "Id").ToPagedListAsync(input.Page, input.PageSize); } /// /// 不分页查询适配记录 /// /// /// [HttpGet] [ApiDescriptionSettings(Name = "List")] [Description("RecordAdapter/List")] public async Task> List([FromQuery] RecordAdapterInput input) { var query = CommonPageFilter(input); return await query.OrderBuilder(input, "", "Id").Select().ToListAsync(); } /// /// 增加适配记录 /// /// /// [HttpPost] [ApiDescriptionSettings(Name = "Add")] [Description("RecordAdapter/Add")] public async Task Add(AddRecordAdapterInput input) { var entity = input.Adapt(); //重复性验证 await CheckExist(entity); await _rep.InsertAsync(entity); return entity.Id; } /// /// CC调用更改适配器记录状态 /// /// /// [HttpPost] [ApiDescriptionSettings(Name = "UpdateAdapterRecordByCC")] [Description("RecordAdapter/UpdateAdapterRecordByCC")] [AllowAnonymous] public async Task UpdateAdapterRecordByCC(UpdateAdapterRecordByCCInput input) { var entity = await _rep.AsQueryable().Where(p => input.RecordAdapterIdList.Contains(p.Id)).ToListAsync(); var RecordReceivingDeliveryIDList = new List(); var wmsRecordReceivingDelivery = new List(); var stockList = new List(); foreach (var item in entity) { var stockModel = new WmsStockQuan(); var BaoWen = new AdminResult(); try { item.DealWithStatus = AdapterLogDealWithEnum.已处理; BaoWen.Code = 200; BaoWen.Type = "success"; BaoWen.Time = DateTime.Now; item.AdapterReturnMassage = JsonConvert.SerializeObject(BaoWen); //item.EndingTime = DateTime.Now; //TimeSpan timeDifference = (TimeSpan)(item.CreateTime - item.EndingTime); //item.TimeDifference = (int)timeDifference.TotalSeconds; var wmsRecordReceivingDeliveryModel = await _repWmsRecordReceivingDelivery.GetFirstAsync(p => p.Id.ToString() == item.KeyCode); wmsRecordReceivingDeliveryModel.ErpVoucher = input.ErpVoucher; wmsRecordReceivingDeliveryModel.ErpPushStatus = ErpPushStatusEnum.发送完成; wmsRecordReceivingDeliveryModel.UpdateTime = DateTime.Now; wmsRecordReceivingDeliveryModel.UpdateUserName = "调度任务"; wmsRecordReceivingDelivery.Add(wmsRecordReceivingDeliveryModel); stockModel = await _repWmsStockQuanRep.GetFirstAsync(p => p.SNCode == wmsRecordReceivingDeliveryModel.SNCode); stockModel.ErpVoucher = input.ErpVoucher; stockList.Add(stockModel); } catch (Exception ex) { item.ErrMessage = ex.Message; item.DealWithStatus = AdapterLogDealWithEnum.处理失败; BaoWen.Message = ex.Message; BaoWen.Code = 500; BaoWen.Type = "error"; BaoWen.Time = DateTime.Now; item.AdapterReturnMassage = JsonConvert.SerializeObject(BaoWen); //ex.Message } finally { item.EndingTime = DateTime.Now; TimeSpan timeDifference = (TimeSpan)(item.CreateTime - item.EndingTime); item.TimeDifference = (int)timeDifference.TotalSeconds; item.PushCount++; } } var _tenant = _repWmsRecordReceivingDelivery.AsTenant(); try { await _tenant.BeginTranAsync(); await _repWmsRecordReceivingDelivery.UpdateRangeAsync(wmsRecordReceivingDelivery); await _repWmsStockQuanRep.UpdateRangeAsync(stockList); await _rep.UpdateRangeAsync(entity); await _tenant.CommitTranAsync(); } catch { await _tenant.RollbackTranAsync(); throw; } } /// /// CC调用更改适配器记录状态 /// /// /// [HttpPost] [ApiDescriptionSettings(Name = "UpdateAdapterRecordInfo")] [Description("RecordAdapter/UpdateAdapterRecordInfo")] [AllowAnonymous] public async Task UpdateAdapterRecordInfo(AdapterLogsInfoUpdateInput input) { var entity = await _rep.AsQueryable().Where(p => input.RecordAdapterIdList.Contains(p.Id)).ToListAsync(); var result = JsonConvert.DeserializeObject>(input.AdapterInputInfo); if (result != null) { foreach (var item in entity) { item.AdapterReturnMassage = input.AdapterInputInfo; item.ErrMessage = result.Message; if (result.Code != 200) { item.DealWithStatus = AdapterLogDealWithEnum.处理失败; } } await _rep.UpdateRangeAsync(entity); } } /// /// 删除适配记录 /// /// /// [HttpPost] [ApiDescriptionSettings(Name = "Delete")] [Description("RecordAdapter/Delete")] public async Task Delete(DeleteRecordAdapterInput input) { var entity = await _rep.GetFirstAsync(u => u.Id == input.Id) ?? throw Oops.Oh(ErrorCodeEnum.D1002); //await _rep.FakeDeleteAsync(entity); //假删除 await _rep.DeleteAsync(entity); //真删除 } /// /// 更新适配记录 /// /// /// [HttpPost] [ApiDescriptionSettings(Name = "Update")] [Description("RecordAdapter/Update")] public async Task Update(UpdateRecordAdapterInput input) { var entity = input.Adapt(); //重复性验证 await CheckExist(entity, true); await _rep.AsUpdateable(entity).IgnoreColumns(ignoreAllNullColumns: true).ExecuteCommandAsync(); } /// /// 取消适配记录 /// /// /// [HttpPost] [ApiDescriptionSettings(Name = "Cancel")] [Description("RecordAdapter/Cancel")] public async Task Cancel(CancelAndCompletionInput input) { var model = await _rep.AsQueryable().FirstAsync(p => p.Id == input.Id); if (model == null) throw Oops.Oh("未查到当前适配器记录"); if (model.DealWithStatus != AdapterLogDealWithEnum.未处理 || model.DealWithStatus != AdapterLogDealWithEnum.处理失败) throw Oops.Oh("当前适配记录状态不可取消"); model.DealWithStatus = AdapterLogDealWithEnum.已取消; await _rep.UpdateAsync(model); } /// /// 强制完成适配记录 /// /// /// [HttpPost] [ApiDescriptionSettings(Name = "ForcedCompletion")] [Description("RecordAdapter/ForcedCompletion")] public async Task ForcedCompletion(CancelAndCompletionInput input) { var model = await _rep.AsQueryable().FirstAsync(p => p.Id == input.Id); if (model == null) throw Oops.Oh("未查到当前适配器记录"); if (model.DealWithStatus != AdapterLogDealWithEnum.未处理) throw Oops.Oh("当前适配记录状态不可强制完成"); model.DealWithStatus = AdapterLogDealWithEnum.强制完成; await _rep.UpdateAsync(model); } /// /// 重试 /// /// /// [HttpPost] [ApiDescriptionSettings(Name = "TryAgain")] [Description("RecordAdapter/TryAgain")] public async Task TryAgain(TryAgainInput input) { //将适配器记录中的执行失败的状态改为待执行 var adapterList = await _rep.AsQueryable().Where(p => input.IdList.Contains(p.Id)).ToListAsync(); if (adapterList.Count == 0) throw Oops.Oh("未查到当前适配器记录"); // if(adapterList.) foreach (var adapter in adapterList) { if (adapter.DealWithStatus != AdapterLogDealWithEnum.处理失败) throw Oops.Oh("当前适配器记录不可重试"); adapter.DealWithStatus = AdapterLogDealWithEnum.未处理; } await _rep.UpdateRangeAsync(adapterList); } /// /// 获取适配记录 /// /// /// [HttpGet] [ApiDescriptionSettings(Name = "Detail")] [Description("RecordAdapter/Detail")] public async Task Detail([FromQuery] QueryByIdRecordAdapterInput input) { return await _rep.GetFirstAsync(u => u.Id == input.Id); } #region 导入 /// /// Excel模板导入适配记录功能 /// /// Excel模板文件 /// 导入的记录数 [HttpPost] [ApiDescriptionSettings(Name = "ImportExcel")] [Description("RecordAdapter/ImportExcel")] public async Task ImportExcelAsync(IFormFile file) { int _HeadStartLine = 2;//第1行是说明,第2行是列名 int _DataStartLine = 3;//第3行开始是数据 DataTable importDataTable = ExcelUtil.ImportExcelToDataTable(file, _HeadStartLine, _DataStartLine); var addList = await CommonImport(importDataTable, _DataStartLine); await _rep.InsertRangeAsync(addList); return addList.Count; } /// /// DataTable转换实体对象列表 /// /// /// 模版列名开始行 /// private async Task> CommonImport(DataTable dataTable, int dataStartLine) { var details = new List(); int index = dataStartLine;//模版列名开始行 foreach (System.Data.DataRow row in dataTable.Rows) { index++; //导入模版定制化代码(替换模版使用) var addItem = new WmsAdapterRecord(); #region 定义变量 var _AdapterCategoryId = "";//适配器大类id var _CategoryName = "";//单据大类名称 var _AdapterName = "";//适配器名称 var _AdapterId = "";//适配器id var _AdapterMethodName = "";//适配器方法名称 var _RequestSoure = "";//请求来源 var _AdapterSID = "";//适配SID var _BeginTime = "";//开始时间 var _EndingTime = "";//结束时间 var _TimeDifference = "";//耗时 var _DealWithStatus = "";//处理状态 var _ErrMessage = "";//请求来源 var _AdapterInput = "";//适配参数 var _AdapterReturnMassage = "";//适配报文 #endregion #region 取值 _AdapterCategoryId = row["适配器大类id"]?.ToString(); _CategoryName = row["单据大类名称"]?.ToString(); _AdapterName = row["适配器名称"]?.ToString(); _AdapterId = row["适配器id"]?.ToString(); _AdapterMethodName = row["适配器方法名称"]?.ToString(); _RequestSoure = row["请求来源"]?.ToString(); _AdapterSID = row["适配SID"]?.ToString(); _BeginTime = row["开始时间"]?.ToString(); _EndingTime = row["结束时间"]?.ToString(); _TimeDifference = row["耗时"]?.ToString(); _DealWithStatus = row["处理状态"]?.ToString(); _ErrMessage = row["请求来源"]?.ToString(); _AdapterInput = row["适配参数"]?.ToString(); _AdapterReturnMassage = row["适配报文"]?.ToString(); #endregion #region 验证 if (string.IsNullOrEmpty(_AdapterCategoryId)) { throw Oops.Oh($"第{index}行[适配器大类id]{_AdapterCategoryId}不能为空!"); } if (!string.IsNullOrEmpty(_AdapterCategoryId)) { if (!long.TryParse(_AdapterCategoryId, out long outAdapterCategoryId) && !string.IsNullOrEmpty(_AdapterCategoryId)) { throw Oops.Oh($"第{index}行[适配器大类id]{_AdapterCategoryId}值不正确!"); } if (outAdapterCategoryId <= 0 && !string.IsNullOrEmpty(_AdapterCategoryId)) { throw Oops.Oh($"第{index}行[适配器大类id]{_AdapterCategoryId}值不能小于等于0!"); } else { addItem.AdapterCategoryId = outAdapterCategoryId; } } if (string.IsNullOrEmpty(_CategoryName)) { throw Oops.Oh($"第{index}行[单据大类名称]{_CategoryName}不能为空!"); } if (!string.IsNullOrEmpty(_CategoryName)) { addItem.CategoryName = (string)(_CategoryName.Trim()); } if (string.IsNullOrEmpty(_AdapterName)) { throw Oops.Oh($"第{index}行[适配器名称]{_AdapterName}不能为空!"); } if (!string.IsNullOrEmpty(_AdapterName)) { addItem.AdapterName = (string)(_AdapterName.Trim()); } if (string.IsNullOrEmpty(_AdapterId)) { throw Oops.Oh($"第{index}行[适配器id]{_AdapterId}不能为空!"); } if (!string.IsNullOrEmpty(_AdapterId)) { if (!long.TryParse(_AdapterId, out long outAdapterId) && !string.IsNullOrEmpty(_AdapterId)) { throw Oops.Oh($"第{index}行[适配器id]{_AdapterId}值不正确!"); } if (outAdapterId <= 0 && !string.IsNullOrEmpty(_AdapterId)) { throw Oops.Oh($"第{index}行[适配器id]{_AdapterId}值不能小于等于0!"); } else { addItem.AdapterId = outAdapterId; } } if (string.IsNullOrEmpty(_AdapterMethodName)) { throw Oops.Oh($"第{index}行[适配器方法名称]{_AdapterMethodName}不能为空!"); } if (!string.IsNullOrEmpty(_AdapterMethodName)) { addItem.AdapterMethodName = (string)(_AdapterMethodName.Trim()); } if (string.IsNullOrEmpty(_RequestSoure)) { throw Oops.Oh($"第{index}行[请求来源]{_RequestSoure}不能为空!"); } if (!string.IsNullOrEmpty(_RequestSoure)) { addItem.RequestSoure = (string)(_RequestSoure.Trim()); } if (string.IsNullOrEmpty(_AdapterSID)) { throw Oops.Oh($"第{index}行[适配SID]{_AdapterSID}不能为空!"); } if (!string.IsNullOrEmpty(_AdapterSID)) { addItem.AdapterSID = (string)(_AdapterSID.Trim()); } if (!string.IsNullOrEmpty(_BeginTime)) { addItem.BeginTime = Convert.ToDateTime(Convert.ToDateTime(_BeginTime.Trim()).ToShortDateString()); } if (!string.IsNullOrEmpty(_EndingTime)) { addItem.EndingTime = Convert.ToDateTime(Convert.ToDateTime(_EndingTime.Trim()).ToShortDateString()); } if (string.IsNullOrEmpty(_TimeDifference)) { throw Oops.Oh($"第{index}行[耗时]{_TimeDifference}不能为空!"); } if (!string.IsNullOrEmpty(_TimeDifference)) { //addItem.TimeDifference = (System.TimeSpan)(_TimeDifference.Trim()); } if (string.IsNullOrEmpty(_DealWithStatus)) { throw Oops.Oh($"第{index}行[处理状态]{_DealWithStatus}不能为空!"); } if (!string.IsNullOrEmpty(_DealWithStatus)) { Admin.NET.Application.AdapterLogDealWithEnum enumDealWithStatus = default(Admin.NET.Application.AdapterLogDealWithEnum); if (!Enum.TryParse(_DealWithStatus, out enumDealWithStatus) && !string.IsNullOrEmpty(_DealWithStatus)) { throw Oops.Oh($"第{index}行[处理状态]{_DealWithStatus}值不正确!"); } else { addItem.DealWithStatus = enumDealWithStatus; } } if (string.IsNullOrEmpty(_ErrMessage)) { throw Oops.Oh($"第{index}行[请求来源]{_ErrMessage}不能为空!"); } if (!string.IsNullOrEmpty(_ErrMessage)) { addItem.ErrMessage = (string)(_ErrMessage.Trim()); } if (string.IsNullOrEmpty(_AdapterInput)) { throw Oops.Oh($"第{index}行[适配参数]{_AdapterInput}不能为空!"); } if (!string.IsNullOrEmpty(_AdapterInput)) { addItem.AdapterInput = (string)(_AdapterInput.Trim()); } if (string.IsNullOrEmpty(_AdapterReturnMassage)) { throw Oops.Oh($"第{index}行[适配报文]{_AdapterReturnMassage}不能为空!"); } if (!string.IsNullOrEmpty(_AdapterReturnMassage)) { addItem.AdapterReturnMassage = (string)(_AdapterReturnMassage.Trim()); } #endregion details.Add(addItem); } //验重 await CheckExisitForImport(details); return details; } /// /// 根据版本下载适配记录的Excel导入模板 /// /// 下载的模板文件 [HttpGet] [ApiDescriptionSettings(Name = "DownloadExcelTemplate")] [Description("RecordAdapter/DownloadExcelTemplate")] public IActionResult DownloadExcelTemplate() { string _path = TemplateConst.EXCEL_TEMPLATEFILE_导入模版路径 + $"\\适配记录{TemplateConst.EXCEL_TEMPLATEFILE_导入模版名称后缀}.xlsx"; var fileName = HttpUtility.UrlEncode($"导入模板(适配记录).xlsx", Encoding.GetEncoding("UTF-8")); return new FileStreamResult(new FileStream(_path, FileMode.Open), "application/octet-stream") { FileDownloadName = fileName }; } #endregion #region 私有方法 /// /// 公共查询适配记录条件 /// /// /// private ISugarQueryable CommonPageFilter(RecordAdapterInput input) { var query = _rep.AsQueryable() .WhereIF(!string.IsNullOrWhiteSpace(input.SearchKey), u => u.CategoryName.Contains(input.SearchKey.Trim()) || u.AdapterName.Contains(input.SearchKey.Trim()) || u.AdapterMethodName.Contains(input.SearchKey.Trim()) || u.RequestSoure.Contains(input.SearchKey.Trim()) || u.AdapterSID.Contains(input.SearchKey.Trim()) || u.ErrMessage.Contains(input.SearchKey.Trim()) || u.AdapterInput.Contains(input.SearchKey.Trim()) || u.AdapterReturnMassage.Contains(input.SearchKey.Trim()) || u.CreateUserName.Contains(input.SearchKey.Trim()) || u.UpdateUserName.Contains(input.SearchKey.Trim()) ) .WhereIF(input.AdapterCategoryId > 0, u => u.AdapterCategoryId == input.AdapterCategoryId) .WhereIF(!string.IsNullOrWhiteSpace(input.CategoryName), u => u.CategoryName.Contains(input.CategoryName.Trim())) .WhereIF(!string.IsNullOrWhiteSpace(input.KeyCode), u => u.KeyCode.Contains(input.KeyCode.Trim())) .WhereIF(!string.IsNullOrWhiteSpace(input.AdapterName), u => u.AdapterName.Contains(input.AdapterName.Trim())) .WhereIF(input.AdapterId > 0, u => u.AdapterId == input.AdapterId) .WhereIF(!string.IsNullOrWhiteSpace(input.AdapterMethodName), u => u.AdapterMethodName.Contains(input.AdapterMethodName.Trim())) .WhereIF(!string.IsNullOrWhiteSpace(input.RequestSoure), u => u.RequestSoure.Contains(input.RequestSoure.Trim())) .WhereIF(!string.IsNullOrWhiteSpace(input.AdapterSID), u => u.AdapterSID.Contains(input.AdapterSID.Trim())) .WhereIF(input.DealWithStatus.HasValue, u => u.DealWithStatus == input.DealWithStatus) .WhereIF(!string.IsNullOrWhiteSpace(input.ErrMessage), u => u.ErrMessage.Contains(input.ErrMessage.Trim())) .WhereIF(!string.IsNullOrWhiteSpace(input.AdapterInput), u => u.AdapterInput.Contains(input.AdapterInput.Trim())) .WhereIF(!string.IsNullOrWhiteSpace(input.AdapterReturnMassage), u => u.AdapterReturnMassage.Contains(input.AdapterReturnMassage.Trim())) .Select(); if (input.BeginTimeRange != null && input.BeginTimeRange.Count > 0) { DateTime? start = input.BeginTimeRange[0].Value.AddDays(-1); query = query.WhereIF(start.HasValue, u => u.BeginTime > start); if (input.BeginTimeRange.Count > 1 && input.BeginTimeRange[1].HasValue) { var end = input.BeginTimeRange[1].Value.AddDays(1); query = query.Where(u => u.BeginTime < end); } } if (input.EndingTimeRange != null && input.EndingTimeRange.Count > 0) { DateTime? start = input.EndingTimeRange[0].Value.AddDays(-1); query = query.WhereIF(start.HasValue, u => u.EndingTime > start); if (input.EndingTimeRange.Count > 1 && input.EndingTimeRange[1].HasValue) { var end = input.EndingTimeRange[1].Value.AddDays(1); query = query.Where(u => u.EndingTime < end); } } return query; } /// /// 重复性验证 /// /// 验证对象 /// 是否是编辑 /// private async Task CheckExist(WmsAdapterRecord input, bool isEdit = false) { //没有配置组合校验,不需要验重 //没有配置单独校验,不需要验重 } /// /// 根据组合校验和单独校验验证数据是否已存在-导入时验证 /// /// /// private async Task CheckExisitForImport(List inputs) { if (inputs?.Count <= 0) { throw Oops.Oh($"导入数据不能为空"); } //根据组合校验验证表格中中是否已存在相同数据 //根据单独校验验证表格中中是否已存在相同数据 } #endregion }