All checks were successful
Build and Deploy / deploy (push) Successful in 1m3s
Co-authored-by: Cursor <cursoragent@cursor.com>
184 lines
7.3 KiB
C#
184 lines
7.3 KiB
C#
using System.Linq.Expressions;
|
|
using Fake.Application;
|
|
using Microsoft.AspNetCore.Mvc;
|
|
using Oms.Application.Dtos.Shared;
|
|
using Oms.Application.Dtos.System;
|
|
using Oms.Application.Shared;
|
|
using Oms.Domain.SystemAggregate.Consts;
|
|
using Oms.Domain.SystemAggregate.Entities;
|
|
using Oms.Domain.SystemAggregate.Repositories;
|
|
|
|
namespace Oms.Application.Services.System;
|
|
|
|
/// <summary>
|
|
/// 仓库 API 服务。
|
|
/// </summary>
|
|
[ApiExplorerSettings(GroupName = "OMS-System")]
|
|
public class WarehouseService : ApplicationService
|
|
{
|
|
private IWarehouseAddressRepository WarehouseAddressRepository => LazyServiceProvider.GetRequiredService<IWarehouseAddressRepository>();
|
|
|
|
private OmsRbacUserDisplayNameResolver UserDisplayNameResolver =>
|
|
LazyServiceProvider.GetRequiredService<OmsRbacUserDisplayNameResolver>();
|
|
|
|
/// <summary>
|
|
/// 查询仓库列表。
|
|
/// </summary>
|
|
/// <param name="input">入参:仓库分页查询条件。</param>
|
|
/// <returns>仓库分页结果,包含列表数据和总记录数。</returns>
|
|
[HttpGet("/system/warehouse/list")]
|
|
public async Task<OmsPageResult<WarehousePaginatedOutput>> GetPaginatedListAsync([FromQuery] WarehousePaginatedInput input)
|
|
{
|
|
var predicate = BuildPaginatedPredicate(input);
|
|
var pageIndex = OmsDocHelper.NormalizePage(input.Page);
|
|
var pageSize = OmsDocHelper.NormalizePageSize(input.PageSize);
|
|
|
|
var entities = await WarehouseAddressRepository.GetPagedListAsync(
|
|
predicate,
|
|
pageIndex,
|
|
pageSize,
|
|
new Dictionary<string, bool> { [nameof(WarehouseAddress.UpdateTime)] = false, [nameof(WarehouseAddress.Id)] = false });
|
|
|
|
var totalCount = await WarehouseAddressRepository.CountAsync(predicate);
|
|
var items = entities.Select(entity =>
|
|
{
|
|
var output = ObjectMapper.Map<WarehouseAddress, WarehousePaginatedOutput>(entity);
|
|
output.WarehouseTypeName = OmsDocHelper.GetWarehouseTypeName(entity.WarehouseType);
|
|
output.UpdateTime = OmsDocHelper.NullIfDefault(entity.UpdateTime);
|
|
return output;
|
|
}).ToList();
|
|
|
|
return new OmsPageResult<WarehousePaginatedOutput>
|
|
{
|
|
Items = items,
|
|
Total = totalCount
|
|
};
|
|
}
|
|
|
|
/// <summary>
|
|
/// 查询仓库详情。
|
|
/// </summary>
|
|
/// <param name="id">入参:目标主键。</param>
|
|
/// <returns>仓库详情。</returns>
|
|
[HttpGet("/system/warehouse/detail")]
|
|
public async Task<WarehouseOutput> GetByIdAsync([FromQuery] int id)
|
|
{
|
|
var entity = await GetWarehouseOrThrowAsync(id);
|
|
var output = ObjectMapper.Map<WarehouseAddress, WarehouseOutput>(entity);
|
|
var auditUserNameMap = await UserDisplayNameResolver.ResolveManyAsync(
|
|
[entity.CreateUserId, entity.UpdateUserId]);
|
|
output.CreateBy = OmsRbacUserDisplayNameResolver.FormatUserId(entity.CreateUserId, auditUserNameMap);
|
|
output.UpdateBy = OmsRbacUserDisplayNameResolver.FormatUserId(entity.UpdateUserId, auditUserNameMap);
|
|
output.UpdateTime = OmsDocHelper.NullIfDefault(entity.UpdateTime);
|
|
return output;
|
|
}
|
|
|
|
/// <summary>
|
|
/// 新增仓库。
|
|
/// </summary>
|
|
/// <param name="input">入参:仓库创建参数。</param>
|
|
/// <returns>无返回体,仅完成新增仓库。</returns>
|
|
[HttpPost("/system/warehouse/create")]
|
|
public async Task CreateAsync(CreateWarehouseInput input)
|
|
{
|
|
var warehouseName = input.WarehouseName.Trim();
|
|
var duplicatedWarehouse = await WarehouseAddressRepository.GetByWarehouseNameAsync(warehouseName);
|
|
if (duplicatedWarehouse != null)
|
|
{
|
|
throw new BusinessException("仓库名称已存在");
|
|
}
|
|
|
|
var deleted = await WarehouseAddressRepository.GetByWarehouseNameIncludingDeletedAsync(warehouseName);
|
|
if (deleted != null && deleted.IsDeleted)
|
|
{
|
|
deleted.IsDeleted = false;
|
|
deleted.WarehouseName = warehouseName;
|
|
deleted.WarehouseType = input.WarehouseType;
|
|
deleted.Recipient = input.Recipient;
|
|
deleted.ContactPhone = input.ContactPhone;
|
|
deleted.ShippingAddress = input.ShippingAddress;
|
|
await WarehouseAddressRepository.UpdateAsync(deleted);
|
|
return;
|
|
}
|
|
|
|
var entity = new WarehouseAddress
|
|
{
|
|
WarehouseName = warehouseName,
|
|
WarehouseType = input.WarehouseType,
|
|
Recipient = input.Recipient,
|
|
ContactPhone = input.ContactPhone,
|
|
ShippingAddress = input.ShippingAddress,
|
|
};
|
|
|
|
await WarehouseAddressRepository.InsertAsync(entity);
|
|
}
|
|
|
|
/// <summary>
|
|
/// 更新仓库。
|
|
/// </summary>
|
|
/// <param name="input">入参:仓库更新参数。</param>
|
|
/// <returns>无返回体,仅完成更新仓库。</returns>
|
|
[HttpPost("/system/warehouse/update")]
|
|
public async Task UpdateAsync(UpdateWarehouseInput input)
|
|
{
|
|
var entity = await GetWarehouseOrThrowAsync(input.Id);
|
|
var warehouseName = input.WarehouseName.Trim();
|
|
var duplicatedWarehouse = await WarehouseAddressRepository.GetByWarehouseNameAsync(warehouseName);
|
|
if (duplicatedWarehouse != null && duplicatedWarehouse.Id != entity.Id)
|
|
{
|
|
throw new BusinessException("仓库名称已存在");
|
|
}
|
|
|
|
var softDeleted = await WarehouseAddressRepository.GetByWarehouseNameIncludingDeletedAsync(warehouseName);
|
|
if (softDeleted != null && softDeleted.IsDeleted && softDeleted.Id != entity.Id)
|
|
{
|
|
softDeleted.WarehouseName = $"{warehouseName}__deleted_{softDeleted.Id}";
|
|
await WarehouseAddressRepository.UpdateAsync(softDeleted);
|
|
}
|
|
|
|
entity.WarehouseName = warehouseName;
|
|
entity.WarehouseType = input.WarehouseType;
|
|
entity.Recipient = input.Recipient;
|
|
entity.ContactPhone = input.ContactPhone;
|
|
entity.ShippingAddress = input.ShippingAddress;
|
|
|
|
await WarehouseAddressRepository.UpdateAsync(entity);
|
|
}
|
|
|
|
/// <summary>
|
|
/// 删除仓库。
|
|
/// </summary>
|
|
/// <param name="input">入参:目标主键。</param>
|
|
/// <returns>无返回体,仅完成删除仓库。</returns>
|
|
[HttpPost("/system/warehouse/delete")]
|
|
public async Task DeleteAsync(IdInput input)
|
|
{
|
|
var entity = await GetWarehouseOrThrowAsync(input.Id);
|
|
await WarehouseAddressRepository.DeleteAsync(entity);
|
|
}
|
|
|
|
private Expression<Func<WarehouseAddress, bool>> BuildPaginatedPredicate(WarehousePaginatedInput input)
|
|
{
|
|
var keyword = input.Keyword?.Trim();
|
|
var warehouseType = input.WarehouseType?.Trim();
|
|
|
|
return warehouse =>
|
|
(string.IsNullOrWhiteSpace(warehouseType) || warehouse.WarehouseType == warehouseType) &&
|
|
(string.IsNullOrWhiteSpace(keyword) ||
|
|
warehouse.WarehouseName.Contains(keyword) ||
|
|
(warehouse.Recipient ?? string.Empty).Contains(keyword) ||
|
|
(warehouse.ContactPhone ?? string.Empty).Contains(keyword));
|
|
}
|
|
|
|
private async Task<WarehouseAddress> GetWarehouseOrThrowAsync(int id)
|
|
{
|
|
var entity = await WarehouseAddressRepository.FirstOrDefaultAsync(x => x.Id == id);
|
|
if (entity == null)
|
|
{
|
|
throw new BusinessException("仓库不存在");
|
|
}
|
|
|
|
return entity;
|
|
}
|
|
}
|