自动映射,映射配置不会持久化

时间:2016-05-24 14:32:37

标签: c# asp.net-mvc automapper

所以问题。

我添加了

AutoMapperConfig.Configure();

到global.asax中的application_Start

它运行代码

Mapper.Initialize(x =>
{
  x.AddProfile<DomainToViewModelMappingProfile>();
  x.AddProfile<ViewModelToDomainMappingProfile>();
});

Mapper.AssertConfigurationIsValid();

运行

public class DomainToViewModelMappingProfile : Profile
{
    protected override void Configure()
    {

        Mapper.CreateMap<DBO.User, ViewModels.UserViewModel>();
    }
}

public class ViewModelToDomainMappingProfile : Profile
{
    protected override void Configure()
    {
        Mapper.Initialize(cfg =>
        {
            cfg.CreateMap<ViewModels.UserViewModel, DBO.User>();
        });
    }
}

并且所有内容都可以编译并运行良好。

但在控制器中:

UserViewModel model = new UserViewModel();
User user = userService.GetUser(2);
model = Mapper.Map<User, UserViewModel>(user); //this line fails as mapping doesnt exist
return View();

但是如果我在控制器方法中添加映射配置

Mapper.CreateMap<ViewModels.UserViewModel,DBO.User>();
UserViewModel model = new UserViewModel();
User user = userService.GetUser(2);
model = Mapper.Map<User, UserViewModel>(user); //Works great
return View();

它工作正常。

忽略与automapper不同的语法。香港专业教育学院尝试了不赞成使用的新方法,但两者都失败了。

由于

3 个答案:

答案 0 :(得分:1)

问题是您在Initialize内调用Profile方法会导致覆盖已存在的映射:

public class ViewModelToDomainMappingProfile : Profile
{
    protected override void Configure()
    {
        // you should not to call Initialize method inside your profiles.
        Mapper.Initialize(cfg =>
        {
            cfg.CreateMap<ViewModels.UserViewModel, DBO.User>();
        });
    }
}

在这里,你有两种方式:

方式#1 (使用静态API - 已弃用)

public class DomainToViewModelMappingProfile : Profile
{
    protected override void Configure()
    {
        Mapper.CreateMap<DBO.User, ViewModels.UserViewModel>();
    }
}

public class ViewModelToDomainMappingProfile : Profile
{
    protected override void Configure()
    {
        Mapper.CreateMap<ViewModels.UserViewModel, DBO.User>();
    }
}

// initialize your mapper by provided profiles
Mapper.Initialize(x =>
{
  x.AddProfile<DomainToViewModelMappingProfile>();
  x.AddProfile<ViewModelToDomainMappingProfile>();
});

Mapper.AssertConfigurationIsValid();

方式#2 (使用实例API)

// in this case just call CreateMap from Profile class - its the same as CreateMap on `cfg`
public class DomainToViewModelMappingProfile : Profile
{
    public DomainToViewModelMappingProfile()
    {
        CreateMap<DBO.User, ViewModels.UserViewModel>();
    }
}

public class ViewModelToDomainMappingProfile : Profile
{
    public ViewModelToDomainMappingProfile()
    {
        CreateMap<ViewModels.UserViewModel, DBO.User>();
    }
}

// initialize you mapper config
var config = new MapperConfiguration(cfg => {
    cfg.AddProfile<DomainToViewModelMappingProfile>();
    cfg.AddProfile<ViewModelToDomainMappingProfile>();
});

// and then use it
var mapper = config.CreateMapper();
// or
var mapper = new Mapper(config);
var dest = mapper.Map<Source, Dest>(new Source());

在方式#2中,您需要在某处存储映射器配置(静态字段,DI),然后在控制器内使用它。我建议将Mapper实例注入您的控制器(例如使用一些DI容器)。

希望它会有所帮助。

答案 1 :(得分:0)

尝试覆盖&#34; ProfileName&#34; :

public class DomainToViewModelMappingProfile : Profile
{
 public override string ProfileName
    {
        get
        {
            return "DomainToViewModelMappingProfile";
        }
    }

protected override void Configure()
{

    Mapper.CreateMap<DBO.User, ViewModels.UserViewModel>();
}
}

答案 2 :(得分:0)

好的,感谢MaKCbIMKo指出我正确的方向

如上所述,我不必初始化,因为它已在automapperconfig中完成。

简介中的语法就是一次。

CreateMap<ViewModels.UserViewModel, DBO.User>();