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.
BookingHeChuan/Myshipping.Application/Event/BookingSlotStockSubscriber.cs

292 lines
12 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 Furion;
using Furion.EventBus;
using Mapster;
using Microsoft.Extensions.Logging;
using Myshipping.Core;
using SqlSugar;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
namespace Myshipping.Application.Event
{
/// <summary>
/// 运踪
/// </summary>
public class BookingSlotStockSubscriber : IEventSubscriber
{
private readonly ILogger<BookingSlotStockSubscriber> _logger;
public BookingSlotStockSubscriber(
ILogger<BookingSlotStockSubscriber> logger)
{
_logger = logger;
}
//更新库存
[EventSubscribe("BookingSlotStock:Update")]
public async Task BookingSlotStock(EventHandlerExecutingContext context)
{
BookingSlotStockUpdateModel paraObj = context.Source.Payload as BookingSlotStockUpdateModel;
await BookingSlotStock(paraObj);
}
public async Task BookingSlotStock(BookingSlotStockUpdateModel paraObj)
{
_logger.LogInformation($"收到更新库存订阅请求:{paraObj.ToJsonString()}");
var _repBase = App.GetService<SqlSugarRepository<BookingSlotBase>>();
var _repCtn = App.GetService<SqlSugarRepository<BookingSlotCtn>>();
var _repStock = App.GetService<SqlSugarRepository<BookingSlotStock>>();
var _repAlloc = App.GetService<SqlSugarRepository<BookingSlotAllocation>>();
var _repAllocCtn = App.GetService<SqlSugarRepository<BookingSlotAllocationCtn>>();
if (string.IsNullOrEmpty(paraObj.VESSEL)
|| string.IsNullOrEmpty(paraObj.VOYNO)
|| string.IsNullOrEmpty(paraObj.CONTRACT_NO)
|| string.IsNullOrEmpty(paraObj.BOOKING_SLOT_TYPE)
|| string.IsNullOrEmpty(paraObj.CARRIERID)
|| string.IsNullOrEmpty(paraObj.PORTLOADID)
|| string.IsNullOrEmpty(paraObj.PORTDISCHARGEID))
{
_logger.LogInformation($"收到更新库存订阅请求:部分参数存在空值,结束");
return;
}
var baseList = await _repBase.AsQueryable().Filter(null, true)
.Where(x => !x.IsDeleted
&& x.TenantId == paraObj.TenantId
&& x.VESSEL == paraObj.VESSEL
&& x.VOYNO == paraObj.VOYNO
&& x.CONTRACT_NO == paraObj.CONTRACT_NO
&& x.BOOKING_SLOT_TYPE == paraObj.BOOKING_SLOT_TYPE
&& x.CARRIERID == paraObj.CARRIERID
&& x.PORTLOADID == paraObj.PORTLOADID
&& x.PORTDISCHARGEID == paraObj.PORTDISCHARGEID)
.OrderByDescending(x => x.UpdatedTime)
.ToListAsync();
var stockObj = await _repStock.AsQueryable().Filter(null, true)
.FirstAsync(x => !x.IsDeleted
&& x.TenantId == paraObj.TenantId
&& x.VESSEL == paraObj.VESSEL
&& x.VOYNO == paraObj.VOYNO
&& x.CONTRACT_NO == paraObj.CONTRACT_NO
&& x.BOOKING_SLOT_TYPE == paraObj.BOOKING_SLOT_TYPE
&& x.CARRIERID == paraObj.CARRIERID
&& x.PORTLOADID == paraObj.PORTLOADID
&& x.PORTDISCHARGEID == paraObj.PORTDISCHARGEID);
if (!baseList.Any())
{
if (stockObj != null)
{
// 从库存表删除这7项维度的库存数据
await _repStock.DeleteAsync(x => x.Id == stockObj.Id);
}
return;
}
var isInsert = stockObj == null;
var idTemp = stockObj?.Id;
stockObj = baseList[0].Adapt(stockObj);
if (isInsert)
{
stockObj.Id = 0;
}
else
{
stockObj.Id = (long)idTemp;
}
// 总舱位数
stockObj.TOTAL_ORDERS = baseList.Count;
// 取消舱位数
stockObj.CANCEL_NUM = baseList.Count(x => x.IS_CANCELLATION);
// 舱位主键列表
var slotBaseIdList = baseList.Select(x => x.Id).ToList();
// 总的箱型箱量
var ctnAllList = await _repCtn.AsQueryable().Filter(null, true)
.Where(x => !x.IsDeleted && slotBaseIdList.Contains(x.SLOT_ID))
.GroupBy(x => x.CTNALL)
.Select(x => new
{
x.CTNALL,
CTNNUM = SqlFunc.AggregateSum(x.CTNNUM)
}).ToListAsync();
stockObj.CTN_STAT = string.Join(' ', ctnAllList.Select(c => c.CTNALL + "*" + c.CTNNUM));
// 总箱数
stockObj.TOTAL_CTNS = ctnAllList.Sum(x => x.CTNNUM);
// 订舱引用表主键与订舱主表主键
var lstAllocKeyList = await _repAlloc.AsQueryable()
.Filter(null, true)
.Where(x => !x.IsDeleted && slotBaseIdList.Contains(x.BOOKING_SLOT_ID))
.Select(x => new { x.Id, x.BOOKING_SLOT_ID })
.ToListAsync();
// 如果舱位未被引用过,可以直接确定库存
if (!lstAllocKeyList.Any())
{
// 已使用舱位数
stockObj.USE_NUM = 0;
// 已使用的箱型箱量
stockObj.USE_CTN_STAT = "";
// 已使用的箱数
stockObj.USE_CTNS_NUM = 0;
// 剩余的箱型箱量
stockObj.REMAIN_CTN_STAT = stockObj.CTN_STAT;
// 剩余箱数
stockObj.REMAIN_CTNS_NUM = stockObj.TOTAL_CTNS;
}
else
{
// 已使用舱位数
//stockObj.USE_NUM = lstAllocKeyList.DistinctBy(x => x.BOOKING_SLOT_ID).Count();
// 订舱引用表主键列表
var allocIdList = lstAllocKeyList.Select(x => x.Id).ToList();
var allocSlotIdList = lstAllocKeyList.Select(x => x.BOOKING_SLOT_ID).Distinct().ToList();
var userCtnNumList = await _repAllocCtn.AsQueryable().Filter(null, true)
.Where(x => !x.IsDeleted && allocIdList.Contains(x.SLOT_ALLOC_ID))
.GroupBy(x => x.SLOT_ALLOC_ID)
.Select(x => new
{
x.SLOT_ALLOC_ID,
CTNNUM = SqlFunc.AggregateSum(x.CTNNUM)
}).ToListAsync();
var hasCtnNumList = await _repCtn.AsQueryable().Filter(null, true)
.Where(x => !x.IsDeleted && allocSlotIdList.Contains(x.SLOT_ID))
.GroupBy(x => x.SLOT_ID)
.Select(x => new
{
x.SLOT_ID,
CTNNUM = SqlFunc.AggregateSum(x.CTNNUM)
})
.ToListAsync();
var useNum = 0;
foreach (long slotId in allocSlotIdList)
{
List<long> temp1 = lstAllocKeyList.Where(x => x.BOOKING_SLOT_ID == slotId).Select(x => x.Id).ToList();
var userNum = userCtnNumList.Where(x => temp1.Contains(x.SLOT_ALLOC_ID)).Sum(x => x.CTNNUM);
var hasNum = hasCtnNumList.Where(x => x.SLOT_ID == slotId).Sum(x => x.CTNNUM);
if (userNum >= hasNum)
{
useNum++;
}
}
// 已使用舱位数
stockObj.USE_NUM = useNum;
// 已使用的箱型箱量
var userCtnList = await _repAllocCtn.AsQueryable()
.Filter(null, true)
.Where(x => !x.IsDeleted && allocIdList.Contains(x.SLOT_ALLOC_ID))
.GroupBy(x => x.CTNALL)
.Select(x => new
{
x.CTNALL,
CTNNUM = SqlFunc.AggregateSum(x.CTNNUM)
}).ToListAsync();
stockObj.USE_CTN_STAT = string.Join(' ', userCtnList.Select(c => c.CTNALL + "*" + c.CTNNUM));
// 已使用的箱数
stockObj.USE_CTNS_NUM = userCtnList.Sum(x => x.CTNNUM);
// 剩余的箱型箱量
Dictionary<string, int> remainCtnList = new(ctnAllList.Count);
foreach (var item in ctnAllList)
{
var useItem = userCtnList.FirstOrDefault(x => x.CTNALL == item.CTNALL);
if (useItem == null)
{
remainCtnList.Add(item.CTNALL, item.CTNNUM);
}
else
{
int remainCtnNum = item.CTNNUM - useItem.CTNNUM;
if (remainCtnNum > 0)
{
remainCtnList.Add(item.CTNALL, remainCtnNum);
}
}
}
stockObj.REMAIN_CTN_STAT = string.Join(' ', remainCtnList.Select(x => x.Key + "*" + x.Value));
// 剩余箱数
stockObj.REMAIN_CTNS_NUM = stockObj.TOTAL_CTNS - stockObj.USE_CTNS_NUM;
}
if (isInsert)
{
await _repStock.InsertAsync(stockObj);
}
else
{
await _repStock.UpdateAsync(stockObj);
}
}
}
/// <summary>
/// 刷新库存统计对象
/// </summary>
public class BookingSlotStockUpdateModel
{
/// <summary>
/// 船名
/// </summary>
public string VESSEL { get; set; }
/// <summary>
/// 航次号
/// </summary>
public string VOYNO { get; set; }
/// <summary>
/// 合约号
/// </summary>
public string CONTRACT_NO { get; set; }
/// <summary>
/// 订舱方式 CONTRACT_ORDER-合约订舱SPOT_ORDER-SPOT订舱
/// </summary>
public string BOOKING_SLOT_TYPE { get; set; }
/// <summary>
/// 船公司代号
/// </summary>
public string CARRIERID { get; set; }
///// <summary>
///// 收货地
///// </summary>
//public string PLACERECEIPT { get; set; }
///// <summary>
///// 交货地
///// </summary>
//public string PLACEDELIVERY { get; set; }
/// <summary>
/// 装货港代码
/// </summary>
public string PORTLOADID { get; set; }
/// <summary>
/// 卸货港代码
/// </summary>
public string PORTDISCHARGEID { get; set; }
/// <summary>
/// 租户Id
/// </summary>
public long? TenantId { get; set; }
}
}