AutoMapper 在源 属性 条件下将目标设置为空
AutoMapper set destination to null on condition of source property
我在两个对象之间进行映射,根据源的条件,我希望目标为空。
例如,这里是 类:
public class Foo
{
public int Code { get; set; }
public string Name { get; set; }
}
public class Bar
{
public string Name { get; set; }
public string Type { get; set; }
}
还有我的地图:
Mapper.CreateMap<Foo, Bar>()
.AfterMap((s, d) => { if (s.Code != 0) d = null; });
但是好像忽略了AfterMap。尽管具有所有默认属性,但 Bar 已初始化。
如何根据代码不等于 0 将映射器设为 return null?
谢谢
一种可能的方法是-
class Converter : TypeConverter<Foo, Bar>
{
protected override Bar ConvertCore(Foo source)
{
if (source.Code != 0)
return null;
return new Bar();
}
}
static void Main(string[] args)
{
Mapper.CreateMap<Foo, Bar>()
.ConvertUsing<Converter>();
var bar = Mapper.Map<Bar>(new Foo
{
Code = 1
});
//bar == null true
}
我创建了以下扩展方法来解决这个问题。
public static IMappingExpression<TSource, TDestination> PreCondition<TSource, TDestination>(
this IMappingExpression<TSource, TDestination> mapping
, Func<TSource, bool> condition
)
where TDestination : new()
{
// This will configure the mapping to return null if the source object condition fails
mapping.ConstructUsing(
src => condition(src)
? new TDestination()
: default(TDestination)
);
// This will configure the mapping to ignore all member mappings to the null destination object
mapping.ForAllMembers(opt => opt.PreCondition(condition));
return mapping;
}
对于题例,可以这样使用:
Mapper.CreateMap<Foo, Bar>()
.PreCondition(src => src.Code == 0);
现在,如果条件失败,映射器将 return null;否则,它将 return 映射对象。
我更喜欢自定义值解析器。这是我的看法...
public class CustomValueResolver : IValueResolver<Foo, Bar, string>
{
public string Resolve(Foo source, Bar destination, string destMember, ResolutionContext context)
{
return source.Code != 0 ? null : "asd";
}
}
public class YourProfile : Profile
{
public YourProfile()
{
this.CreateMap<Foo, Bar>()
.ForMember(dst => dst.Name, opt => opt.MapFrom<CustomValueResolver>())
// ...
;
}
}
我在两个对象之间进行映射,根据源的条件,我希望目标为空。
例如,这里是 类:
public class Foo
{
public int Code { get; set; }
public string Name { get; set; }
}
public class Bar
{
public string Name { get; set; }
public string Type { get; set; }
}
还有我的地图:
Mapper.CreateMap<Foo, Bar>()
.AfterMap((s, d) => { if (s.Code != 0) d = null; });
但是好像忽略了AfterMap。尽管具有所有默认属性,但 Bar 已初始化。
如何根据代码不等于 0 将映射器设为 return null?
谢谢
一种可能的方法是-
class Converter : TypeConverter<Foo, Bar>
{
protected override Bar ConvertCore(Foo source)
{
if (source.Code != 0)
return null;
return new Bar();
}
}
static void Main(string[] args)
{
Mapper.CreateMap<Foo, Bar>()
.ConvertUsing<Converter>();
var bar = Mapper.Map<Bar>(new Foo
{
Code = 1
});
//bar == null true
}
我创建了以下扩展方法来解决这个问题。
public static IMappingExpression<TSource, TDestination> PreCondition<TSource, TDestination>(
this IMappingExpression<TSource, TDestination> mapping
, Func<TSource, bool> condition
)
where TDestination : new()
{
// This will configure the mapping to return null if the source object condition fails
mapping.ConstructUsing(
src => condition(src)
? new TDestination()
: default(TDestination)
);
// This will configure the mapping to ignore all member mappings to the null destination object
mapping.ForAllMembers(opt => opt.PreCondition(condition));
return mapping;
}
对于题例,可以这样使用:
Mapper.CreateMap<Foo, Bar>()
.PreCondition(src => src.Code == 0);
现在,如果条件失败,映射器将 return null;否则,它将 return 映射对象。
我更喜欢自定义值解析器。这是我的看法...
public class CustomValueResolver : IValueResolver<Foo, Bar, string>
{
public string Resolve(Foo source, Bar destination, string destMember, ResolutionContext context)
{
return source.Code != 0 ? null : "asd";
}
}
public class YourProfile : Profile
{
public YourProfile()
{
this.CreateMap<Foo, Bar>()
.ForMember(dst => dst.Name, opt => opt.MapFrom<CustomValueResolver>())
// ...
;
}
}