Files
CMS/src/CMSMicroservice.WebApi/Common/Mappings/InventoryProfile.cs
T
masoodafar-web 8c3d710253
Build and Deploy to Kubernetes / build-and-deploy (push) Failing after 1m37s
feat(mappings): expand InventoryProfile with comprehensive CQRS mappings for warehouses and inventory items
2026-01-03 10:05:47 +03:30

248 lines
12 KiB
C#

using CMSMicroservice.Domain.Entities;
using CMSMicroservice.Protobuf.Protos.Inventory;
using CMSMicroservice.Application.Features.Warehouses.Commands;
using CMSMicroservice.Application.Features.Warehouses.Queries;
using CMSMicroservice.Application.Features.InventoryItems.Commands;
using CMSMicroservice.Application.Features.InventoryItems.Queries;
using CMSMicroservice.Application.Features.StockMovements.Commands;
using CMSMicroservice.Application.Features.StockMovements.Queries;
using Google.Protobuf.WellKnownTypes;
using ProtoProductType = CMSMicroservice.Protobuf.Protos.Inventory.ProductType;
using DomainProductType = CMSMicroservice.Domain.Enums.ProductType;
using ProtoStockMovementType = CMSMicroservice.Protobuf.Protos.Inventory.StockMovementType;
using DomainStockMovementType = CMSMicroservice.Domain.Enums.StockMovementType;
namespace CMSMicroservice.WebApi.Common.Mappings;
/// <summary>
/// Mapster profile برای Inventory Protobuf به CQRS و Entities به DTOs
/// </summary>
public class InventoryProfile : IRegister
{
void IRegister.Register(TypeAdapterConfig config)
{
// =============================================
// Protobuf Request به CQRS Query/Command Mappings
// =============================================
// Warehouse Commands
config.NewConfig<CreateWarehouseRequest, CreateWarehouseCommand>()
.MapWith(src => new CreateWarehouseCommand
{
Name = src.Name,
Code = src.Code,
Address = src.Address,
IsDefault = src.IsDefault
});
config.NewConfig<UpdateWarehouseRequest, UpdateWarehouseCommand>()
.MapWith(src => new UpdateWarehouseCommand
{
Id = src.Id,
Name = src.Name,
Code = src.Code,
Address = src.Address,
IsActive = src.IsActive
});
config.NewConfig<DeleteWarehouseRequest, DeleteWarehouseCommand>()
.MapWith(src => new DeleteWarehouseCommand(src.Id));
config.NewConfig<SetDefaultWarehouseRequest, SetDefaultWarehouseCommand>()
.MapWith(src => new SetDefaultWarehouseCommand(src.Id));
// Warehouse Queries
config.NewConfig<GetWarehouseRequest, GetWarehouseByIdQuery>()
.MapWith(src => new GetWarehouseByIdQuery(src.Id));
config.NewConfig<GetAllWarehousesRequest, GetAllWarehousesQuery>()
.MapWith(src => new GetAllWarehousesQuery());
// Inventory Item Queries
config.NewConfig<GetInventoryItemRequest, GetInventoryItemByIdQuery>()
.MapWith(src => new GetInventoryItemByIdQuery(src.Id));
config.NewConfig<GetInventoryByProductRequest, GetInventoryItemByProductIdQuery>()
.MapWith(src => new GetInventoryItemByProductIdQuery(src.ProductId, null));
config.NewConfig<GetInventoryByProductRequest, GetInventoryItemByDiscountProductIdQuery>()
.MapWith(src => new GetInventoryItemByDiscountProductIdQuery(src.ProductId, null));
config.NewConfig<GetAllInventoryItemsRequest, SearchInventoryItemsQuery>()
.MapWith(src => new SearchInventoryItemsQuery(
null, // SearchTerm
null, // ProductType
null, // WarehouseId
null, // MinQuantity
null, // MaxQuantity
0, // Skip
50 // Take
));
config.NewConfig<GetLowStockItemsRequest, GetLowStockItemsQuery>()
.MapWith(src => new GetLowStockItemsQuery(null, 1));
// Inventory Item Commands
config.NewConfig<UpdateInventorySettingsRequest, UpdateInventoryItemCommand>()
.MapWith(src => new UpdateInventoryItemCommand
{
Id = src.Id,
LowStockThreshold = src.LowStockThreshold,
ReorderPoint = src.ReorderPoint,
MaxStockLevel = src.MaxStockLevel
});
// Stock Operation Commands
config.NewConfig<AddStockRequest, IncreaseInventoryCommand>()
.MapWith(src => new IncreaseInventoryCommand
{
ProductId = src.ProductId,
ProductType = (DomainProductType)src.ProductType,
Quantity = src.Quantity,
Note = src.Note,
ReferenceNumber = src.ReferenceNumber,
WarehouseId = src.WarehouseId?.Value ?? 1
});
config.NewConfig<AdjustStockRequest, UpdateInventoryQuantityCommand>()
.MapWith(src => new UpdateInventoryQuantityCommand
{
ProductId = src.ProductId,
ProductType = (DomainProductType)src.ProductType,
NewQuantity = src.NewQuantity,
Note = src.Note,
ReferenceNumber = src.ReferenceNumber,
WarehouseId = src.WarehouseId?.Value ?? 1
});
config.NewConfig<ReserveStockRequest, ReserveInventoryCommand>()
.MapWith(src => new ReserveInventoryCommand
{
ProductId = src.ProductId,
ProductType = (DomainProductType)src.ProductType,
Quantity = src.Quantity,
Note = src.Note,
ReferenceNumber = src.ReferenceNumber,
OrderId = src.OrderId?.Value,
WarehouseId = src.WarehouseId?.Value ?? 1
});
config.NewConfig<ReleaseReservationRequest, ReleaseReservedInventoryCommand>()
.MapWith(src => new ReleaseReservedInventoryCommand
{
ProductId = src.ProductId,
ProductType = (DomainProductType)src.ProductType,
Quantity = src.Quantity,
Note = src.Note,
ReferenceNumber = src.ReferenceNumber,
WarehouseId = src.WarehouseId?.Value ?? 1
});
config.NewConfig<ConfirmSaleRequest, ReduceInventoryCommand>()
.MapWith(src => new ReduceInventoryCommand
{
ProductId = src.ProductId,
ProductType = (DomainProductType)src.ProductType,
Quantity = src.Quantity,
Note = src.Note,
ReferenceNumber = src.ReferenceNumber,
OrderId = src.OrderId?.Value,
WarehouseId = src.WarehouseId?.Value ?? 1
});
config.NewConfig<ProcessReturnRequest, IncreaseInventoryCommand>()
.MapWith(src => new IncreaseInventoryCommand
{
ProductId = src.ProductId,
ProductType = (DomainProductType)src.ProductType,
Quantity = src.Quantity,
Note = !string.IsNullOrEmpty(src.Note) ? src.Note : "Product return",
ReferenceNumber = src.ReferenceNumber,
OrderId = src.OrderId?.Value,
WarehouseId = src.WarehouseId?.Value ?? 1
});
config.NewConfig<RecordLossRequest, CreateStockMovementCommand>()
.MapWith(src => new CreateStockMovementCommand
{
ProductId = src.ProductId,
ProductType = (DomainProductType)src.ProductType,
MovementType = DomainStockMovementType.Loss,
Quantity = src.Quantity,
Note = !string.IsNullOrEmpty(src.Note) ? src.Note : "Stock loss/damage",
ReferenceNumber = src.ReferenceNumber,
WarehouseId = src.WarehouseId?.Value ?? 1
});
// Stock Movement Queries
config.NewConfig<GetStockMovementsRequest, SearchStockMovementsQuery>()
.MapWith(src => new SearchStockMovementsQuery
{
InventoryItemId = src.InventoryItemId?.Value,
ProductId = src.ProductId?.Value,
ProductType = src.ProductType != ProtoProductType.Unspecified ? (DomainProductType?)src.ProductType : null,
MovementType = src.MovementType != ProtoStockMovementType.Unspecified ? (DomainStockMovementType?)src.MovementType : null,
StartDate = src.StartDate?.ToDateTime(),
EndDate = src.EndDate?.ToDateTime(),
Skip = src.Skip,
Take = src.Take > 0 ? src.Take : 50
});
config.NewConfig<GetStockMovementsByInventoryItemRequest, GetInventoryItemMovementHistoryQuery>()
.MapWith(src => new GetInventoryItemMovementHistoryQuery
{
InventoryItemId = src.InventoryItemId,
Skip = (src.Page - 1) * src.PageSize,
Take = src.PageSize > 0 ? src.PageSize : 50
});
// =============================================
// Entity به Protobuf DTO Mappings
// =============================================
// Warehouse Entity به WarehouseDto
config.NewConfig<Warehouse, WarehouseDto>()
.Map(dest => dest.Id, src => src.Id)
.Map(dest => dest.Name, src => src.Name)
.Map(dest => dest.Code, src => src.Code ?? string.Empty)
.Map(dest => dest.Address, src => src.Address ?? string.Empty)
.Map(dest => dest.IsDefault, src => src.IsDefault)
.Map(dest => dest.IsActive, src => src.IsActive);
// InventoryItem Entity به InventoryItemDto
config.NewConfig<InventoryItem, InventoryItemDto>()
.Map(dest => dest.Id, src => src.Id)
.Map(dest => dest.WarehouseId, src => src.WarehouseId)
.Map(dest => dest.WarehouseName, src => src.Warehouse != null ? src.Warehouse.Name : string.Empty)
.Map(dest => dest.ProductId, src => src.ProductId.HasValue ? new Int64Value { Value = src.ProductId.Value } : null)
.Map(dest => dest.DiscountProductId, src => src.DiscountProductId.HasValue ? new Int64Value { Value = src.DiscountProductId.Value } : null)
.Map(dest => dest.ProductType, src => (ProtoProductType)src.ProductType)
.Map(dest => dest.Quantity, src => src.Quantity)
.Map(dest => dest.ReservedQuantity, src => src.ReservedQuantity)
.Map(dest => dest.AvailableQuantity, src => src.AvailableQuantity)
.Map(dest => dest.LowStockThreshold, src => src.LowStockThreshold)
.Map(dest => dest.ReorderPoint, src => src.ReorderPoint)
.Map(dest => dest.MaxStockLevel, src => src.MaxStockLevel)
.Map(dest => dest.LastRestockedAt, src => src.LastRestockedAt.HasValue ? Timestamp.FromDateTime(src.LastRestockedAt.Value.ToUniversalTime()) : null)
.Map(dest => dest.LastSoldAt, src => src.LastSoldAt.HasValue ? Timestamp.FromDateTime(src.LastSoldAt.Value.ToUniversalTime()) : null)
.Map(dest => dest.ProductTitle, src => src.Product != null ? src.Product.Title : (src.DiscountProduct != null ? src.DiscountProduct.Title : string.Empty))
.Map(dest => dest.ProductPrice, src => src.Product != null ? src.Product.Price : (src.DiscountProduct != null ? src.DiscountProduct.Price : 0))
.Map(dest => dest.Created, src => Timestamp.FromDateTime(src.Created.ToUniversalTime()));
// StockMovement Entity به StockMovementDto
config.NewConfig<StockMovement, StockMovementDto>()
.Map(dest => dest.Id, src => src.Id)
.Map(dest => dest.InventoryItemId, src => src.InventoryItemId)
.Map(dest => dest.MovementType, src => (ProtoStockMovementType)src.MovementType)
.Map(dest => dest.Quantity, src => src.Quantity)
.Map(dest => dest.QuantityBefore, src => src.QuantityBefore)
.Map(dest => dest.QuantityAfter, src => src.QuantityAfter)
.Map(dest => dest.Note, src => src.Note ?? string.Empty)
.Map(dest => dest.ReferenceNumber, src => src.ReferenceNumber ?? string.Empty)
.Map(dest => dest.OrderId, src => src.OrderId.HasValue ? new Int64Value { Value = src.OrderId.Value } : null)
.Map(dest => dest.DiscountOrderId, src => src.DiscountOrderId.HasValue ? new Int64Value { Value = src.DiscountOrderId.Value } : null)
.Map(dest => dest.PerformedByUserId, src => src.PerformedByUserId.HasValue ? new Int64Value { Value = src.PerformedByUserId.Value } : null)
.Map(dest => dest.Created, src => Timestamp.FromDateTime(src.Created.ToUniversalTime()))
.Map(dest => dest.ProductTitle, src => src.InventoryItem != null && src.InventoryItem.Product != null ? src.InventoryItem.Product.Title : (src.InventoryItem != null && src.InventoryItem.DiscountProduct != null ? src.InventoryItem.DiscountProduct.Title : string.Empty));
}
}