15

私が見つけたAutomapperの例のほとんどは、タイプ マッピングの管理に静的な Mapper オブジェクトを使用しています。私のプロジェクトでは、StructureMap を使用してオブジェクト構築の一部として IMapperEngine を挿入する必要があります。これにより、単体テストでマッパーをモックできるため、静的マッパーを使用できなくなります。AutoMapper プロファイルの構成もサポートする必要があります。

私の質問は、MyService のインスタンスが構築されたときに IMappingEngine のインスタンスを提供できるように、StructureMap レジストリを構成する方法です。

Service コンストラクターのシグネチャは次のとおりです。

public MyService(IMappingEngine mapper, IMyRepository myRepository, ILogger logger)

そして、ここに StructureMap レジストリがあります

public class MyRegistry : StructureMap.Configuration.DSL.Registry
{
    public MyRegistry()
    {
        For<IMyRepository>().Use<MyRepository>();
        For<ILogger>().Use<Logger>();
        //what to do for IMappingEngine?
    }
}

そして、ロードしたいプロファイル

public class MyAutoMapperProfile : AutoMapper.Profile
{
    protected override void Configure()
    {
        this.CreateMap<MyModel, MyDTO>();
    }
}
4

4 に答える 4

14

クラスにはMapperstatic プロパティがありますMapper.Engine。これを使用して、エンジンをコンテナーに登録します。

For<IMappingEngine>().Use(() => Mapper.Engine);

エンジンを挿入する前にプロファイルをロードする必要がある場合は、その構成コードを上記のスニペットと一緒に挿入します。


アップデート

カスタム レジストリは次のようになります。

class MyRegistry : Registry
{
  public MyRegistry()
  {
    For<IMyRepository>().Use<MyRepository>();
    For<ILogger>().Use<Logger>();

    Mapper.AddProfile(new AutoMapperProfile());
    For<IMappingEngine>().Use(() => Mapper.Engine);
  }
}

このコードはブートストラップで一度実行され、タイプの依存関係はその後、カスタムを使用して構成されIMappingEngineた静的プロパティの値で提供されます。Mapper.EngineAutoMapperProfile

于 2012-09-26T15:34:13.043 に答える
7

静的 API はバージョン 5.0 で削除されます。MapperConfiguration インスタンスを使用し、必要に応じて静的に保存します。CreateMapper を使用してマッパー インスタンスを作成します。

新しいバージョン (4.2.0 >=)では、DI を介してIMapperを保持して渡す必要があります。

シンプルな構成サービスは次のようになります (ASP.NET Core)

services.AddSingleton<IMapper>(_ => new MapperConfiguration(cfg =>
            {
                cfg.CreateMap<Foo,Bar>();
            })
            .CreateMapper());

そして私たちのサービスレイヤー(コンストラクターインジェクションの助けを借りて):

public class CrudService<TDocument> : ICrudService<TDocument>
    {
        private readonly IMapper _internalMapper;
        private readonly IRepository<TDocument> _repository;

        public CrudService(IRepository<TDocument> repository, IMapper mapper)                
        {
            _internalMapper = mapper;
            _repository = repository;
        }

        public virtual ServiceResult<string> Create<TModel>(TModel foo)
        {
            var bar = _internalMapper.Map<TDocument>(foo);

            try
            {
                _repository.Create(bar);
            }
            catch (Exception ex)
            {
                return ServiceResult<string>.Exception(ex);
            }

            return ServiceResult<string>.Okay(entity.Id);
        }
}

consider TDocument as Bar, and TModel as Foo


更新:
AutoMapper 4.2.1 がリリースされました – Static が復活しました

少しのフィードバックと魂の検索、そして正直なところ質問への対処にうんざりした後、静的 API の一部がこのリリースで復元されました。現在 (そして将来的に) Mapper.Initialize と Mapper.Map を使用できます。

于 2016-02-16T11:16:39.883 に答える
1

StructureMap をセットアップした AutoMapper を紹介するブログ記事を書きました。AutoMapper 3.1.0 (3.1.1 でも動作)、3.0.0、および 2.2.1 用の特定のレジストリを作成しました。

http://www.martijnburgers.net/post/2013/12/20/My-AutoMapper-setup-for-StructureMap.aspx

于 2014-02-06T23:11:53.567 に答える
1

Mapper.Engine で構成を設定し、それを For().Use に渡す方法がわからなかったので、最終的には次のようになりました。

public MyRegistry()
{
    For<IMyRepository>().Use<MyRepository>();
    For<ILogger>().Use<Logger>();

    //type mapping
    For<ConfigurationStore>()
        .Singleton()
        .Use(ctx =>
        {
            ITypeMapFactory factory = ctx.GetInstance<ITypeMapFactory>();
            ConfigurationStore store 
                = new ConfigurationStore(factory, MapperRegistry.AllMappers());
            IConfiguration cfg = store;
            cfg.AddProfile<MyAutoMapperProfile>();
            store.AssertConfigurationIsValid();
            return store;
        });
    For<IConfigurationProvider>().Use(ctx => ctx.GetInstance<ConfigurationStore>());
    For<IConfiguration>().Use(ctx => ctx.GetInstance<ConfigurationStore>());
    For<IMappingEngine>().Singleton().Use<MappingEngine>();
    For<ITypeMapFactory>().Use<TypeMapFactory>();
}
于 2012-09-26T18:10:55.377 に答える