I created a domain entity and all set methods are private because they have some validations before setting the data.
So I have Dtos to exchange data and than I map it to the Entity so I could persist to the database if everything goes fine.
When mapping Dto to Entity I'm getting the Entity with all the properties filled but the SetXXX are not executed as it would happen if I called the constructor directly.
What is the best or correct approach for those cases when using AutoMapper?
Domain Entity
public Product(Guid id, ... decimal originalPrice, decimal discountedPrice...) :
base(id)
{
OriginalPrice = CheckOriginalPrice(originalPrice, discountedPrice);
DiscountedPrice = CheckDiscountedPrice(originalPrice, discountedPrice);
}
public virtual void SetOriginalPrice(decimal originalPrice, decimal discountedPrice)
{
OriginalPrice = CheckOriginalPrice(originalPrice, discountedPrice);
}
private static decimal CheckOriginalPrice(decimal originalPrice, decimal discountedPrice)
{
if (originalPrice < 0)
throw new ArgumentOutOfRangeException($"original price ({originalPrice} cannot be negative");
else if (originalPrice < discountedPrice)
throw new ArgumentOutOfRangeException($"original price ({originalPrice}) can not be lower than discounted price ({discountedPrice})!");
return originalPrice;
}
Map will succeed if I do this, so no validation is happening, how to trigger the constructor?
var product = _objectMapper.Map<CreateProductDto, Product>(product);
If I test the entity class directly it pass the test as the price is checked and I get the exception.
var exception = await Assert.ThrowsAsync<ArgumentOutOfRangeException>(async () =>
{
//Act
var product =
new Product(
_guidGenerator.Create(),
...
4.05m,
8.05m,
...
);
});
//Assert
exception.Message.ShouldContain("original price");
So, how can I achieve that when mapping using ObjetMapper.Map the constructor will get executed properly, is there an easy way to accomplish it?