You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

1222 lines
57 KiB
C#

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

using DS.Module.Core;
using DS.Module.Core.Constants;
using DS.Module.DjyServiceStatus;
using DS.Module.SqlSugar;
using DS.Module.UserModule;
using DS.WMS.Core.Code.Interface;
using DS.WMS.Core.Info.Dtos;
using DS.WMS.Core.Info.Interface;
using DS.WMS.Core.Map.Dtos;
using DS.WMS.Core.Map.Interface;
using DS.WMS.Core.Op.Dtos;
using DS.WMS.Core.Op.Entity;
using DS.WMS.Core.Op.Interface;
using DS.WMS.Core.Op.Method;
using DS.WMS.Core.Sys.Interface;
using DS.WMS.Core.TaskPlat.Dtos;
using DS.WMS.Core.TaskPlat.Entity;
using DS.WMS.Core.TaskPlat.Interface;
using Mapster;
using Microsoft.AspNetCore.Hosting;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json;
using NPOI.XWPF.UserModel;
using SqlSugar;
namespace DS.WMS.Core.TaskPlat.Method
{
/// <summary>
/// 任务台-BC子任务
/// </summary>
public class TaskManageBCService : TaskManageBaseService<TaskManageBCService>, ITaskManageBCService
{
// 实例化时构建
private readonly IConfigService configService;
private readonly IClientInfoService clientInfoService;
private readonly IMappingCarrierService mappingCarrierService;
private readonly IOpFileService opFileService;
private readonly ICodeCtnService codeCtnService;
// 按需构建
private Lazy<IBookingSlotService> bookingSlotService;
private Lazy<ISeaExportService> seaExportService;
private Lazy<IDjyServiceStatusService> djyServiceStatusService;
public TaskManageBCService(IUser user,
ILogger<TaskManageBCService> logger,
ISaasDbService saasDbService,
IServiceProvider serviceProvider,
IWebHostEnvironment environment,
IConfigService configService,
IClientInfoService clientInfoService,
IMappingCarrierService mappingCarrierService,
IOpFileService opFileService,
ICodeCtnService codeCtnService)
: base(user, logger, saasDbService, serviceProvider, environment)
{
this.configService = configService;
this.clientInfoService = clientInfoService;
this.mappingCarrierService = mappingCarrierService;
this.opFileService = opFileService;
this.codeCtnService = codeCtnService;
bookingSlotService = new Lazy<IBookingSlotService>(serviceProvider.GetRequiredService<IBookingSlotService>);
seaExportService = new Lazy<ISeaExportService>(serviceProvider.GetRequiredService<ISeaExportService>);
djyServiceStatusService = new Lazy<IDjyServiceStatusService>(serviceProvider.GetRequiredService<IDjyServiceStatusService>);
}
/// <summary>
/// 通过任务信息BC生成订舱或舱位
/// </summary>
/// <param name="model">生成订舱或者舱位请求</param>
/// <returns>返回回执</returns>
public async Task<DataResult<TaskManageOrderResultDto>> CreateBookingAndSlot(BookingOrSlotGenerateDto model)
{
TaskManageOrderResultDto result = new TaskManageOrderResultDto();
logger.LogInformation($"接收生成订舱或舱位请求,参数{JsonConvert.SerializeObject(model)}");
try
{
/*
1、GEN_BOOKING_SLOT-生成舱位和订舱
1生成舱位
2生成海运订舱
3更新舱位库存
4更新BC任务
2、GEN_BOOKING-只生成订舱
1生成海运订舱
4更新BC任务
3、GEN_SLOT-只生成舱位
1生成舱位
4更新BC任务
3、GEN_SLOT-只生成舱位
1查找订舱记录
3更新舱位库存
4更新BC任务
*/
if (model.BCTaskId == 0)
throw new Exception($"BC任务主键不能为空");
//生成方式GEN_BOOKING_SLOT-生成舱位和订舱;GEN_BOOKING-只生成订舱GEN_SLOT-只生成舱位GEN_EXIST_BOOKING-匹配指定的订舱)
if (string.IsNullOrWhiteSpace(model.GenerateMethod))
throw new Exception($"生成方式不能为空,需要指定一种生成方式");
var tenantDb = saasDbService.GetBizDbScopeById(user.TenantId);
var bcTaskInfo = await tenantDb.Queryable<TaskBaseInfo>().Where(u => u.Id == model.BCTaskId).FirstAsync();
if (bcTaskInfo == null)
{
throw new Exception($"任务主键{model.BCTaskId}无法获取业务信息");
}
var bcOrder = await tenantDb.Queryable<TaskBCInfo>().Where(a => a.TASK_ID == bcTaskInfo.Id).FirstAsync();
if (bcOrder == null)
throw new Exception($"任务主键{model.BCTaskId}无法获取BC业务信息");
var bcCtnList = await tenantDb.Queryable<TaskBCCTNInfo>().Where(a => a.P_ID == bcOrder.Id).ToListAsync();
var fileList = await tenantDb.Queryable<TaskFileInfo>().Where(a => a.TASK_PKID == bcTaskInfo.Id).ToListAsync();
if (model.GenerateMethod != "UPD_BOOKING")
{
if (bcOrder.BOOKING_ORDER_ID.HasValue && bcOrder.BOOKING_ORDER_ID.Value > 0)
{
throw new Exception($"当前BC任务已生成订舱订单不能重复生成");
}
}
if (model.GenerateMethod == "GEN_BOOKING_SLOT")
{
#region 推送舱位、推送订舱
//推送舱位
//long bookingSlotId = 0;
BookingSlotBase? bookingSlot = null;
if (bcOrder.BOOKING_SLOT_ID.HasValue && bcOrder.BOOKING_SLOT_ID.Value > 0)
{
//bookingSlotId = bcOrder.BOOKING_SLOT_ID.Value;
throw new Exception($"生成舱位失败,舱位已存在");
}
//这里增加委托单位联系人的校验,重新从后台拉取了委托单位相关联系人,如果比对不一致跳出异常终止执行
ValidateContact(model);
//触发生成舱位
bookingSlot = await GenerateBookingSlotByTaskBcInfo(bcOrder, bcCtnList, fileList);
logger.LogInformation($"生成舱位完成bookingSlotId={bookingSlot?.Id} taskid={bcOrder.TASK_ID}");
if (bookingSlot == null || bookingSlot.Id == 0)
throw new Exception($"生成舱位失败");
var slotFileList = opFileService.GetOpFileList(bookingSlot.Id.ToString()).Data;
//if (bookingSlotService == null)
//{
// bookingSlotService = serviceProvider.GetRequiredService<IBookingSlotService>();
//}
//推送订舱订单
var bookingOrderId = await bookingSlotService.Value.GenerateBookingOrder(bookingSlot, slotFileList, model, null);
logger.LogInformation($"生成订舱订单完成bookingOrderId={bookingOrderId} taskid={bcOrder.TASK_ID}");
if (bookingOrderId < 1)
throw new Exception($"生成订舱订单失败");
List<BookingSlotBaseWithCtnDto> slots = new List<BookingSlotBaseWithCtnDto>();
//检索舱位信息
var slotInfo = (await bookingSlotService.Value.Detail(bookingSlot.Id)).Data;
BookingSlotBaseWithCtnDto baseInfo = slotInfo.Adapt<BookingSlotBaseWithCtnDto>();
baseInfo.Id = bookingSlot.Id;
baseInfo.CtnList = slotInfo.CtnList.Adapt<List<BookingSlotCtnDto>>();
slots.Add(baseInfo);
//对应订舱和舱位关系
ImportSlotsDto importSlotsDto = new()
{
bookingOrderId = bookingOrderId,
slots = slots,
isCheck = false
};
var allocRlt = await bookingSlotService.Value.ImportSlots(importSlotsDto);
logger.LogInformation($"生成订舱和舱位关系完成allocRlt={JsonConvert.SerializeObject(allocRlt)} taskid={bcOrder.TASK_ID}");
if (!allocRlt.Succeeded)
{
throw new Exception($"生成订舱和舱位关系失败");
}
var bcEntity = await tenantDb.Queryable<TaskBCInfo>().Where(a => a.Id == bcOrder.Id).FirstAsync();
if (bcEntity == null)
{
throw new Exception($"未获取有效任务BC失败更新失败");
}
bcEntity.BOOKING_ORDER_ID = bookingOrderId;
bcEntity.BOOKING_SLOT_ID = slotInfo.Id;
bcEntity.UpdateTime = DateTime.Now;
bcEntity.UpdateBy = long.Parse(user.UserId);
bcEntity.UpdateUserName = user.UserName;
//更新任务BC
await tenantDb.Updateable<TaskBCInfo>(bcEntity).UpdateColumns(it => new
{
it.BOOKING_ORDER_ID,
it.BOOKING_SLOT_ID,
it.UpdateTime,
it.UpdateBy,
it.UpdateUserName
}).ExecuteCommandAsync();
var taskEntity = await tenantDb.Queryable<TaskBaseInfo>().FirstAsync(u => u.Id == bcEntity.TASK_ID);
if (taskEntity == null)
{
throw new Exception($"未获取有效任务记录,更新失败");
}
#region 更新任务
//如果是公共任务,需要变成个人任务 RealUserId = 当前操作人
if (taskEntity.IS_PUBLIC == 1)
{
taskEntity.IS_PUBLIC = 0;
taskEntity.RealUserId = long.Parse(user.UserId);
taskEntity.RealUserName = user.UserName;
taskEntity.UpdateTime = DateTime.Now;
taskEntity.UpdateBy = taskEntity.RealUserId ?? 0;
taskEntity.UpdateUserName = user.UserName;
taskEntity.IS_COMPLETE = 1;
taskEntity.COMPLETE_DATE = DateTime.Now;
taskEntity.COMPLETE_DEAL = "MANUAL";
taskEntity.COMPLETE_DEAL = "手工";
await tenantDb.Updateable(taskEntity).UpdateColumns(it => new
{
it.IS_PUBLIC,
it.UpdateTime,
it.UpdateBy,
it.UpdateUserName,
it.RealUserId,
it.RealUserName,
it.IS_COMPLETE,
it.COMPLETE_DATE,
it.COMPLETE_DEAL,
it.COMPLETE_DEAL_NAME
}).ExecuteCommandAsync();
}
else
{
taskEntity.UpdateTime = DateTime.Now;
taskEntity.UpdateBy = long.Parse(user.UserId);
taskEntity.UpdateUserName = user.UserName;
taskEntity.IS_COMPLETE = 1;
taskEntity.COMPLETE_DATE = DateTime.Now;
taskEntity.COMPLETE_DEAL = "MANUAL";
taskEntity.COMPLETE_DEAL = "手工";
await tenantDb.Updateable(taskEntity).UpdateColumns(it => new
{
it.UpdateTime,
it.UpdateBy,
it.UpdateUserName,
it.IS_COMPLETE,
it.COMPLETE_DATE,
it.COMPLETE_DEAL,
it.COMPLETE_DEAL_NAME
}).ExecuteCommandAsync();
}
#endregion
//var currBCOrder = await tenantDb.Queryable<TaskBaseInfo>().Where(a => a.Id == bcEntity.Id).FirstAsync();
//if (currBCOrder != null && model.IsDirectSend)
//{
// //异步推送邮件
// var mailRlt = await GenerateSendEmail(currBCOrder, bcTaskInfo, model.usePersonalEmailSend);
// if (!mailRlt.succ)
// {
// throw Oops.Oh($"邮件推送失败,原因:{mailRlt.msg},可以任务编辑页面重新发送邮件");
// }
//}
#endregion
}
else if (model.GenerateMethod == "GEN_BOOKING")
{
#region 推送订舱
//bookingSlot = null;
if (bcOrder.BOOKING_ORDER_ID.HasValue && bcOrder.BOOKING_ORDER_ID.Value > 0)
{
//bookingSlotId = bcOrder.BOOKING_SLOT_ID.Value;
throw new Exception($"生成订舱订单失败,订舱订单已存在");
}
if (!bcOrder.BOOKING_SLOT_ID.HasValue || bcOrder.BOOKING_SLOT_ID.Value < 1)
{
//bookingSlotId = bcOrder.BOOKING_SLOT_ID.Value;
throw new Exception($"生成订舱订单失败,舱位未生成不能直接生成订舱订单");
}
long bookingSlotId = bcOrder.BOOKING_SLOT_ID.Value;
//这里增加委托单位联系人的校验,重新从后台拉取了委托单位相关联系人,如果比对不一致跳出异常终止执行
ValidateContact(model);
BookingSlotBase? bookingSlot = await tenantDb.Queryable<BookingSlotBase>().Where(x => x.Id == bookingSlotId).FirstAsync();
if (bookingSlot == null)
{
throw new Exception($"生成订舱订单失败,舱位未生成不能直接生成订舱订单");
}
var slotFileList = opFileService.GetOpFileList(bookingSlotId.ToString()).Data;
//推送订舱订单
//if (bookingSlotService == null)
//{
// bookingSlotService = serviceProvider.GetRequiredService<IBookingSlotService>();
//}
var bookingOrderId = await bookingSlotService.Value.GenerateBookingOrder(bookingSlot, slotFileList, model, null);
logger.LogInformation($"生成订舱订单完成bookingOrderId={bookingOrderId} taskid={bcOrder.TASK_ID}");
if (bookingOrderId < 1)
throw new Exception($"生成订舱订单失败");
List<BookingSlotBaseWithCtnDto> slots = new List<BookingSlotBaseWithCtnDto>();
//检索舱位信息
var slotInfo = (await bookingSlotService.Value.Detail(bookingSlot.Id)).Data;
BookingSlotBaseWithCtnDto baseInfo = slotInfo.Adapt<BookingSlotBaseWithCtnDto>();
baseInfo.Id = bookingSlot.Id;
baseInfo.CtnList = slotInfo.CtnList.Adapt<List<BookingSlotCtnDto>>();
slots.Add(baseInfo);
//对应订舱和舱位关系
ImportSlotsDto importSlotsDto = new()
{
bookingOrderId = bookingOrderId,
slots = slots,
isCheck = false
};
var allocRlt = await bookingSlotService.Value.ImportSlots(importSlotsDto);
logger.LogInformation($"生成订舱和舱位关系完成allocRlt={JsonConvert.SerializeObject(allocRlt)} taskid={bcOrder.TASK_ID}");
if (!allocRlt.Succeeded)
{
throw new Exception($"生成订舱和舱位关系失败");
}
var bcEntity = await tenantDb.Queryable<TaskBCInfo>().Where(a => a.Id == bcOrder.Id).FirstAsync();
if (bcEntity == null)
{
throw new Exception($"未获取有效任务BC失败更新失败");
}
bcEntity.BOOKING_ORDER_ID = bookingOrderId;
bcEntity.BOOKING_SLOT_ID = slotInfo.Id;
bcEntity.UpdateTime = DateTime.Now;
bcEntity.UpdateBy = long.Parse(user.UserId);
bcEntity.UpdateUserName = user.UserName;
//更新任务BC
await tenantDb.Updateable<TaskBCInfo>(bcEntity).UpdateColumns(it => new
{
it.BOOKING_ORDER_ID,
it.BOOKING_SLOT_ID,
it.UpdateTime,
it.UpdateBy,
it.UpdateUserName
}).ExecuteCommandAsync();
var taskEntity = await tenantDb.Queryable<TaskBaseInfo>().FirstAsync(u => u.Id == bcEntity.TASK_ID);
if (taskEntity == null)
{
throw new Exception($"未获取有效任务记录,更新失败");
}
#region 更新任务
//如果是公共任务,需要变成个人任务 RealUserId = 当前操作人
if (taskEntity.IS_PUBLIC == 1)
{
taskEntity.IS_PUBLIC = 0;
taskEntity.RealUserId = long.Parse(user.UserId);
taskEntity.RealUserName = user.UserName;
taskEntity.UpdateTime = DateTime.Now;
taskEntity.UpdateBy = taskEntity.RealUserId ?? 0;
taskEntity.UpdateUserName = user.UserName;
taskEntity.IS_COMPLETE = 1;
taskEntity.COMPLETE_DATE = DateTime.Now;
taskEntity.COMPLETE_DEAL = "MANUAL";
taskEntity.COMPLETE_DEAL = "手工";
await tenantDb.Updateable(taskEntity).UpdateColumns(it => new
{
it.IS_PUBLIC,
it.UpdateTime,
it.UpdateBy,
it.UpdateUserName,
it.RealUserId,
it.RealUserName,
it.IS_COMPLETE,
it.COMPLETE_DATE,
it.COMPLETE_DEAL,
it.COMPLETE_DEAL_NAME
}).ExecuteCommandAsync();
}
else
{
taskEntity.UpdateTime = DateTime.Now;
taskEntity.UpdateBy = long.Parse(user.UserId);
taskEntity.UpdateUserName = user.UserName;
taskEntity.IS_COMPLETE = 1;
taskEntity.COMPLETE_DATE = DateTime.Now;
taskEntity.COMPLETE_DEAL = "MANUAL";
taskEntity.COMPLETE_DEAL = "手工";
await tenantDb.Updateable(taskEntity).UpdateColumns(it => new
{
it.UpdateTime,
it.UpdateBy,
it.UpdateUserName,
it.IS_COMPLETE,
it.COMPLETE_DATE,
it.COMPLETE_DEAL,
it.COMPLETE_DEAL_NAME
}).ExecuteCommandAsync();
}
#endregion
//var currBCOrder = _taskBCInfoRepository.AsQueryable().First(a => a.PK_ID == bcEntity.PK_ID);
//if (currBCOrder != null && model.IsDirectSend)
//{
// //异步推送邮件
// var mailRlt = await GenerateSendEmail(currBCOrder, bcTaskInfo, model.usePersonalEmailSend);
// if (!mailRlt.succ)
// {
// throw Oops.Oh($"邮件推送失败,原因:{mailRlt.msg},可以任务编辑页面重新发送邮件");
// }
//}
#endregion
}
else if (model.GenerateMethod == "GEN_SLOT")
{
#region 推送舱位
BookingSlotBase? bookingSlot = null;
if (bcOrder.BOOKING_SLOT_ID.HasValue && bcOrder.BOOKING_SLOT_ID.Value > 0)
{
//bookingSlotId = bcOrder.BOOKING_SLOT_ID.Value;
throw new Exception($"生成舱位失败,舱位已存在");
}
//触发生成舱位
bookingSlot = await GenerateBookingSlotByTaskBcInfo(bcOrder, bcCtnList, fileList);
logger.LogInformation($"生成舱位完成bookingSlotId={bookingSlot?.Id} taskid={bcOrder.TASK_ID}");
if (bookingSlot == null || bookingSlot.Id == 0)
throw new Exception($"生成舱位失败");
var bcEntity = await tenantDb.Queryable<TaskBCInfo>().Where(a => a.Id == bcOrder.Id).FirstAsync();
if (bcEntity == null)
{
throw new Exception($"未获取有效任务BC失败更新失败");
}
bcEntity.BOOKING_SLOT_ID = bookingSlot.Id;
bcEntity.UpdateTime = DateTime.Now;
bcEntity.UpdateBy = long.Parse(user.UserId);
bcEntity.UpdateUserName = user.UserName;
//更新任务BC
await tenantDb.Updateable<TaskBCInfo>(bcEntity).UpdateColumns(it => new
{
it.BOOKING_SLOT_ID,
it.UpdateTime,
it.UpdateBy,
it.UpdateUserName
}).ExecuteCommandAsync();
var taskEntity = await tenantDb.Queryable<TaskBaseInfo>().FirstAsync(u => u.Id == bcEntity.TASK_ID);
if (taskEntity == null)
{
throw new Exception($"未获取有效任务记录,更新失败");
}
#region 更新任务
//如果是公共任务,需要变成个人任务 RealUserId = 当前操作人
if (taskEntity.IS_PUBLIC == 1)
{
taskEntity.IS_PUBLIC = 0;
taskEntity.RealUserId = long.Parse(user.UserId);
taskEntity.RealUserName = user.UserName;
taskEntity.UpdateTime = DateTime.Now;
taskEntity.UpdateBy = taskEntity.RealUserId ?? 0;
taskEntity.UpdateUserName = user.UserName;
await tenantDb.Updateable(taskEntity).UpdateColumns(it => new
{
it.IS_PUBLIC,
it.UpdateTime,
it.UpdateBy,
it.UpdateUserName,
it.RealUserId,
it.RealUserName,
}).ExecuteCommandAsync();
}
else
{
taskEntity.UpdateTime = DateTime.Now;
taskEntity.UpdateBy = long.Parse(user.UserId);
taskEntity.UpdateUserName = user.UserName;
await tenantDb.Updateable(taskEntity).UpdateColumns(it => new
{
it.UpdateTime,
it.UpdateBy,
it.UpdateUserName,
}).ExecuteCommandAsync();
}
#endregion
#endregion
}
else if (model.GenerateMethod == "UPD_BOOKING")
{
#region 更新订舱
if (bcOrder.BOOKING_ORDER_ID == null || bcOrder.BOOKING_ORDER_ID.Value == 0)
{
throw new Exception($"更新订舱订单失败,舱位未关联到订单信息");
}
//这里增加委托单位联系人的校验,重新从后台拉取了委托单位相关联系人,如果比对不一致跳出异常终止执行
ValidateContact(model);
long bookingSlotId = bcOrder.BOOKING_SLOT_ID.Value;
//这里增加委托单位联系人的校验,重新从后台拉取了委托单位相关联系人,如果比对不一致跳出异常终止执行
ValidateContact(model);
BookingSlotBase? bookingSlot = await tenantDb.Queryable<BookingSlotBase>().Where(x => x.Id == bookingSlotId).FirstAsync();
if (bookingSlot == null)
{
throw new Exception($"更新订舱订单失败未找到id为{bookingSlotId}的舱位信息");
}
List<BookingSlotCtn> bookingSlotCtnList = await tenantDb.Queryable<BookingSlotCtn>().Where(x => x.Id == bookingSlotId).ToListAsync();
//推送订舱订单
var bookingOrderId = await UpdateBookingOrder((long)bcOrder.BOOKING_ORDER_ID, bookingSlot, bookingSlotCtnList, model, tenantDb);
var taskEntity = await tenantDb.Queryable<TaskBaseInfo>().FirstAsync(u => u.Id == bcOrder.TASK_ID);
if (taskEntity == null)
{
throw new Exception($"未获取有效任务记录,更新失败");
}
#region 更新任务
//如果是公共任务,需要变成个人任务 RealUserId = 当前操作人
if (taskEntity.IS_PUBLIC == 1)
{
taskEntity.IS_PUBLIC = 0;
taskEntity.RealUserId = long.Parse(user.UserId);
taskEntity.RealUserName = user.UserName;
taskEntity.UpdateTime = DateTime.Now;
taskEntity.UpdateBy = taskEntity.RealUserId ?? 0;
taskEntity.UpdateUserName = user.UserName;
taskEntity.IS_COMPLETE = 1;
taskEntity.COMPLETE_DATE = DateTime.Now;
taskEntity.COMPLETE_DEAL = "MANUAL";
taskEntity.COMPLETE_DEAL = "手工";
await tenantDb.Updateable(taskEntity).UpdateColumns(it => new
{
it.IS_PUBLIC,
it.UpdateTime,
it.UpdateBy,
it.UpdateUserName,
it.RealUserId,
it.RealUserName,
it.IS_COMPLETE,
it.COMPLETE_DATE,
it.COMPLETE_DEAL,
it.COMPLETE_DEAL_NAME
}).ExecuteCommandAsync();
}
else
{
taskEntity.UpdateTime = DateTime.Now;
taskEntity.UpdateBy = long.Parse(user.UserId);
taskEntity.UpdateUserName = user.UserName;
taskEntity.IS_COMPLETE = 1;
taskEntity.COMPLETE_DATE = DateTime.Now;
taskEntity.COMPLETE_DEAL = "MANUAL";
taskEntity.COMPLETE_DEAL = "手工";
await tenantDb.Updateable(taskEntity).UpdateColumns(it => new
{
it.UpdateTime,
it.UpdateBy,
it.UpdateUserName,
it.IS_COMPLETE,
it.COMPLETE_DATE,
it.COMPLETE_DEAL,
it.COMPLETE_DEAL_NAME
}).ExecuteCommandAsync();
}
#endregion
//var currBCOrder = await tenantDb.Queryable<TaskBaseInfo>().Where(a => a.Id == bcEntity.Id).FirstAsync();
//if (currBCOrder != null && model.IsDirectSend)
//{
// //异步推送邮件
// var mailRlt = await GenerateSendEmail(currBCOrder, bcTaskInfo, model.usePersonalEmailSend);
// if (!mailRlt.succ)
// {
// throw Oops.Oh($"邮件推送失败,原因:{mailRlt.msg},可以任务编辑页面重新发送邮件");
// }
//}
#endregion
}
result.succ = true;
result.msg = "成功";
return DataResult<TaskManageOrderResultDto>.Success(result);
}
catch (Exception ex)
{
result.succ = false;
result.msg = $"生成订舱或舱位失败,原因:{ex.Message}";
return DataResult<TaskManageOrderResultDto>.FailedData(result);
}
}
private void ValidateContact(BookingOrSlotGenerateDto model)
{
var paramConfig = configService.GetConfig(TenantParamCode.CONST_CREATE_BOOKING_NEED_CONTACT, long.Parse(user.TenantId), false).GetAwaiter().GetResult()?.Data?.Value;
if (model.CustomerContactList != null && model.CustomerContactList.Count > 0)
{
//取委托客户下面所有的联系人列表
var djyCustomerInfo = clientInfoService.GetClientInfoWithContact(new Info.Dtos.QueryClientInfo { ClientId = model.CustomerId.Value, IsController = true }).GetAwaiter().GetResult().Data;
if (djyCustomerInfo == null)
{
logger.LogInformation($"委托单位{model.CustomerName} 获取失败,委托单位不存在或已作废 SlotId={model.SlotId.Value}");
//委托单位{0} 获取失败,委托单位不存在或已作废
throw new Exception(string.Format(MultiLanguageConst.GetDescription(nameof(MultiLanguageConst.BookingSlotCreateContaNull)), model.CustomerName));
}
if (djyCustomerInfo.ClientContactList == null && djyCustomerInfo.ClientContactList.Count < 1)
{
logger.LogInformation($"委托单位{model.CustomerName} 获取相关联系人失败,委托单位相关联系人为空 SlotId={model.SlotId.Value}");
//委托单位{0} 获取相关联系人失败,委托单位相关联系人为空
throw new Exception(string.Format(MultiLanguageConst.GetDescription(nameof(MultiLanguageConst.BookingSlotCreateCustomerContractInfoNull)), model.CustomerName));
}
model.CustomerContactList.ForEach(contact =>
{
var djyCustomerContactMan = djyCustomerInfo.ClientContactList
.FirstOrDefault(a => a.Id == contact.Id);
if (djyCustomerContactMan == null)
{
logger.LogInformation($"委托单位{model.CustomerName} 联系人 {contact.Name}获取失败,联系人不存在或已作废 SlotId={model.SlotId}");
//委托单位 {0} 联系人 {1} 获取失败,联系人不存在或已作废
throw new Exception(string.Format(MultiLanguageConst.GetDescription(nameof(MultiLanguageConst.BookingSlotCreateCustomerContractDeletedOrNoExists)), model.CustomerName, contact.Name));
}
});
}
else
{
if (paramConfig != null && paramConfig.Equals("ENABLE", StringComparison.OrdinalIgnoreCase))
{
//生成订舱时往来单位联系人必填,请修改
throw new Exception(MultiLanguageConst.GetDescription(nameof(MultiLanguageConst.BookingSlotCreateCustomerContractNotNull)));
}
}
}
/// <summary>
/// 通过任务主键获取BC详情
/// </summary>
/// <param name="taskId">BC任务主键</param>
public async Task<DataResult<TaskManageOrderResultDto>> GetInfoByTaskId(long taskId)
{
TaskManageOrderResultDto result = new TaskManageOrderResultDto();
try
{
var tenantDb = saasDbService.GetBizDbScopeById(user.TenantId);
var taskBase = await tenantDb.Queryable<TaskBaseInfo>().FirstAsync(a => a.Id == taskId);
if (taskBase == null)
throw new Exception(MultiLanguageConst.GetDescription(nameof(MultiLanguageConst.TaskBaseEmpty)));
var bcOrder = await tenantDb.Queryable<TaskBCInfo>().FirstAsync(a => a.TASK_ID == taskId);
if (bcOrder == null)
throw new Exception(MultiLanguageConst.GetDescription(nameof(MultiLanguageConst.TaskBCInfoEmpty)));
var bcCtnList = await tenantDb.Queryable<TaskBCCTNInfo>().Where(a => a.P_ID == bcOrder.Id).ToListAsync();
TaskBCShowBaseDto model = bcOrder.Adapt<TaskBCShowBaseDto>();
if (bcCtnList.Count > 0)
model.CtnList = bcCtnList.Adapt<List<TaskBCCTNInfoDto>>();
var fileList = await tenantDb.Queryable<TaskFileInfo>().Where(a => a.TASK_PKID == bcOrder.TASK_ID).ToListAsync();
if (fileList.Count > 0)
model.FileList = fileList.Adapt<List<TaskFileDto>>();
model.taskStatus = taskBase.STATUS;
#region 生成关键信息
model.Keywords = new List<TaskBCShowBaseKeywordDto>();
if (bcOrder.CARRIAGE_TYPE == "DIRECT_SHIP")
{
model.Keywords.Add(new TaskBCShowBaseKeywordDto() { Name = $"承运方式:{bcOrder.CARRIAGE_TYPE_NAME}", Background = "#FFFF80", Icon = "icon-yunshu1" });
}
else if (bcOrder.CARRIAGE_TYPE == "TRANSFER_SHIP")
{
model.Keywords.Add(new TaskBCShowBaseKeywordDto() { Name = $"承运方式:{bcOrder.CARRIAGE_TYPE_NAME}", Background = "#CAF982", Icon = "icon-shuaxin" });
}
if (bcOrder.BOOKING_SLOT_TYPE == "CONTRACT_ORDER")
{
model.Keywords.Add(new TaskBCShowBaseKeywordDto() { Name = $"订舱方式:{bcOrder.BOOKING_SLOT_TYPE_NAME}", Background = "#81D3F8", Icon = "icon-touzijilu" });
}
else if (bcOrder.BOOKING_SLOT_TYPE == "SPOT_ORDER")
{
model.Keywords.Add(new TaskBCShowBaseKeywordDto() { Name = $"订舱方式:{bcOrder.BOOKING_SLOT_TYPE_NAME}", Background = "#FACD91", Icon = "icon-beizhu1" });
}
#endregion
//await SetTaskStatus([taskId], x => x.IS_PUBLIC == 1, x => x.IS_EXCEPT == 0);
//await SetTaskOwner([taskId], new List<RecvUserInfo>()
//{
// new RecvUserInfo(111,"231312321"),
// new RecvUserInfo(222,"affsdfdsf"),
//});
result.succ = true;
result.ext = model;
//如果当前BC有对应记录则读取订舱详情
//0726:经确认页面上没有用到订舱详情,所以暂时不返回
//if (bcOrder.BOOKING_ORDER_ID.HasValue)
//{
// var bkOrder = await _bookingOrderRepository.AsQueryable().
// FirstAsync(a => a.Id == bcOrder.BOOKING_ORDER_ID.Value);
// if (bkOrder != null)
// {
// var showBKOrder = bkOrder.Adapt<BookingOrderOutput>();
// var ctnList = await _bookingCtnRepository.AsQueryable().
// Where(a => a.BILLID == bkOrder.Id).ToListAsync();
// if (ctnList.Count > 0)
// showBKOrder.ctnInputs = ctnList.Adapt<List<BookingCtnDto>>();
// result.ext2 = showBKOrder;
// }
//}
}
catch (Exception ex)
{
result.succ = false;
result.msg = $"获取BC详情异常原因{ex.Message}";
}
return DataResult<TaskManageOrderResultDto>.Success(result);
}
#region 根据BC任务信息生成舱位
/// <summary>
/// 根据BC任务信息生成舱位调用的
/// </summary>
/// <param name="taskBCInfo">BC任务详情</param>
/// <param name="taskBCCtnList">BC任务集装箱列表</param>
/// <param name="taskFileList">BC任务附件列表</param>
/// <returns>返回舱位ID</returns>
private async Task<BookingSlotBase?> GenerateBookingSlotByTaskBcInfo(TaskBCInfo taskBCInfo, List<TaskBCCTNInfo> taskBCCtnList, List<TaskFileInfo> taskFileList, string opType = "add")
{
//long id = 0;
try
{
var allMapCarrierList = await mappingCarrierService.GetAllList();
MappingCarrierRes? carrierInfo = null;
if (allMapCarrierList.Succeeded)
{
carrierInfo = allMapCarrierList.Data.Where(t => t.MapCode.Equals(taskBCInfo.CARRIERID, StringComparison.OrdinalIgnoreCase) && t.Module == MappingModuleConst.CONST_MAPPING_CARRIER_MODULE).FirstOrDefault();
}
BookingSlotBaseApiDto slotModel = new BookingSlotBaseApiDto
{
DataObj = new BookingSlotBaseApiSaveDto
{
CarrierId = carrierInfo?.LinkId,
CarrierCode = carrierInfo?.MapCode,
Carrier = carrierInfo?.MapName,
SlotBookingNo = taskBCInfo.MBL_NO,
BookingParty = taskBCInfo.BOOKING_PARTY,
BookingSlotType = taskBCInfo.BOOKING_SLOT_TYPE,
BookingSlotTypeName = taskBCInfo.BOOKING_SLOT_TYPE_NAME,
Vessel = taskBCInfo.VESSEL,
Voyno = taskBCInfo.VOYNO,
VGMSubmissionCutDate = taskBCInfo.VGM_CUTOFF_TIME,
//WeekAt = taskBCInfoDto.WEEK_AT,
CarriageType = taskBCInfo.CARRIAGE_TYPE,
CarriageTypeName = taskBCInfo.CARRIAGE_TYPE_NAME,
ContractNo = taskBCInfo.CONTRACTNO,
CtnStat = taskBCInfo.CTN_STAT,
CYCutDate = taskBCInfo.CY_CUTOFF_TIME,
DetensionFreeDays = taskBCInfo.DETENSION_FREE_DAYS,
ETD = taskBCInfo.ETD,
ETA = taskBCInfo.ETA,
LaneCode = taskBCInfo.LANECODE,
LaneName = taskBCInfo.LANENAME,
ManifestCutDate = taskBCInfo.MANIFEST_CUT_DATE,
MDGFCutDate = taskBCInfo.MDGF_CUT_DATE,
PlaceDelivery = taskBCInfo.PLACEDELIVERY,
PlaceReceipt = taskBCInfo.PLACERECEIPT,
PortDischarge = taskBCInfo.PORTDISCHARGE,
PortLoad = taskBCInfo.PORTLOAD,
SICutDate = taskBCInfo.SI_CUT_DATE,
CustomSICutDate = taskBCInfo.CUSTOM_SI_CUT_DATE,
TransferPort1 = taskBCInfo.TRANSFER_PORT_1,
TransferPort2 = taskBCInfo.TRANSFER_PORT_2,
PriceCalculationDate = taskBCInfo.PRICE_CALCULATION_DATE,
CtnList = new List<BookingSlotCtnSaveInput>()
},
OpType = "add"
};
if (int.TryParse(taskBCInfo.WEEK_AT, out int _weekat))
{
slotModel.DataObj.WeekAt = _weekat;
}
var ctnCodeList = (await codeCtnService.GetAllList()).Data ?? new List<Code.Dtos.CodeCtnRes>();
if (taskBCCtnList.Count > 0)
{
taskBCCtnList.ForEach(t =>
{
if (string.IsNullOrEmpty(t.CTNCODE) && !string.IsNullOrEmpty(t.CTNALL))
{
var ctnCode = ctnCodeList.FirstOrDefault(a => !string.IsNullOrWhiteSpace(a.CtnName) && a.CtnName.Equals(t.CTNALL, StringComparison.OrdinalIgnoreCase));
t.CTNCODE = ctnCode != null ? $"{ctnCode.CtnSize}{ctnCode.CtnType}" : "(箱型未收录)";
}
BookingSlotCtnSaveInput ctn = new BookingSlotCtnSaveInput
{
CtnCode = t.CTNCODE,
CtnAll = t.CTNALL,
CtnNum = t.CTNNUM.HasValue ? t.CTNNUM.Value : 1
};
slotModel.DataObj.CtnList.Add(ctn);
});
}
var basePath = AppSetting.app(new string[] { "FileSettings", "BasePath" });
DynameFileInfo dynameFile = null;
DynameFileInfo dynameNoticeFile = null;
if (taskFileList.Any(t => t.FILE_CATEGORY == TaskFileCategoryEnum.BC.ToString()))
{
var fileInfo = taskFileList.FirstOrDefault(t => t.FILE_CATEGORY == TaskFileCategoryEnum.BC.ToString());
string fileFullPath;
if (string.IsNullOrEmpty(basePath))
{
fileFullPath = Path.Combine(environment.WebRootPath ?? "", fileInfo.FILE_PATH);
}
else
{
fileFullPath = Path.Combine(basePath, fileInfo.FILE_PATH);
}
dynameFile = new DynameFileInfo
{
FileBytes = File.ReadAllBytes(fileFullPath),
FileName = Path.GetFileName(fileFullPath)
};
}
if (taskFileList.Any(t => t.FILE_CATEGORY == TaskFileCategoryEnum.BC_NOTICE.ToString()))
{
var fileInfo = taskFileList.FirstOrDefault(t => t.FILE_CATEGORY == TaskFileCategoryEnum.BC.ToString());
string fileFullPath;
if (string.IsNullOrEmpty(basePath))
{
fileFullPath = Path.Combine(environment.WebRootPath ?? "", fileInfo.FILE_PATH);
}
else
{
fileFullPath = Path.Combine(basePath, fileInfo.FILE_PATH);
}
dynameNoticeFile = new DynameFileInfo
{
FileBytes = File.ReadAllBytes(fileFullPath),
FileName = Path.GetFileName(fileFullPath)
};
}
var result = await bookingSlotService.Value.InnerApiReceive(slotModel, dynameFile, dynameNoticeFile);
if (result.Succeeded && result.Data != null)
{
var tenantDb = saasDbService.GetBizDbScopeById(user.TenantId);
var taskBcInfo = await tenantDb.Queryable<TaskBCInfo>().Where(x => x.Id == taskBCInfo.Id).FirstAsync();
if (taskBcInfo != null && taskBcInfo.BOOKING_SLOT_ID == null)
{
taskBcInfo.BOOKING_SLOT_ID = result.Data.Id;
await tenantDb.Updateable<TaskBCInfo>(taskBcInfo).UpdateColumns(x => new
{
x.BOOKING_SLOT_ID
}).ExecuteCommandAsync();
}
}
return result.Data;
}
catch (Exception ex)
{
logger.LogError($"任务BC MBLNO:{taskBCInfo.MBL_NO} 生成舱位异常,原因:{ex.Message}");
throw new Exception($"MBLNO:{taskBCInfo.MBL_NO} 生成舱位异常,原因:{ex.Message}");
}
}
#endregion
#region 更新订舱
/// <summary>
/// 更新订舱
/// </summary>
/// <returns>返回订舱ID</returns>
private async Task<long> UpdateBookingOrder(
//TaskBCInfo taskBCInfo,
//List<TaskBCCTNInfo> taskBCCtnList,
long bookingOrderId,
BookingSlotBase bookingSlotBase,
List<BookingSlotCtn> bookingSlotCtnList,
BookingOrSlotGenerateDto generateModel,
SqlSugarScopeProvider? tenantDb = null)
{
long id = 0;
if (tenantDb == null)
{
tenantDb = saasDbService.GetBizDbScopeById(user.TenantId);
}
try
{
/*
1、新增订舱
2、推送服务项目
3、推送附件
*/
var allMapCarrierList = await mappingCarrierService.GetAllList();
MappingCarrierRes carrierInfo = null;
if (allMapCarrierList.Succeeded)
{
carrierInfo = allMapCarrierList.Data.FirstOrDefault(t => t.LinkId == bookingSlotBase.CarrierId.Value && t.Module == MappingModuleConst.CONST_MAPPING_CARRIER_MODULE);
}
SeaExportReq bkModel = new SeaExportReq
{
Id = bookingOrderId,
CustomerId = generateModel.CustomerId.Value,
CustomerName = generateModel.CustomerName,
Carrier = carrierInfo?.MapName?.Trim(),
CarrierId = bookingSlotBase.CarrierId.Value,
BookingNo = bookingSlotBase.SlotBookingNo.Trim(),
MBLNO = bookingSlotBase.SlotBookingNo.Trim(),
ContractNo = !string.IsNullOrWhiteSpace(bookingSlotBase.ContractNo) ? bookingSlotBase.ContractNo : "",
Vessel = bookingSlotBase.Vessel?.ToUpper()?.Trim(),
Voyno = bookingSlotBase.Voyno?.ToUpper()?.Trim(),
InnerVoyno = bookingSlotBase.Voyno?.ToUpper()?.Trim(),
ETD = bookingSlotBase.ETD,
ETA = bookingSlotBase.ETA,
SaleId = generateModel.SaleId.HasValue ? generateModel.SaleId.Value : 0,
Sale = generateModel.SaleName,
OperatorId = generateModel.OpId.HasValue ? generateModel.OpId.Value : 0,
OperatorName = generateModel.OpName,
Doc = generateModel.DocId.HasValue ? generateModel.DocId.Value : 0,
DocName = generateModel.DocName,
//ROUTEID = generateModel.RouteID?.ToString(),
//ROUTE = generateModel.Route,
//CZRemark = generateModel.CZRemark,
//ShenQingXiangShi = generateModel.ShenQingXiangShi,
//LineManageID = generateModel.LineManageID?.ToString(),
//LineName = generateModel.LineManage,
VGMCloseDate = bookingSlotBase.VGMSubmissionCutDate,
ClosingDate = bookingSlotBase.CYCutDate,
CloseDocDate = bookingSlotBase.SICutDate,
CustomerService = generateModel.CustServiceId.HasValue ? generateModel.CustServiceId.Value : 0,
CustomerServiceName = generateModel.CustServiceName,
LoadPort = bookingSlotBase.PortLoad,
LoadPortId = bookingSlotBase.PortLoadId.HasValue ? bookingSlotBase.PortLoadId.Value : 0,
DischargePortId = bookingSlotBase.PortDischargeId.HasValue ? bookingSlotBase.PortLoadId.Value : 0,
DischargePort = bookingSlotBase.PortDischarge,
ReceiptPlace = bookingSlotBase.PlaceReceipt,
ReceiptPlaceId = bookingSlotBase.PlaceReceiptId.HasValue ? bookingSlotBase.PlaceReceiptId.Value : 0,
DeliveryPlace = bookingSlotBase.PlaceDelivery,
DeliveryPlaceId = bookingSlotBase.PlaceDeliveryId.HasValue ? bookingSlotBase.PlaceDeliveryId.Value : 0,
BLType = "整箱",
StlName = "票结",
CtnInfo = new List<OpCtnReq>()
};
//var ctnCodeList = _cache.GetAllCodeCtn().GetAwaiter().GetResult().ToList();
if (bookingSlotCtnList != null && bookingSlotCtnList.Count > 0)
{
bookingSlotCtnList.Select(t =>
{
OpCtnReq ctn = new OpCtnReq
{
CtnCode = t.CtnCode,
CtnAll = t.CtnAll,
CtnNum = t.CtnNum
};
return ctn;
});
}
var bkRlt = await seaExportService.Value.EditSeaExport(bkModel);
id = long.Parse(bkRlt.Data.ToString());
string batchNo = Guid.NewGuid().ToString();
//var hisList = _bookingOrderContactRepository.AsQueryable().Where(a => a.BookingId == id && a.IsDeleted == false).ToList();
//if (hisList.Count > 0)
//{
// //批量作废
// hisList.ForEach(async a =>
// {
// a.IsDeleted = true;
// a.UpdatedTime = DateTime.Now;
// a.UpdatedUserId = UserManager.UserId;
// a.UpdatedUserName = UserManager.Name;
// await _bookingOrderContactRepository.UpdateAsync(a);
// });
//}
//这里如果指定了委托单位的邮件联系人,则推送订舱联系人
if (generateModel.CustomerContactList != null && generateModel.CustomerContactList.Count > 0)
{
var bookingContactList = await tenantDb.Queryable<BusinessOrderContact>()
.Where(a => a.BusinessId == id && a.Deleted == false).ToListAsync();
var djyCustomerInfo = clientInfoService.GetClientInfoWithContact(new Info.Dtos.QueryClientInfo { ClientId = generateModel.CustomerId.Value, IsController = true })
.GetAwaiter().GetResult().Data;
generateModel.CustomerContactList.ForEach(contact =>
{
ClientContactRes djyCustomerContactMan = null;
if (djyCustomerInfo.ClientContactList != null && djyCustomerInfo.ClientContactList.Count > 0)
{
djyCustomerContactMan = djyCustomerInfo.ClientContactList.FirstOrDefault(a =>
a.Id == contact.Id);
}
if (djyCustomerContactMan != null)
{
var bookingContact = bookingContactList
.FirstOrDefault(x => x.Email.Equals(djyCustomerContactMan.Email, StringComparison.OrdinalIgnoreCase));
if (bookingContact == null)
{
bookingContact = new BusinessOrderContact
{
Name = djyCustomerContactMan.ShortName,
BusinessId = id,
Email = djyCustomerContactMan.Email,
Note = djyCustomerContactMan.Note,
CreateTime = DateTime.Now,
CreateBy = long.Parse(user.UserId),
CreateUserName = user.UserName
};
tenantDb.Insertable<BusinessOrderContact>(bookingContact).ExecuteCommand();
//_bookingOrderContactRepository.Insert(bookingContact);
}
else
{
bookingContact.Name = djyCustomerContactMan.ShortName;
bookingContact.Email = djyCustomerContactMan.Email;
bookingContact.Note = djyCustomerContactMan.Note;
bookingContact.UpdateTime = DateTime.Now;
bookingContact.UpdateBy = long.Parse(user.UserId);
bookingContact.UpdateUserName = user.UserName;
tenantDb.Updateable<BusinessOrderContact>(bookingContact).UpdateColumns(it => new
{
it.Name,
it.Email,
it.Note,
it.UpdateTime,
it.UpdateBy,
it.UpdateUserName
}).ExecuteCommand();
}
}
});
}
if (generateModel.ProjectList != null && generateModel.ProjectList.Count > 0)
{
//写入服务项目
var prjRlt = djyServiceStatusService.Value.SaveServiceProject(new EmbedServiceProjectDto
{
BusinessId = id.ToString(),
ProjectCodes = generateModel.ProjectList.Distinct().ToArray(),
});
logger.LogInformation($"推送订舱的服务项目完成 id={id} rlt={JsonConvert.SerializeObject(prjRlt)}");
}
logger.LogInformation($"任务BC MBLNO:{bookingSlotBase.SlotBookingNo} 生成订舱成功 id={id}");
}
catch (Exception ex)
{
logger.LogError($"任务BC MBLNO:{bookingSlotBase.SlotBookingNo} 生成订舱异常,原因:{ex.Message}");
}
return id;
}
#endregion
#region 获取当前比对结果
/// <summary>
/// 获取当前比对结果
/// </summary>
/// <param name="taskId">BC任务主键</param>
/// <returns>返回回执</returns>
public async Task<DataResult<List<CompareResultDetailInfo>>> GetCompareResult(long taskId)
{
var tenantDb = saasDbService.GetBizDbScopeById(user.TenantId);
var queryList = await tenantDb.Queryable<TaskBaseInfo>()
.InnerJoin<TaskBCInfo>((a, b) => a.Id == b.TASK_ID)
.Where((a, b) => a.Id == taskId)
.Select((a, b) => new { Base = a, BC = b })
.ToListAsync();
//任务主键{taskPkId}无法获取业务信息
if (queryList.Count == 0)
throw new Exception(string.Format(MultiLanguageConst.GetDescription(nameof(MultiLanguageConst.TaskBaseInfoFromTaskIdNull)), taskId));
var taskBCInfo = queryList.FirstOrDefault().BC;
if (taskBCInfo.BOOKING_SLOT_ID.HasValue)
{
return await bookingSlotService.Value.GetSlotCompareResult(taskBCInfo.BOOKING_SLOT_ID.Value, taskBCInfo.BATCH_NO);
}
else
{
return DataResult<List<CompareResultDetailInfo>>.FailedData(new List<CompareResultDetailInfo>());
}
}
#endregion
}
}