使用AutoMapper 11.0.0按命名约定反扁平化映射导致关联对象为空的问题
我之前也碰到过一模一样的问题——明明命名完全符合AutoMapper反扁平化的PascalCase约定,可嵌套对象就是没被自动实例化。其实问题的核心在于:AutoMapper默认不会自动为嵌套类型创建映射规则,哪怕你的属性命名完全匹配规则,它也不知道该怎么实例化Supplier.CreatedBy这个User对象。
为什么默认不生效?
你的CreatedById/CreatedByName确实完美对应CreatedBy.Id/CreatedBy.Name的反扁平化路径,但AutoMapper需要明确知道如何处理User类型的映射——要么你显式配置,要么允许它自动创建缺失的类型映射,否则它只会把CreatedBy留为null。
解决方案(两种可选)
方案1:开启自动创建缺失类型映射(推荐,符合你想要的自动映射需求)
只需要在MapperConfiguration中添加一行配置,让AutoMapper自动为需要的嵌套类型生成映射规则:
var configuration = new MapperConfiguration(cfg => { cfg.CreateMissingTypeMaps = true; // 关键配置 cfg.CreateMap<SupplierDto, Supplier>(); }); var mapper = new Mapper(configuration); var dto = new SupplierDto { Id = 1, Name = "Supplier One", CreatedById = 2, CreatedByName = "John Doe", CreatedAt = DateTime.Now, UpdatedAt = DateTime.Now, }; var supplier = mapper.Map<Supplier>(dto); Console.WriteLine(supplier?.CreatedBy?.Name); // 现在会输出 "John Doe"
方案2:显式配置嵌套对象的映射
如果你不想开启全局的自动类型映射,也可以手动指定CreatedBy的映射逻辑:
方式A:直接在Supplier映射中定义CreatedBy的映射
var configuration = new MapperConfiguration(cfg => { cfg.CreateMap<SupplierDto, Supplier>() .ForMember(dest => dest.CreatedBy, opt => opt.MapFrom(src => new User { Id = src.CreatedById, Name = src.CreatedByName })); });
方式B:单独创建SupplierDto到User的映射
var configuration = new MapperConfiguration(cfg => { // 先定义SupplierDto到User的映射规则 cfg.CreateMap<SupplierDto, User>() .ForMember(dest => dest.Id, opt => opt.MapFrom(src => src.CreatedById)) .ForMember(dest => dest.Name, opt => opt.MapFrom(src => src.CreatedByName)); // 之后Supplier的映射会自动复用上面的规则填充CreatedBy cfg.CreateMap<SupplierDto, Supplier>(); });
两种方案都能让supplier.CreatedBy被正确实例化,并且填充对应的Id和Name属性,完全符合你期望的映射结果。
内容的提问来源于stack exchange,提问作者Felipe Rugai
相关产品推荐
相关产品推荐

