AutoMapper未使用SimpleInjector和WebApi2实例化IMappingEngine

本文关键字:实例化 IMappingEngine WebApi2 未使用 SimpleInjector AutoMapper | 更新日期: 2023-09-27 18:22:43

我开始在我的项目(WebApi2,框架4.5.1)中使用AutoMapper(Nuget的最新版本),并使用SimpleInjector(Nuget的最新版)。

我的问题是,我不知道如何配置SimpleInjector来通过构造函数将IMappingEngine注入到我的模型中。

现在我收到错误: 未映射的属性:映射引擎

我使用的是IMappingEngine接口。

我有一个包含所有Mapper.CreateMap<>的AutoMapperProfile类

AutoMapperConfig示例

public class WebApiAutomapperProfile : Profile
{
    /// <summary>
    /// The configure.
    /// </summary>
    protected override void Configure()
    {
        this.CreateMap<Entity, EntityModel>();
    }
}

模型接收IMMappingEngine的原因是,一些映射属性内部有其他映射。

Global.asax(方法Application_Start())中,我正在调用:

 GlobalConfiguration.Configure(WebApiConfig.Register);
 webApiContainer = new Container();
 webApiContainer.Options.DefaultScopedLifestyle = new WebApiRequestLifestyle();
 IocConfig.RegisterIoc(GlobalConfiguration.Configuration, webApiContainer);

IocConfig.cs

public static class IocConfig
{
    public static void RegisterIoc(HttpConfiguration config, Container container)
    {
        InstallDependencies(container);
        RegisterDependencyResolver(container);
    }
    private static void InstallDependencies(Container container)
    {
        new ServiceInstallerSimpleInjector().Install(container);
    }
    private static void RegisterDependencyResolver(Container container)
    {
        GlobalConfiguration.Configuration.DependencyResolver = new SimpleInjectorWebApiDependencyResolver(container);
    }

ServiceInstallerSimpleInjector

public class ServiceInstallerSimpleInjector : IServiceInstallerSimpleInjector
{
    // Automapper registrations
    container.Register(typeof(ITypeMapFactory), typeof(TypeMapFactory), Lifestyle.Scoped);
    container.RegisterCollection<IObjectMapper>(MapperRegistry.Mappers);
    var configurationRegistration = Lifestyle.Scoped.CreateRegistration<ConfigurationStore>(container);
    container.AddRegistration(typeof(IConfiguration), configurationRegistration);
    container.AddRegistration(typeof(IConfigurationProvider), configurationRegistration);
    // The initialization runs all the map creation once so it is then done when you come to do your mapping. 
    // You can create a map whenever you want, but this will slow your code down as the mapping creation involves reflection.
    Mapper.Initialize(config =>
    {
        config.ConstructServicesUsing(container.GetInstance);
        config.AddProfile(new WebApiAutomapperProfile());
        config.AddGlobalIgnore("Errors");
        config.AddGlobalIgnore("IsModelValid");
        config.AddGlobalIgnore("BaseValidator");
        config.AddGlobalIgnore("AuditInformation");
     });
     container.RegisterSingleton<IMappingEngine>(Mapper.Engine);
     Mapper.AssertConfigurationIsValid();
     container.RegisterWebApiControllers(GlobalConfiguration.Configuration);
     container.Verify();
}

然后,每个控制器在构造函数中接收一个IMappingEngine,并使用:

MappingEngine.Map<>

型号类示例

public class EntityModel : BaseModel.BaseModel<EntityModel >
{
    public EntityModel(IMappingEngine mappingEngine) : base(mappingEngine)
    {
    }
}

基本模型

public abstract class BaseModel<T> : IBaseModel
        where T : class
{
    public IMappingEngine MappingEngine { get; set; }
    protected BaseModel(IMappingEngine mappingEngine)
    {
        this.MappingEngine = mappingEngine;
    }
}

错误消息显示:

Type needs to have a constructor with 0 args or only optional args'r'nParameter name: type
Mapping types:
Entity -> EntityModel
Model.Entity -> WebApi.Models.EntityModel
Destination path:
EntityModel
Source value:
System.Data.Entity.DynamicProxies.Entity_1D417730D5BE3DEAF6292D57AB49B32FA18136A1DCF74193E8716EC6EE4DC62B

问题是IMappingEngine映射引擎没有注入到模型的构造函数中。问题是如何让它发挥作用。

当我尝试执行.Map时抛出错误

return this.MappingEngine.Map<Entity,EntityModel>(this.EntityRepository.AllMaterialized().FirstOrDefault());

这就是Stacktrace

   at WebApi.Controllers.Api.EntityController.Get() in c:'Users'Guillermo'Downloads'Backend'WebApi'Controllers'Api'EntityController.cs:line 108
   at lambda_method(Closure , Object , Object[] )
   at System.Web.Http.Controllers.ReflectedHttpActionDescriptor.ActionExecutor.<>c__DisplayClass10.<GetExecutor>b__9(Object instance, Object[] methodParameters)
   at System.Web.Http.Controllers.ReflectedHttpActionDescriptor.ActionExecutor.Execute(Object instance, Object[] arguments)
   at System.Web.Http.Controllers.ReflectedHttpActionDescriptor.ExecuteAsync(HttpControllerContext controllerContext, IDictionary`2 arguments, CancellationToken cancellationToken)

有什么遗漏或错误吗?

提前感谢!吉列尔莫。

AutoMapper未使用SimpleInjector和WebApi2实例化IMappingEngine

由于您的EntityController由Simple Injector正确解析,并且它取决于IMapperEngine,因此您可以放心地确保映射器引擎正确注入。可能发生的情况是,注册的Mapper.Engine在这一点上没有正确初始化,但我只是猜测。Automapper专家应该能够看到这里出了什么问题。

然而,问题的核心是您试图将依赖项注入到域实体中。看看Jimmy Bogard(Automapper的创建者)的这篇文章,他解释了为什么这是一个坏主意。

一旦在实体初始化期间停止要求服务依赖性,这个问题就会完全消失。