使用AutoMapper展平嵌套对象的更好方法? [英] A better way to use AutoMapper to flatten nested objects?

查看:90
本文介绍了使用AutoMapper展平嵌套对象的更好方法?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我已经将域对象压平成DTO,如下例所示:

I have been flattening domain objects into DTOs as shown in the example below:

public class Root
{
    public string AParentProperty { get; set; }
    public Nested TheNestedClass { get; set; }
}

public class Nested
{
    public string ANestedProperty { get; set; }
}

public class Flattened
{
    public string AParentProperty { get; set; }
    public string ANestedProperty { get; set; }
}

// I put the equivalent of the following in a profile, configured at application start
// as suggested by others:

Mapper.CreateMap<Root, Flattened>()
      .ForMember
       (
          dest => dest.ANestedProperty
          , opt => opt.MapFrom(src => src.TheNestedClass.ANestedProperty)
       );

// This is in my controller:
Flattened myFlattened = Mapper.Map<Root, Flattened>(myRoot);

我看了很多示例,到目前为止,这似乎是扁平化嵌套层次结构的方法.但是,如果子对象具有许多属性,则此方法不会节省太多代码.

I have looked at a number of examples, and so far this seems to be the way to flatten a nested hierarchy. If the child object has a number of properties, however, this approach doesn't save much coding.

我找到了这个例子:

http://consultingblogs.emc.com /owainwragg/archive/2010/12/22/automapper-mapping-from-multiple-objects.aspx

,但是它需要Map()函数所需的映射对象的实例,据我所知,它无法与配置文件一起使用.

but it requires instances of the mapped objects, required by the Map() function, which won't work with a profile as I understand it.

我是AutoMapper的新手,所以我想知道是否有更好的方法可以做到这一点.

I am new to AutoMapper, so I would like to know if there is a better way to do this.

推荐答案

我更喜欢避免使用较早的Static方法,而是这样做.

I much prefer avoiding the older Static methods and do it like this.

将映射定义放入个人资料.我们先映射根,然后再应用嵌套的映射.请注意 Context 的使用.

Place our mapping definitions into a Profile. We map the Root first, and then apply the mappings of the Nested afterwards. Note the use of the Context.

public class MappingProfile : Profile
{
    public MappingProfile()
    {
        CreateMap<Root, Flattened>()
            .AfterMap((src, dest, context) => context.Mapper.Map(src.TheNestedClass, dest));
        CreateMap<Nested, Flattened>();
    }
}

同时定义从 Root Flattened Nested Flatterned 的映射的优点是您保留了完全控制属性的映射,例如目标属性名称是否不同或您要应用转换等.

The advantage of defining both the mapping from Root to Flattened and Nested to Flatterned is that you retain full control over the mapping of the properties, such as if the destination property name is different or you want to apply a transformation etc.

XUnit测试:

[Fact]
public void Mapping_root_to_flattened_should_include_nested_properties()
{
    // ARRANGE
    var myRoot = new Root
    {
        AParentProperty = "my AParentProperty",
        TheNestedClass = new Nested
        {
            ANestedProperty = "my ANestedProperty"
        }
    };

    // Manually create the mapper using the Profile
    var mapper = new MapperConfiguration(cfg => cfg.AddProfile(new MappingProfile())).CreateMapper();

    // ACT
    var myFlattened = mapper.Map<Root, Flattened>(myRoot);

    // ASSERT
    Assert.Equal(myRoot.AParentProperty, myFlattened.AParentProperty);
    Assert.Equal(myRoot.TheNestedClass.ANestedProperty, myFlattened.ANestedProperty);
}

通过从 AutoMapper.Extensions.Microsoft.DependencyInjection nuget程序包中添加AutoMapper的 serviceCollection.AddAutoMapper()到您的启动程序中,配置文件将被自动提取,并且您只需将 IMapper 注入到要应用映射的任何位置即可.

By adding AutoMapper's serviceCollection.AddAutoMapper() from the AutoMapper.Extensions.Microsoft.DependencyInjection nuget package to your start up, the Profile will be picked up automatically, and you can simply inject IMapper into wherever you are applying the mapping.

这篇关于使用AutoMapper展平嵌套对象的更好方法?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆