You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
200 lines
8.4 KiB
200 lines
8.4 KiB
using AutoMapper;
|
|
using Kean.Domain.Stock.Commands;
|
|
using Kean.Domain.Stock.Events;
|
|
using Kean.Domain.Stock.Repositories;
|
|
using Kean.Domain.Stock.SharedServices.Proxies;
|
|
using Kean.Infrastructure.Configuration;
|
|
using Newtonsoft.Json;
|
|
using Newtonsoft.Json.Linq;
|
|
using System;
|
|
using System.Linq;
|
|
using System.Threading;
|
|
using System.Threading.Tasks;
|
|
|
|
namespace Kean.Domain.Stock.CommandHandlers
|
|
{
|
|
/// <summary>
|
|
/// 入库命令处理程序
|
|
/// </summary>
|
|
public sealed class ScanInboundCommandHandler : CommandHandler<ScanInboundCommand>
|
|
{
|
|
private readonly ICommandBus _commandBus; // 命令总线
|
|
private readonly INotification _notifications; // 总线通知
|
|
private readonly IMapper _mapper; // 模型映射
|
|
private readonly IStockRepository _stockRepository; // 存储仓库
|
|
private readonly IWarehouseRepository _warehouseRepository; // 库房仓库
|
|
private readonly BarcodeValidator _barcodeValidator; // 条码验证器
|
|
private readonly TaskProxy _taskProxy; // 任务域
|
|
private readonly MaterialProxy _materialProxy; // 物料服务
|
|
|
|
/// <summary>
|
|
/// 依赖注入
|
|
/// </summary>
|
|
public ScanInboundCommandHandler(
|
|
ICommandBus commandBus,
|
|
INotification notifications,
|
|
IMapper mapper,
|
|
IStockRepository stockRepository,
|
|
IWarehouseRepository warehouseRepository,
|
|
BarcodeValidator barcodeValidator,
|
|
MaterialProxy materialProxy,
|
|
TaskProxy taskProxy)
|
|
{
|
|
_commandBus = commandBus;
|
|
_notifications = notifications;
|
|
_mapper = mapper;
|
|
_stockRepository = stockRepository;
|
|
_warehouseRepository = warehouseRepository;
|
|
_barcodeValidator = barcodeValidator;
|
|
_taskProxy = taskProxy;
|
|
_materialProxy = materialProxy;
|
|
}
|
|
|
|
/// <summary>
|
|
/// 处理程序
|
|
/// </summary>
|
|
public override async Task Handle(ScanInboundCommand command, CancellationToken cancellationToken)
|
|
{
|
|
if (command.ValidationResult.IsValid)
|
|
{
|
|
// 条码格式校验
|
|
if (!await _barcodeValidator.Validate(command.Barcode))
|
|
{
|
|
await _commandBus.Notify(nameof(command.Barcode), "条码格式不正确", command.Barcode,
|
|
cancellationToken: cancellationToken);
|
|
return;
|
|
}
|
|
//校验 托盘规则与物料类型是否匹配
|
|
var sCategory = await _materialProxy.GetMaterialClass(command.Lines.First().Material);
|
|
Models.Category category = JsonConvert.DeserializeObject<Models.Category>(sCategory);
|
|
if (!(category.Code.Contains(command.Barcode.Substring(2,1))))
|
|
{
|
|
await _commandBus.Notify(nameof(command.Barcode), $"托盘({command.Barcode})不能装载 物料类别({category.Code})的物料", command.Barcode,
|
|
cancellationToken: cancellationToken);
|
|
return;
|
|
}
|
|
|
|
// 托盘有任务
|
|
if (await _taskProxy.HasTask(command.Barcode))
|
|
{
|
|
await _commandBus.Notify(nameof(command.Barcode), $"托盘({command.Barcode})已有任务", command.Barcode,
|
|
cancellationToken: cancellationToken);
|
|
return;
|
|
}
|
|
var original = command.Barcode == string.Empty ? null : await _stockRepository.GetCell(command.Barcode);
|
|
// 托盘已存在
|
|
if (original.HasValue)
|
|
{
|
|
await _commandBus.Notify(nameof(command.Barcode), $"{command.Barcode}已有库存", command.Barcode,
|
|
cancellationToken: cancellationToken);
|
|
return;
|
|
}
|
|
// 托盘不存在
|
|
else
|
|
{
|
|
//车身 车架
|
|
if (command.Barcode.Substring(0,3) == "LCF" || command.Barcode.Substring(0, 3) == "LCG")
|
|
{
|
|
original = 12001;
|
|
}
|
|
else
|
|
{
|
|
original = 12007;
|
|
}
|
|
//// 要求指定位置
|
|
//if (!command.Destination.HasValue)
|
|
//{
|
|
// await _commandBus.Notify(nameof(command.Destination), "位置未指定", command.Destination,
|
|
// cancellationToken: cancellationToken);
|
|
// return;
|
|
//}
|
|
//// 如果命令中带有位置,要求该位置不是立库货位
|
|
//if (await _warehouseRepository.IsCell(command.Destination.Value) != false)
|
|
//{
|
|
// await _commandBus.Notify(nameof(command.Destination), "位置不可用", command.Destination,
|
|
// cancellationToken: cancellationToken);
|
|
// return;
|
|
//}
|
|
|
|
}
|
|
|
|
//校验膜卷号唯一
|
|
foreach (var r in command.Lines)
|
|
{
|
|
if (await this._stockRepository.GetStorageBill(r.Bill) != null)
|
|
{
|
|
await _commandBus.Notify(nameof(r.Bill), $"膜卷码({r.Bill})已经存在,不能再入库", command.Barcode,
|
|
cancellationToken: cancellationToken);
|
|
return;
|
|
}
|
|
}
|
|
|
|
if (!string.IsNullOrEmpty(command.Tag))
|
|
{
|
|
JObject jObj = JObject.Parse(command.Tag);
|
|
jObj.Add("requestNo", command.RequestNo);
|
|
|
|
command.Tag = JsonConvert.SerializeObject(jObj);
|
|
}
|
|
else
|
|
{
|
|
//command.Tag = JsonConvert.SerializeObject(new
|
|
//{
|
|
// requestNo = command.RequestNo
|
|
//});
|
|
}
|
|
|
|
// 时间戳
|
|
command.Timestamp ??= DateTime.Now;
|
|
// 切点事件
|
|
var event0 = _mapper.Map<ScanInboundExecutingEvent>(command);
|
|
event0.Cell = command.Destination ?? original.Value;
|
|
await _commandBus.Trigger(event0, cancellationToken);
|
|
if (!_notifications.Any())
|
|
{
|
|
// 允许创建库存
|
|
var stock = _mapper.Map<Models.Stock>(command);
|
|
stock.Cell = command.Destination ?? original.Value;
|
|
stock.Timestamp = command.Timestamp.Value;
|
|
|
|
if (await _stockRepository.CreateStock(stock).ContinueWith(task =>
|
|
{
|
|
if (task.Exception?.InnerException is RepositoryException ex)
|
|
{
|
|
task.Exception.Handle(_ => true);
|
|
_commandBus.Notify(ex.Member.Key, ex.Message, ex.Member.Value,
|
|
cancellationToken: cancellationToken).Wait();
|
|
return true;
|
|
}
|
|
return false;
|
|
}))
|
|
{
|
|
return;
|
|
}
|
|
// 成功事件
|
|
var event1 = _mapper.Map<ScanInboundSuccessEvent>(command);
|
|
event1.Cell = stock.Cell;
|
|
event1.Timestamp = command.Timestamp.Value;
|
|
await _commandBus.Trigger(event1, cancellationToken);
|
|
}
|
|
|
|
// //获取最佳入库口
|
|
// string startStation = await this._warehouseRepository.GetInStartDevice((int)command.Destination, null, command.Barcode.Substring(0, 5), command.Lines.First().Material, command.Barcode);
|
|
// if (string.IsNullOrEmpty(startStation))
|
|
// {
|
|
// await _commandBus.Notify(nameof(command.Tag), $"设备故障,请先排除故障", startStation,
|
|
//cancellationToken: cancellationToken);
|
|
// return;
|
|
// }
|
|
// Output(nameof(command.Tag), startStation);
|
|
|
|
}
|
|
else
|
|
{
|
|
await _commandBus.Notify(command.ValidationResult,
|
|
cancellationToken: cancellationToken);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|