feat: tenant门店管理首批接口落地
All checks were successful
Build and Deploy TenantApi / build-and-deploy (push) Successful in 30s
All checks were successful
Build and Deploy TenantApi / build-and-deploy (push) Successful in 30s
This commit is contained in:
@@ -0,0 +1,71 @@
|
||||
using MediatR;
|
||||
using TakeoutSaaS.Application.App.Stores.Commands;
|
||||
using TakeoutSaaS.Application.App.Stores.Enums;
|
||||
using TakeoutSaaS.Application.App.Stores.Services;
|
||||
using TakeoutSaaS.Domain.Stores.Entities;
|
||||
using TakeoutSaaS.Domain.Stores.Enums;
|
||||
using TakeoutSaaS.Domain.Stores.Repositories;
|
||||
using TakeoutSaaS.Shared.Abstractions.Constants;
|
||||
using TakeoutSaaS.Shared.Abstractions.Exceptions;
|
||||
|
||||
namespace TakeoutSaaS.Application.App.Stores.Handlers;
|
||||
|
||||
/// <summary>
|
||||
/// 租户端创建门店命令处理器。
|
||||
/// </summary>
|
||||
public sealed class CreateStoreCommandHandler(
|
||||
StoreContextService storeContextService,
|
||||
IStoreRepository storeRepository)
|
||||
: IRequestHandler<CreateStoreCommand>
|
||||
{
|
||||
/// <inheritdoc />
|
||||
public async Task Handle(CreateStoreCommand request, CancellationToken cancellationToken)
|
||||
{
|
||||
// 1. 解析上下文
|
||||
var context = storeContextService.GetRequiredContext();
|
||||
|
||||
// 2. 校验编码唯一性
|
||||
var existingStores = await storeRepository.SearchAsync(
|
||||
context.TenantId,
|
||||
context.MerchantId,
|
||||
status: null,
|
||||
auditStatus: null,
|
||||
businessStatus: null,
|
||||
ownershipType: null,
|
||||
keyword: null,
|
||||
includeDeleted: false,
|
||||
cancellationToken: cancellationToken);
|
||||
var normalizedCode = request.Code.Trim();
|
||||
var hasDuplicateCode = existingStores.Any(store => string.Equals(store.Code, normalizedCode, StringComparison.OrdinalIgnoreCase));
|
||||
if (hasDuplicateCode)
|
||||
{
|
||||
throw new BusinessException(ErrorCodes.Conflict, "门店编码已存在");
|
||||
}
|
||||
|
||||
// 3. 组装门店实体
|
||||
var serviceTypes = request.ServiceTypes?.Count > 0
|
||||
? request.ServiceTypes
|
||||
: [ServiceType.Delivery];
|
||||
var store = new Store
|
||||
{
|
||||
TenantId = context.TenantId,
|
||||
MerchantId = context.MerchantId,
|
||||
Code = normalizedCode,
|
||||
Name = request.Name.Trim(),
|
||||
Phone = request.ContactPhone.Trim(),
|
||||
ManagerName = request.ManagerName.Trim(),
|
||||
Address = request.Address.Trim(),
|
||||
CoverImageUrl = request.CoverImage?.Trim(),
|
||||
SignboardImageUrl = request.CoverImage?.Trim(),
|
||||
OwnershipType = StoreOwnershipType.SameEntity,
|
||||
AuditStatus = StoreAuditStatus.Draft,
|
||||
BusinessStatus = request.BusinessStatus ?? StoreBusinessStatus.Open,
|
||||
Status = StoreStatus.Operating
|
||||
};
|
||||
StoreListMapping.ApplyServiceTypes(store, serviceTypes);
|
||||
|
||||
// 4. 持久化
|
||||
await storeRepository.AddStoreAsync(store, cancellationToken);
|
||||
await storeRepository.SaveChangesAsync(cancellationToken);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user