C# 如何从平面图元映射到多个DTO?
我希望使用C#.NET核心中的AutoMapper将已经扁平化的实体映射到嵌套的DTO集合。此外,DTO具有一对多关系,扁平实体隐藏在结构中。例如:C# 如何从平面图元映射到多个DTO?,c#,asp.net-core,automapper,C#,Asp.net Core,Automapper,我希望使用C#.NET核心中的AutoMapper将已经扁平化的实体映射到嵌套的DTO集合。此外,DTO具有一对多关系,扁平实体隐藏在结构中。例如: public class Product { public int Id { get; set; } public string Name { get; set; } public int Price { get; set; } public int Weight { get; set; } } public cl
public class Product
{
public int Id { get; set; }
public string Name { get; set; }
public int Price { get; set; }
public int Weight { get; set; }
}
public class ProductDto
{
public string Name { get; set; }
public IEnumerable<PriceDto> Prices { get; set; }
}
public class PriceDto
{
public int Price { get; set; }
public int Weight { get; set; }
}
我将定义两个域配置文件。 一个用于产品到产品的转换
CreateMap<Product, ProductDto>()
.ForMember(x => x.Id , opts => opts.Ignore())
.ForMember(x => x.Price , opts => opts.Ignore())
.ForMember(x => x.Weight , opts => opts.Ignore())
.ForMember(x => x.Name , opts => opts.MapFrom(y => y.Name));
CreateMap()
.ForMember(x=>x.Id,opts=>opts.Ignore())
.ForMember(x=>x.Price,opts=>opts.Ignore())
.ForMember(x=>x.Weight,opts=>opts.Ignore())
.ForMember(x=>x.Name,opts=>opts.MapFrom(y=>y.Name));
还有一个是产品定价
CreateMap<Product, ProductDto>()
.ForMember(x => x.Id , opts => opts.Ignore())
.ForMember(x => x.Name , opts => opts.Ignore())
.ForMember(x => x.Price , opts => opts.MapFrom(y => y.Price ))
.ForMember(x => x.Weight , opts => opts.MapFrom(y => y.Weight ));
CreateMap()
.ForMember(x=>x.Id,opts=>opts.Ignore())
.ForMember(x=>x.Name,opts=>opts.Ignore())
.ForMember(x=>x.Price,opts=>opts.MapFrom(y=>y.Price))
.ForMember(x=>x.Weight,opts=>opts.MapFrom(y=>y.Weight));
然后一次从同一个源映射到两个不同的目标。您需要实现自己的转换器,如下所示:
ProductsConverter
public class ProductsConverter : ITypeConverter<List<Product>, List<ProductDto>>
{
public List<ProductDto> Convert(List<Product> source, List<ProductDto> destination, ResolutionContext context)
{
return source.GroupBy(p => p.Name)
.Select(r => new ProductDto
{
Name = r.Key,
Prices = source.Where(pp => pp.Name == r.Key)
.Select(rr => new PriceDto
{
Price = rr.Price,
Weight = rr.Weight
})
}).ToList();
}
}
public class ModelProfile: Profile
{
public ModelProfile()
{
CreateMap<List<Product>, List<ProductDto>>()
.ConvertUsing<ProductsConverter>();
}
}
public IActionResult Index()
{
List<Product> products= new List<Product>() {
new Product{ Id = 1, Name = "foo", Price = 8, Weight = 12},
new Product{ Id = 2, Name = "foo", Price = 12, Weight = 18},
new Product{ Id = 3, Name = "bar", Price = 3, Weight = 1},
new Product{ Id = 4, Name = "bar", Price = 6, Weight = 2},
};
var result = _mapper.Map<List<ProductDto>>(products);
return Ok(result);
}
public IActionResult Index()
{
列表产品=新列表(){
新产品{Id=1,Name=“foo”,价格=8,重量=12},
新产品{Id=2,Name=“foo”,价格=12,重量=18},
新产品{Id=3,Name=“bar”,价格=3,重量=1},
新产品{Id=4,Name=“bar”,价格=6,重量=2},
};
var result=_mapper.Map(产品);
返回Ok(结果);
}
你的真实数据是什么?产品会有很多价格吗?与我们分享使用AutoMapper转换实体的代码。你好@TaoZhou是的,ProductDto将有许多PriceDto。我还没有关于CreateMap()设置的任何代码,因为这就是我目前正在研究的。我将用一组扁平化实体的示例更新帖子如果ProductDto和PriceDto之间分别存在一对多关系,该方法是否有效?如果将product映射到ProductDto,然后初始化ProductDto。Prices使用一个包含单个元素的列表将product映射到PriceDto,则该方法应该有效。它不会是全自动的,但据我所知它会工作的
public IActionResult Index()
{
List<Product> products= new List<Product>() {
new Product{ Id = 1, Name = "foo", Price = 8, Weight = 12},
new Product{ Id = 2, Name = "foo", Price = 12, Weight = 18},
new Product{ Id = 3, Name = "bar", Price = 3, Weight = 1},
new Product{ Id = 4, Name = "bar", Price = 6, Weight = 2},
};
var result = _mapper.Map<List<ProductDto>>(products);
return Ok(result);
}