diff --git a/modules/EasyAbp.EShop.Products/src/EasyAbp.EShop.Products.Application/EasyAbp/EShop/Products/ProductDetails/ProductDetailAppService.cs b/modules/EasyAbp.EShop.Products/src/EasyAbp.EShop.Products.Application/EasyAbp/EShop/Products/ProductDetails/ProductDetailAppService.cs index f4f8604a..47266633 100644 --- a/modules/EasyAbp.EShop.Products/src/EasyAbp.EShop.Products.Application/EasyAbp/EShop/Products/ProductDetails/ProductDetailAppService.cs +++ b/modules/EasyAbp.EShop.Products/src/EasyAbp.EShop.Products.Application/EasyAbp/EShop/Products/ProductDetails/ProductDetailAppService.cs @@ -83,7 +83,7 @@ namespace EasyAbp.EShop.Products.ProductDetails ProductsPermissions.Products.CrossStore); } - MapToEntity(input, detail); + await MapToEntityAsync(input, detail); await Repository.UpdateAsync(detail, autoSave: true); diff --git a/modules/EasyAbp.EShop.Products/src/EasyAbp.EShop.Products.Application/EasyAbp/EShop/Products/Products/ProductAppService.cs b/modules/EasyAbp.EShop.Products/src/EasyAbp.EShop.Products.Application/EasyAbp/EShop/Products/Products/ProductAppService.cs index 9cc63dd6..e5060506 100644 --- a/modules/EasyAbp.EShop.Products/src/EasyAbp.EShop.Products.Application/EasyAbp/EShop/Products/Products/ProductAppService.cs +++ b/modules/EasyAbp.EShop.Products/src/EasyAbp.EShop.Products.Application/EasyAbp/EShop/Products/Products/ProductAppService.cs @@ -70,16 +70,9 @@ namespace EasyAbp.EShop.Products.Products .ThenBy(x => x.Id); } - protected override Product MapToEntity(CreateUpdateProductDto createInput) - { - var product = base.MapToEntity(createInput); - - return product; - } - public override async Task CreateAsync(CreateUpdateProductDto input) { - var product = MapToEntity(input); + var product = await MapToEntityAsync(input); await CheckMultiStorePolicyAsync(product.StoreId, CreatePolicyName); @@ -117,7 +110,7 @@ namespace EasyAbp.EShop.Products.Products CheckProductIsNotStatic(product); - MapToEntity(input, product); + await MapToEntityAsync(input, product); await UpdateProductAttributesAsync(product, input); @@ -356,7 +349,7 @@ namespace EasyAbp.EShop.Products.Products UnitOfWorkManager.Current.OnCompleted(async () => { await ClearProductViewCacheAsync(product.StoreId); }); } - private static void CheckProductIsNotStatic(Product product) + protected virtual void CheckProductIsNotStatic(Product product) { if (product.IsStatic) { @@ -372,7 +365,7 @@ namespace EasyAbp.EShop.Products.Products CheckProductIsNotStatic(product); - var sku = ObjectMapper.Map(input); + var sku = await MapToProductSkuAsync(input); EntityHelper.TrySetId(sku, GuidGenerator.Create); @@ -388,7 +381,8 @@ namespace EasyAbp.EShop.Products.Products return dto; } - public async Task UpdateSkuAsync(Guid productId, Guid productSkuId, UpdateProductSkuDto input) + public virtual async Task UpdateSkuAsync(Guid productId, Guid productSkuId, + UpdateProductSkuDto input) { var product = await GetEntityByIdAsync(productId); @@ -398,7 +392,7 @@ namespace EasyAbp.EShop.Products.Products var sku = product.ProductSkus.Single(x => x.Id == productSkuId); - ObjectMapper.Map(input, sku); + await MapToProductSkuAsync(input, sku); await _productManager.UpdateSkuAsync(product, sku); @@ -412,7 +406,7 @@ namespace EasyAbp.EShop.Products.Products return dto; } - public async Task DeleteSkuAsync(Guid productId, Guid productSkuId) + public virtual async Task DeleteSkuAsync(Guid productId, Guid productSkuId) { var product = await GetEntityByIdAsync(productId); @@ -485,6 +479,80 @@ namespace EasyAbp.EShop.Products.Products return SortAttributesAndOptions(productDto); } + protected override Task MapToEntityAsync(CreateUpdateProductDto createInput) + { + return Task.FromResult(new Product( + GuidGenerator.Create(), + CurrentTenant.Id, + createInput.StoreId, + createInput.ProductGroupName, + createInput.ProductDetailId, + createInput.UniqueName, + createInput.DisplayName, + createInput.InventoryStrategy, + createInput.InventoryProviderName, + createInput.IsPublished, + false, + createInput.IsHidden, + createInput.PaymentExpireIn, + createInput.MediaResources, + createInput.DisplayOrder)); + } + + protected override Task MapToEntityAsync(CreateUpdateProductDto updateInput, Product entity) + { + entity.Update( + updateInput.StoreId, + updateInput.ProductGroupName, + updateInput.ProductDetailId, + updateInput.UniqueName, + updateInput.DisplayName, + updateInput.InventoryStrategy, + updateInput.InventoryProviderName, + updateInput.IsPublished, + false, + updateInput.IsHidden, + updateInput.PaymentExpireIn, + updateInput.MediaResources, + updateInput.DisplayOrder); + + return Task.CompletedTask; + } + + protected virtual async Task MapToProductSkuAsync(CreateProductSkuDto createInput) + { + return new ProductSku( + GuidGenerator.Create(), + await _attributeOptionIdsSerializer.SerializeAsync(createInput.AttributeOptionIds), + createInput.Name, + createInput.Currency, + createInput.OriginalPrice, + createInput.Price, + createInput.OrderMinQuantity, + createInput.OrderMaxQuantity, + createInput.PaymentExpireIn, + createInput.MediaResources, + createInput.ProductDetailId + ); + } + + protected virtual Task MapToProductSkuAsync(UpdateProductSkuDto updateInput, ProductSku entity) + { + entity.Update( + updateInput.Name, + updateInput.Currency, + updateInput.OriginalPrice, + updateInput.Price, + updateInput.OrderMinQuantity, + updateInput.OrderMaxQuantity, + updateInput.PaymentExpireIn, + updateInput.MediaResources, + updateInput.ProductDetailId + ); + + return Task.CompletedTask; + } + protected virtual ProductDto SortAttributesAndOptions(ProductDto productDto) { productDto.ProductAttributes = productDto.ProductAttributes.OrderBy(x => x.DisplayOrder).ToList(); diff --git a/modules/EasyAbp.EShop.Products/src/EasyAbp.EShop.Products.Application/EasyAbp/EShop/Products/ProductsApplicationAutoMapperProfile.cs b/modules/EasyAbp.EShop.Products/src/EasyAbp.EShop.Products.Application/EasyAbp/EShop/Products/ProductsApplicationAutoMapperProfile.cs index bfefd578..f575692b 100644 --- a/modules/EasyAbp.EShop.Products/src/EasyAbp.EShop.Products.Application/EasyAbp/EShop/Products/ProductsApplicationAutoMapperProfile.cs +++ b/modules/EasyAbp.EShop.Products/src/EasyAbp.EShop.Products.Application/EasyAbp/EShop/Products/ProductsApplicationAutoMapperProfile.cs @@ -41,23 +41,10 @@ namespace EasyAbp.EShop.Products .Ignore(dto => dto.Sold) .AfterMap(async (src, dest) => dest.AttributeOptionIds = (await attributeOptionIdsSerializer.DeserializeAsync(src.SerializedAttributeOptionIds)).ToList()); - CreateMap(MemberList.Source) - .ForSourceMember(dto => dto.StoreId, opt => opt.DoNotValidate()) - .ForSourceMember(dto => dto.CategoryIds, opt => opt.DoNotValidate()) - .Ignore(p => p.ProductAttributes) - .Ignore(p => p.ProductSkus) - .AfterMap((src, dest) => dest.InitializeNullCollections()); CreateMap(MemberList.Source) .ForSourceMember(dto => dto.StoreId, opt => opt.DoNotValidate()); CreateMap(MemberList.Source); CreateMap(MemberList.Source); - CreateMap(MemberList.Source) - .ForSourceMember(dto => dto.AttributeOptionIds, opt => opt.DoNotValidate()) - .Ignore(entity => entity.SerializedAttributeOptionIds) - .AfterMap(async (src, dest) => - dest.SetSerializedAttributeOptionIds( - await attributeOptionIdsSerializer.SerializeAsync(src.AttributeOptionIds))); - CreateMap(MemberList.Source); CreateMap(); CreateMap(); CreateMap(); diff --git a/modules/EasyAbp.EShop.Products/src/EasyAbp.EShop.Products.Domain/EasyAbp/EShop/Products/Products/Product.cs b/modules/EasyAbp.EShop.Products/src/EasyAbp.EShop.Products.Domain/EasyAbp/EShop/Products/Products/Product.cs index 1de5fec9..457c1a4a 100644 --- a/modules/EasyAbp.EShop.Products/src/EasyAbp.EShop.Products.Domain/EasyAbp/EShop/Products/Products/Product.cs +++ b/modules/EasyAbp.EShop.Products/src/EasyAbp.EShop.Products.Domain/EasyAbp/EShop/Products/Products/Product.cs @@ -2,6 +2,7 @@ using JetBrains.Annotations; using System; using System.Collections.Generic; using EasyAbp.EShop.Products.Options.ProductGroups; +using Volo.Abp; using Volo.Abp.Domain.Entities.Auditing; using Volo.Abp.MultiTenancy; @@ -13,13 +14,16 @@ namespace EasyAbp.EShop.Products.Products public virtual Guid StoreId { get; protected set; } - [NotNull] public virtual string ProductGroupName { get; protected set; } + [NotNull] + public virtual string ProductGroupName { get; protected set; } public virtual Guid? ProductDetailId { get; protected set; } - [CanBeNull] public virtual string UniqueName { get; protected set; } + [CanBeNull] + public virtual string UniqueName { get; protected set; } - [NotNull] public virtual string DisplayName { get; protected set; } + [NotNull] + public virtual string DisplayName { get; protected set; } public virtual InventoryStrategy InventoryStrategy { get; protected set; } @@ -29,7 +33,8 @@ namespace EasyAbp.EShop.Products.Products /// public virtual string InventoryProviderName { get; protected set; } - [CanBeNull] public virtual string MediaResources { get; protected set; } + [CanBeNull] + public virtual string MediaResources { get; protected set; } public virtual int DisplayOrder { get; protected set; } @@ -69,10 +74,10 @@ namespace EasyAbp.EShop.Products.Products { TenantId = tenantId; StoreId = storeId; - ProductGroupName = productGroupName; + ProductGroupName = Check.NotNullOrWhiteSpace(productGroupName, nameof(productGroupName)); ProductDetailId = productDetailId; UniqueName = uniqueName?.Trim(); - DisplayName = displayName; + DisplayName = Check.NotNullOrWhiteSpace(displayName, nameof(displayName)); InventoryStrategy = inventoryStrategy; InventoryProviderName = inventoryProviderName; IsPublished = isPublished; @@ -86,10 +91,34 @@ namespace EasyAbp.EShop.Products.Products ProductSkus = new List(); } - public void InitializeNullCollections() + public void Update( + Guid storeId, + [NotNull] string productGroupName, + Guid? productDetailId, + [CanBeNull] string uniqueName, + [NotNull] string displayName, + InventoryStrategy inventoryStrategy, + [CanBeNull] string inventoryProviderName, + bool isPublished, + bool isStatic, + bool isHidden, + TimeSpan? paymentExpireIn, + [CanBeNull] string mediaResources, + int displayOrder) { - ProductAttributes ??= new List(); - ProductSkus ??= new List(); + StoreId = storeId; + ProductGroupName = Check.NotNullOrWhiteSpace(productGroupName, nameof(productGroupName)); + ProductDetailId = productDetailId; + UniqueName = uniqueName?.Trim(); + DisplayName = Check.NotNullOrWhiteSpace(displayName, nameof(displayName)); + InventoryStrategy = inventoryStrategy; + InventoryProviderName = inventoryProviderName; + IsPublished = isPublished; + IsStatic = isStatic; + IsHidden = isHidden; + PaymentExpireIn = paymentExpireIn; + MediaResources = mediaResources; + DisplayOrder = displayOrder; } public void TrimUniqueName() diff --git a/modules/EasyAbp.EShop.Products/src/EasyAbp.EShop.Products.Domain/EasyAbp/EShop/Products/Products/ProductSku.cs b/modules/EasyAbp.EShop.Products/src/EasyAbp.EShop.Products.Domain/EasyAbp/EShop/Products/Products/ProductSku.cs index c8ab79a9..9f83221d 100644 --- a/modules/EasyAbp.EShop.Products/src/EasyAbp.EShop.Products.Domain/EasyAbp/EShop/Products/Products/ProductSku.cs +++ b/modules/EasyAbp.EShop.Products/src/EasyAbp.EShop.Products.Domain/EasyAbp/EShop/Products/Products/ProductSku.cs @@ -1,7 +1,7 @@ using System; -using System.Collections.Generic; using System.Text.Json.Serialization; using JetBrains.Annotations; +using Volo.Abp; using Volo.Abp.Data; using Volo.Abp.Domain.Entities.Auditing; @@ -11,28 +11,28 @@ namespace EasyAbp.EShop.Products.Products { [NotNull] public virtual string SerializedAttributeOptionIds { get; protected set; } - + [CanBeNull] public virtual string Name { get; protected set; } - + [NotNull] public virtual string Currency { get; protected set; } - + public virtual decimal? OriginalPrice { get; protected set; } - + public virtual decimal Price { get; protected set; } public virtual int OrderMinQuantity { get; protected set; } - + public virtual int OrderMaxQuantity { get; protected set; } - + public virtual TimeSpan? PaymentExpireIn { get; protected set; } [CanBeNull] public virtual string MediaResources { get; protected set; } public virtual Guid? ProductDetailId { get; protected set; } - + [JsonInclude] public virtual ExtraPropertyDictionary ExtraProperties { get; protected set; } @@ -41,7 +41,7 @@ namespace EasyAbp.EShop.Products.Products ExtraProperties = new ExtraPropertyDictionary(); this.SetDefaultsForExtraProperties(); } - + public ProductSku( Guid id, [NotNull] string serializedAttributeOptionIds, @@ -55,9 +55,10 @@ namespace EasyAbp.EShop.Products.Products [CanBeNull] string mediaResources, Guid? productDetailId) : base(id) { - SerializedAttributeOptionIds = serializedAttributeOptionIds; + SerializedAttributeOptionIds = + Check.NotNullOrWhiteSpace(serializedAttributeOptionIds, nameof(serializedAttributeOptionIds)); Name = name?.Trim(); - Currency = currency; + Currency = Check.NotNullOrWhiteSpace(currency, nameof(currency)); OriginalPrice = originalPrice; Price = price; OrderMinQuantity = orderMinQuantity; @@ -65,7 +66,7 @@ namespace EasyAbp.EShop.Products.Products PaymentExpireIn = paymentExpireIn; MediaResources = mediaResources; ProductDetailId = productDetailId; - + ExtraProperties = new ExtraPropertyDictionary(); this.SetDefaultsForExtraProperties(); } @@ -75,9 +76,26 @@ namespace EasyAbp.EShop.Products.Products Name = Name?.Trim(); } - public void SetSerializedAttributeOptionIds(string serializedAttributeOptionIds) + public void Update( + [CanBeNull] string name, + [NotNull] string currency, + decimal? originalPrice, + decimal price, + int orderMinQuantity, + int orderMaxQuantity, + TimeSpan? paymentExpireIn, + [CanBeNull] string mediaResources, + Guid? productDetailId) { - SerializedAttributeOptionIds = serializedAttributeOptionIds; + Name = name?.Trim(); + Currency = Check.NotNullOrWhiteSpace(currency, nameof(currency)); + OriginalPrice = originalPrice; + Price = price; + OrderMinQuantity = orderMinQuantity; + OrderMaxQuantity = orderMaxQuantity; + PaymentExpireIn = paymentExpireIn; + MediaResources = mediaResources; + ProductDetailId = productDetailId; } } } \ No newline at end of file diff --git a/modules/EasyAbp.EShop.Products/test/EasyAbp.EShop.Products.Domain.Tests/Products/ProductDomainTests.cs b/modules/EasyAbp.EShop.Products/test/EasyAbp.EShop.Products.Domain.Tests/Products/ProductDomainTests.cs index 1fe241aa..0d9aaae6 100644 --- a/modules/EasyAbp.EShop.Products/test/EasyAbp.EShop.Products.Domain.Tests/Products/ProductDomainTests.cs +++ b/modules/EasyAbp.EShop.Products/test/EasyAbp.EShop.Products.Domain.Tests/Products/ProductDomainTests.cs @@ -186,7 +186,7 @@ namespace EasyAbp.EShop.Products.Products await ProductManager.CreateAsync(product2); - var fakeSku = new ProductSku(Guid.NewGuid(), "", null, "", null, 0m, 1, 1, null, null, null); + var fakeSku = new ProductSku(Guid.NewGuid(), "[]", null, "USD", null, 0m, 1, 1, null, null, null); var inventoryDataModel = await ProductManager.GetInventoryDataAsync(product2, fakeSku); diff --git a/modules/EasyAbp.EShop.Stores/src/EasyAbp.EShop.Stores.Application.Shared/EasyAbp/EShop/Stores/Stores/MultiStoreAbstractKeyCrudAppService.cs b/modules/EasyAbp.EShop.Stores/src/EasyAbp.EShop.Stores.Application.Shared/EasyAbp/EShop/Stores/Stores/MultiStoreAbstractKeyCrudAppService.cs index a34c202c..0995f97e 100644 --- a/modules/EasyAbp.EShop.Stores/src/EasyAbp.EShop.Stores.Application.Shared/EasyAbp/EShop/Stores/Stores/MultiStoreAbstractKeyCrudAppService.cs +++ b/modules/EasyAbp.EShop.Stores/src/EasyAbp.EShop.Stores.Application.Shared/EasyAbp/EShop/Stores/Stores/MultiStoreAbstractKeyCrudAppService.cs @@ -82,7 +82,7 @@ namespace EasyAbp.EShop.Stores.Stores { await CheckMultiStorePolicyAsync(input.StoreId, CreatePolicyName); - var entity = MapToEntity(input); + var entity = await MapToEntityAsync(input); TryToSetTenantId(entity); @@ -96,7 +96,7 @@ namespace EasyAbp.EShop.Stores.Stores var entity = await GetEntityByIdAsync(id); await CheckMultiStorePolicyAsync(entity.StoreId, UpdatePolicyName); - MapToEntity(input, entity); + await MapToEntityAsync(input, entity); await Repository.UpdateAsync(entity, autoSave: true); return await MapToGetOutputDtoAsync(entity);