简体   繁体   中英

Mapping properties from base class doesn't work using ExplicitExpansion

AutoMapper is not projecting query in EF when using ExplicitExpansion in a property that is defined in a base class. The following code shows the models:

/*********** Source Types ***********/
class EntityBase
{
    public Guid? CreatedById { get; set; }
    public Guid? ModifiedById { get; set; }
    [ForeignKey("CreatedById")]
    public User CreatedBy { get; set; }
    [ForeignKey("ModifiedById")]
    public User ModifiedBy { get; set; }
}

class User
{
    [Key]
    public Guid Id { get; set; }
    public string Name { get; set; }
}

class Script : EntityBase
{
    [Key]
    public Guid Id { get; set; }
    public string Text { get; set; }
}


/*********** Destination Types ***********/
class EntityBaseModel
{
    public Guid? CreatedById { get; set; }
    public Guid? ModifiedById { get; set; }
    public UserModel CreatedBy { get; set; }
    public UserModel ModifiedBy { get; set; }
}

class UserModel
{
    public Guid Id { get; set; }
    public string Name { get; set; }
}

class ScriptModel : EntityBaseModel
{
    public Guid Id { get; set; }
    public string Text { get; set; }
    public new UserModel ModifiedBy { get; set; } //notice the 'new' here? this will work
}

I'm using the following mapping configuration:

 Mapper.Initialize(cfg =>
        {
            cfg.CreateMap<Script, ScriptModel>()
            .MaxDepth(1)
            .ForMember(d => d.ModifiedBy, o => o.ExplicitExpansion())
            .ForMember(d => d.CreatedBy, o => o.ExplicitExpansion());
        });

The following test will fail, but it shouldn't... it should fetch the CreatedBy property because I've explicitly said so:

/// <summary>
    /// This will fail, but it shouldn't.
    /// </summary>
    [TestMethod]
    public void Should_Map_CreatedBy()
    {
        using (var context = new MyContext())
        {
            var model = context.Scripts.Include("CreatedBy").ProjectTo<ScriptModel>(null, "CreatedBy").FirstOrDefault();
            Assert.IsNotNull(model);
            Assert.IsNotNull(model.CreatedBy);
        }
    }

I've also tried these configurations, but it doesn't work either

Mapper.Initialize(cfg =>
        {
            cfg.CreateMap<EntityBase, EntityBaseModel>();
            cfg.CreateMap<User, UserModel>();
            cfg.CreateMap<Script, ScriptModel>()
            .MaxDepth(1)
            .ForMember(d => d.ModifiedBy, o => o.ExplicitExpansion())
            .ForMember(d => d.CreatedBy, o => o.ExplicitExpansion());
        });
Mapper.Initialize(cfg =>
        {
            cfg.CreateMap<EntityBase, EntityBaseModel>();
            cfg.CreateMap<User, UserModel>();
            cfg.CreateMap<Script, ScriptModel>()
            .IncludeBase<EntityBase, EntityBaseModel>()
            .MaxDepth(1)
            .ForMember(d => d.ModifiedBy, o => o.ExplicitExpansion())
            .ForMember(d => d.CreatedBy, o => o.ExplicitExpansion());
        });

Is there something wrong with my mapping configuration? Is that an automapper bug?

Here's the full repro: https://1drv.ms/u/s!AhH0QYI81F61gtIx0q27BZ05EM-xQA

    cfg.CreateMap<User, UserModel>();
    cfg.CreateMap<Script, ScriptModel>()
        .ForMember(d => d.ModifiedBy, o => o.ExplicitExpansion())
        .ForMember(d => d.CreatedBy, o => o.ExplicitExpansion());

    var model = context.Scripts.ProjectTo<ScriptModel>(s=>s.CreatedBy).FirstOrDefault()

This works for me with the latest version.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM