优化
This commit is contained in:
@@ -2,7 +2,9 @@
|
|||||||
using Microsoft.EntityFrameworkCore.Storage;
|
using Microsoft.EntityFrameworkCore.Storage;
|
||||||
using Microsoft.Extensions.DependencyInjection;
|
using Microsoft.Extensions.DependencyInjection;
|
||||||
using Microsoft.Extensions.Logging;
|
using Microsoft.Extensions.Logging;
|
||||||
|
using Microsoft.Extensions.Options;
|
||||||
using Newtonsoft.Json;
|
using Newtonsoft.Json;
|
||||||
|
using StackExchange.Redis;
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Concurrent;
|
using System.Collections.Concurrent;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
@@ -25,6 +27,7 @@ using WMS.Web.Domain.Infrastructure;
|
|||||||
using WMS.Web.Domain.IService;
|
using WMS.Web.Domain.IService;
|
||||||
using WMS.Web.Domain.IService.Public;
|
using WMS.Web.Domain.IService.Public;
|
||||||
using WMS.Web.Domain.Mappers;
|
using WMS.Web.Domain.Mappers;
|
||||||
|
using WMS.Web.Domain.Options;
|
||||||
using WMS.Web.Domain.Values;
|
using WMS.Web.Domain.Values;
|
||||||
using WMS.Web.Domain.Values.Erp;
|
using WMS.Web.Domain.Values.Erp;
|
||||||
|
|
||||||
@@ -51,9 +54,11 @@ namespace WMS.Web.Domain.Services
|
|||||||
private readonly IBoxInventoryRepositories _boxInventoryRepositories;
|
private readonly IBoxInventoryRepositories _boxInventoryRepositories;
|
||||||
private readonly ILogger<InStockService> _logger;
|
private readonly ILogger<InStockService> _logger;
|
||||||
private readonly IServiceScopeFactory _serviceScopeFactory;
|
private readonly IServiceScopeFactory _serviceScopeFactory;
|
||||||
|
private readonly AppOptions _options;
|
||||||
|
private ConnectionMultiplexer redisMultiplexer;
|
||||||
|
public StackExchange.Redis.IDatabase _redisDb = null;
|
||||||
|
|
||||||
private readonly ConcurrentDictionary<int, SemaphoreSlim> _locks = new ConcurrentDictionary<int, SemaphoreSlim>();
|
public InStockService(IMapper mapper, IOptions<AppOptions> options, ISerialNumbersRepositories serialNumbersRepositories, IErpService erpService, IBoxInventoryService boxInventoryService, ISerialNumberService serialNumberService, ILoginService loginService, IBoxRepositories boxRepositories,
|
||||||
public InStockService(IMapper mapper, ISerialNumbersRepositories serialNumbersRepositories, IErpService erpService, IBoxInventoryService boxInventoryService, ISerialNumberService serialNumberService, ILoginService loginService, IBoxRepositories boxRepositories,
|
|
||||||
IBasicsRepositories basicsRepositories, IErpBasicDataExtendService erpBasicDataExtendService, IChangeMoveBoxService changeMoveBoxService, IInStockTaskBoxRepositories inStockTaskBoxRepositories,
|
IBasicsRepositories basicsRepositories, IErpBasicDataExtendService erpBasicDataExtendService, IChangeMoveBoxService changeMoveBoxService, IInStockTaskBoxRepositories inStockTaskBoxRepositories,
|
||||||
IInStockRepositories inStockRepositories, IInStockTaskRepositories inStockTaskRepositories, IBoxInventoryRepositories boxInventoryRepositories, ILogger<InStockService> logger, IServiceScopeFactory serviceScopeFactory)
|
IInStockRepositories inStockRepositories, IInStockTaskRepositories inStockTaskRepositories, IBoxInventoryRepositories boxInventoryRepositories, ILogger<InStockService> logger, IServiceScopeFactory serviceScopeFactory)
|
||||||
{
|
{
|
||||||
@@ -73,6 +78,9 @@ namespace WMS.Web.Domain.Services
|
|||||||
_erpBasicDataExtendService = erpBasicDataExtendService;
|
_erpBasicDataExtendService = erpBasicDataExtendService;
|
||||||
_serialNumbersRepositories = serialNumbersRepositories;
|
_serialNumbersRepositories = serialNumbersRepositories;
|
||||||
_boxInventoryRepositories = boxInventoryRepositories;
|
_boxInventoryRepositories = boxInventoryRepositories;
|
||||||
|
_options = options?.Value;
|
||||||
|
redisMultiplexer = ConnectionMultiplexer.Connect(_options.RedisConnectionString);
|
||||||
|
_redisDb = redisMultiplexer.GetDatabase();
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@@ -133,39 +141,50 @@ namespace WMS.Web.Domain.Services
|
|||||||
/// <returns></returns>
|
/// <returns></returns>
|
||||||
public async Task<Result> Shelf(PurchaseShelfRequest instock, LoginInDto loginInfo)
|
public async Task<Result> Shelf(PurchaseShelfRequest instock, LoginInDto loginInfo)
|
||||||
{
|
{
|
||||||
var taskId= instock.Details.Select(x => x.TaskId).FirstOrDefault();
|
var taskId = instock.Details.Select(x => x.TaskId).FirstOrDefault();
|
||||||
|
|
||||||
var taskLock = _locks.GetOrAdd(taskId, _ => new SemaphoreSlim(1, 1));
|
// 构建 Redis 锁的键名
|
||||||
await taskLock.WaitAsync();
|
string lockKey = $"lock:taskid{taskId}";
|
||||||
try
|
// 构建 Redis 锁的值,用于标识锁的持有者
|
||||||
|
string lockValue = Guid.NewGuid().ToString();
|
||||||
|
// 获取 Redis 锁,设置超时时间为 10 秒
|
||||||
|
if (await _redisDb.LockTakeAsync(lockKey, lockValue, TimeSpan.FromSeconds(10)))
|
||||||
{
|
{
|
||||||
IDbContextTransaction _transaction = _basicsRepositories.GetTransaction();
|
try
|
||||||
bool isRollback = false;
|
|
||||||
bool isTransaction = false;
|
|
||||||
//1.添加入库单:(同步金蝶在save方法里面进行)
|
|
||||||
var save_result = await this.ShelfSave(instock, InstockType.Purchase, loginInfo, isTransaction);
|
|
||||||
if (!save_result.IsSuccess) isRollback = true;
|
|
||||||
|
|
||||||
//实体
|
|
||||||
var entity = save_result.Data;
|
|
||||||
|
|
||||||
//提交事务
|
|
||||||
var isSuccess = _basicsRepositories.CommitTransaction(isRollback, _transaction);
|
|
||||||
if (!isSuccess)
|
|
||||||
return save_result;
|
|
||||||
|
|
||||||
//同步金蝶
|
|
||||||
if (entity.Type == InstockType.Purchase)
|
|
||||||
{
|
{
|
||||||
OperateRequest oRequest = new OperateRequest();
|
IDbContextTransaction _transaction = _basicsRepositories.GetTransaction();
|
||||||
oRequest.Ids.Add(entity.Id);
|
bool isRollback = false;
|
||||||
await Sync(oRequest, loginInfo, false);
|
bool isTransaction = false;
|
||||||
|
//1.添加入库单:(同步金蝶在save方法里面进行)
|
||||||
|
var save_result = await this.ShelfSave(instock, InstockType.Purchase, loginInfo, isTransaction);
|
||||||
|
if (!save_result.IsSuccess) isRollback = true;
|
||||||
|
|
||||||
|
//实体
|
||||||
|
var entity = save_result.Data;
|
||||||
|
|
||||||
|
//提交事务
|
||||||
|
var isSuccess = _basicsRepositories.CommitTransaction(isRollback, _transaction);
|
||||||
|
if (!isSuccess)
|
||||||
|
return save_result;
|
||||||
|
|
||||||
|
//同步金蝶
|
||||||
|
if (entity.Type == InstockType.Purchase)
|
||||||
|
{
|
||||||
|
OperateRequest oRequest = new OperateRequest();
|
||||||
|
oRequest.Ids.Add(entity.Id);
|
||||||
|
await Sync(oRequest, loginInfo, false);
|
||||||
|
}
|
||||||
|
return Result.ReSuccess();
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
// 释放 Redis 锁
|
||||||
|
await _redisDb.LockReleaseAsync(lockKey, lockValue);
|
||||||
}
|
}
|
||||||
return Result.ReSuccess();
|
|
||||||
}
|
}
|
||||||
finally
|
else
|
||||||
{
|
{
|
||||||
taskLock.Release();
|
return Result.ReFailure(ResultCodes.Concurrent_Instock);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -37,13 +37,15 @@ namespace WMS.Web.Domain.Services
|
|||||||
var delete_ids = new List<int>();
|
var delete_ids = new List<int>();
|
||||||
var t_boxIds = boxIds.Distinct().ToList();
|
var t_boxIds = boxIds.Distinct().ToList();
|
||||||
var list= await _inStockTaskBoxRepositories.GetListBy(t_boxIds);
|
var list= await _inStockTaskBoxRepositories.GetListBy(t_boxIds);
|
||||||
var boxInvetList = await _boxInventoryRepositories.GetList(t_boxIds);
|
|
||||||
foreach (var item in list)
|
delete_ids= list.Select(x => x.Id).ToList();
|
||||||
{
|
//var boxInvetList = await _boxInventoryRepositories.GetList(t_boxIds);
|
||||||
var isHave= boxInvetList.Where(x => x.BoxId == item.BoxId).Any();
|
//foreach (var item in list)
|
||||||
if (!isHave)
|
//{
|
||||||
delete_ids.Add(item.Id);
|
// var isHave= boxInvetList.Where(x => x.BoxId == item.BoxId).Any();
|
||||||
}
|
// if (!isHave)
|
||||||
|
// delete_ids.Add(item.Id);
|
||||||
|
//}
|
||||||
|
|
||||||
if (delete_ids.Count != 0)
|
if (delete_ids.Count != 0)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -22,6 +22,8 @@ namespace WMS.Web.Domain.Services.Public
|
|||||||
db = redisMultiplexer.GetDatabase();
|
db = redisMultiplexer.GetDatabase();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
#region String
|
#region String
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// 保存单个key value
|
/// 保存单个key value
|
||||||
|
|||||||
@@ -24,7 +24,7 @@ namespace WMS.Web.Domain.Values
|
|||||||
public static ValueTuple<int, string> NoDateError = (40005, "数据不存在");
|
public static ValueTuple<int, string> NoDateError = (40005, "数据不存在");
|
||||||
public static ValueTuple<int, string> SourceBillNoDateError = (40005, "来源单不存在,请核对后再试");
|
public static ValueTuple<int, string> SourceBillNoDateError = (40005, "来源单不存在,请核对后再试");
|
||||||
|
|
||||||
public static ValueTuple<int, string> Concurrent_Instock = (80005, "该任务单正在处理中");
|
public static ValueTuple<int, string> Concurrent_Instock = (80005, "该来源单正在处理中");
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// 没有菜单权限,无法登录
|
/// 没有菜单权限,无法登录
|
||||||
|
|||||||
Reference in New Issue
Block a user