gpt4 book ai didi

C# AutoMapper 映射多对多问题,外键错误

转载 作者:行者123 更新时间:2023-12-04 08:53:32 24 4
gpt4 key购买 nike

我遇到了将模型映射到具有多对多关系的实体的奇怪问题
我有以下实体和模型:

using System;
using System.Diagnostics;
using System.Collections.Generic;

namespace AutoMapper.ReproducedExample
{
public class StoreEntity
{
public int Id { get; set; }
public string Name { get; set; }
public List<StoreProductEntity> Products { get; set; } = new List<StoreProductEntity>();
}

public class ProductEntity
{
public int Id { get; set; }
public string Name { get; set; }
public List<StoreProductEntity> Stores { get; set; } = new List<StoreProductEntity>();
}

public class StoreProductEntity
{
public int StoreId { get; set; }
public StoreEntity Store { get; set; }
public int ProductId { get; set; }
public ProductEntity Product { get; set; }
}

public class StoreModel
{
public int Id { get; set; }
public string Name { get; set; }
public List<ProductModel> Products { get; set; } = new List<ProductModel>();
}

public class ProductModel
{
public int Id { get; set; }
public string Name { get; set; }
public List<StoreModel> Stores { get; set; } = new List<StoreModel>();
}

public class CustomProfile : Profile
{
public CustomProfile()
{
CreateMap<StoreModel, StoreEntity>()
.ForMember(d => d.Products,
opt => opt.MapFrom(s => s.Products))
.AfterMap((model, entity) =>
{
foreach (var entityProduct in entity.Products)
{
entityProduct.StoreId = entity.Id;
entityProduct.Store = entity;
}
});
CreateMap<StoreModel, StoreProductEntity>()
.ForMember(entity => entity.StoreId, opt => opt.MapFrom(model => model.Id))
.ForMember(entity => entity.Store, opt => opt.MapFrom(model => model))
.ForMember(entity => entity.ProductId, opt => opt.Ignore())
.ForMember(entity => entity.Product, opt => opt.Ignore());

CreateMap<ProductModel, ProductEntity>()
.ForMember(d => d.Stores,
opt => opt.MapFrom(s => s.Stores))
.AfterMap((model, entity) =>
{
foreach (var entityStore in entity.Stores)
{
entityStore.ProductId = entity.Id;
entityStore.Product = entity;
}
});
CreateMap<ProductModel, StoreProductEntity>()
.ForMember(entity => entity.StoreId, opt => opt.Ignore())
.ForMember(entity => entity.Store, opt => opt.Ignore())
.ForMember(entity => entity.ProductId, opt => opt.MapFrom(model => model.Id))
.ForMember(entity => entity.Product, opt => opt.MapFrom(model => model));

}
}

class Program
{
static void Main(string[] args)
{
var configuration = new MapperConfiguration(cfg =>
{
cfg.AddProfile<CustomProfile>();
});
#if DEBUG
configuration.AssertConfigurationIsValid();
#endif
var mapper = configuration.CreateMapper();
var store0 = new StoreModel()
{
Id = 1,
Name = "Store0",
};
var store1 = new StoreModel()
{
Id = 2,
Name = "Store1",
};
var product = new ProductModel()
{
Id = 1,
Name = "Product",
};
store1.Products.Add(product);
product.Stores.Add(store1);
store0.Products.Add(product);
product.Stores.Add(store0);

var store0Entity = mapper.Map<StoreEntity>(store0);
Debug.Assert(store0Entity.Products[0].Product.Stores[0].Store.Id ==
store0Entity.Products[0].Product.Stores[0].Store.Products[0].StoreId);
}
}
}
映射成功,但由于某种原因,某些深键没有映射到相关的 StoreEntity以下断言失败...
Debug.Assert(store0Entity.Products[0].Product.Stores[0].Store.Id ==
store0Entity.Products[0].Product.Stores[0].Store.Products[0].StoreId);
似乎由于某种原因深入 Store 类 AutoMapper 使用了错误的映射列表......但我不确定......

最佳答案

我已经想出了如何解决这个问题(感谢回答问题 Automapper creates 2 instances of one object )
为了检测 Circular references 我可以添加 .PreserveReferences() 方法进行映射
这是正确的 CustomProfile :

    public class CustomProfile : Profile
{
public CustomProfile()
{
CreateMap<StoreModel, StoreEntity>()
.ForMember(d => d.Products,
opt => opt.MapFrom(s => s.Products))
.AfterMap((model, entity) =>
{
foreach (var entityProduct in entity.Products)
{
entityProduct.StoreId = entity.Id;
entityProduct.Store = entity;
}
})
.PreserveReferences();
CreateMap<StoreModel, StoreProductEntity>()
.ForMember(entity => entity.StoreId, opt => opt.MapFrom(model => model.Id))
.ForMember(entity => entity.Store, opt => opt.MapFrom(model => model))
.ForMember(entity => entity.ProductId, opt => opt.Ignore())
.ForMember(entity => entity.Product, opt => opt.Ignore());

CreateMap<ProductModel, ProductEntity>()
.ForMember(d => d.Stores,
opt => opt.MapFrom(s => s.Stores))
.AfterMap((model, entity) =>
{
foreach (var entityStore in entity.Stores)
{
entityStore.ProductId = entity.Id;
entityStore.Product = entity;
}
})
.PreserveReferences();
CreateMap<ProductModel, StoreProductEntity>()
.ForMember(entity => entity.StoreId, opt => opt.Ignore())
.ForMember(entity => entity.Store, opt => opt.Ignore())
.ForMember(entity => entity.ProductId, opt => opt.MapFrom(model => model.Id))
.ForMember(entity => entity.Product, opt => opt.MapFrom(model => model));
}
}
但实际上我不知道这是否是一个问题,因为根据文档 AutoMapper 应该为 AutoMapper 版本 10.0.0 自动检测 Circular References 并且似乎这是一个问题

关于C# AutoMapper 映射多对多问题,外键错误,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/63973722/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com