当我想使用 UseDestinationValue
方法的行为时如何配置 AutoMapper 映射,但仅当目标属性不是 null
时。
类似的东西:
Mapper.CreateMap<Item, ItemViewModel>()
.ForMember(x => x.Details, _ => _.UseDestinationValue(dontUseWhenNullDestination: true))
编辑
class ItemDetails {
public string Info { get; set; }
public string ImportantData { get; set; } // only in Domain, not in ViewModel
}
class Item {
public ItemDetails Details { get; set; }
}
class ItemDetailsViewModel {
public string Info { get; set; }
}
class ItemViewModel {
public ItemDetailsViewModel Details { get; set; }
}
现在是用法示例。我有一个 ItemViewModel
类,我想将它映射到 Item
类。
映射配置:
Mapper.CreateMap<Item, ItemViewModel>()
.ForMember(x => x.Details, _ => _.UseDestinationValue())
第一种情况 - 目标属性
Item.Details
属性不是 NULL。现在我希望 AutoMapper 使用Details
属性的目标实例,因为它不为空。逻辑是这样的:
var item = new Item { Details = new Details { Info = "Old text", ImportantData = "Data" } }; var itemViewModel = new ItemViewModel { Details = new DetailsViewModel { Info = "New text" } }; Mapper.Map(itemViewModel, item);
AutoMapper,由于
UseDestinationValue
的存在,将保留item.Details
实例并仅设置item.Details.Info
属性。第二种情况 - 目标属性
Item.Details
属性为 NULL。现在我希望 AutoMapper 不要使用 这个空实例,而是创建一个新实例。问题是如何配置映射以考虑这种情况?逻辑是这样的:
var item = new Item { Details = null }; var itemViewModel = new ItemViewModel { Details = new DetailsViewModel { Info = "New text" } }; Mapper.Map(itemViewModel, item);
问题
这里我遇到了一个问题,因为在映射之后,
item.Details
属性将为 null(因为UseDestinationValue
的使用是null
在这种情况下)。
原因
NHibernate 从数据库中获取实体后,将其放入代理中。所以加载对象的 Details
属性不是类型:ItemDetails
,而是 ItemDetailsNHibernateProxy
- 所以我必须使用这种类型,当我想要稍后将此现有对象保存到数据库中。但如果此属性为 null
,则我不能使用 null 目标值,因此 Automapper 应该创建一个新实例。
谢谢, 克里斯
最佳答案
有同样的问题,但使用 EF。 Cryss 关于使用 BeforeMap 的评论为我指明了正确的方向。
我最终得到的代码类似于:
在 Configure() 方法中:
Mapper.CreateMap<ItemViewModel, Item>()
.AfterMap((s, d) => { MapDetailsAction(s, d); })
.ForMember(dest => dest.Details, opt => opt.UseDestinationValue());
然后是 Action :
Action<ItemViewModel, Item> MapDetailsAction = (source, destination) =>
{
if (destination.Details == null)
{
destination.Details = new Details();
destination.Details =
Mapper.Map<ItemViewModel, Item>(
source.Details, destination.Details);
}
};
关于c# - 仅当目标属性不为 null 时才使用 DestinationValue,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12262940/