Structuremapを使用してタイプごとに内部依存関係を設定する

StackOverflow https://stackoverflow.com/questions/1628382

  •  06-07-2019
  •  | 
  •  

質問

構造マップの構成があり、頭を悩ましています。インターフェイス化された検証クラスを必要とするインターフェイス化されたui要素を必要とする具体的なクラスがあります。外側の具象クラスにデフォルトのui要素を取得させたいが、具象クラス固有の検証オブジェクトを取得させたい。このようなもの:

class MyView 
{
   IPrompt prompt
}

class GenericPrompt : IPrompt
{
   IValidator validator
}

class MyValidator : IValidator
{
   bool Validate() {}
}

MyViewの依存関係を作成するときにMyValidatorのみを使用するようにRegistry DSLでstructuremapを構成するにはどうすればよいですか。 (およびBobsViewの依存関係を作成するときにBobsValidatorを使用すると思われます)

役に立ちましたか?

解決

コンテナからMyView(およびBobsView)を取得していますか?すべてがIPromptのインスタンスを取ると想定できますか?

1つのアプローチは、ビューの名前と一致する名前ですべてのバリデーターを登録することです。 Validatorサフィックスを削除するだけの独自のタイプスキャナーを実装できます。

public class ValidatorScanner : ITypeScanner
{
    public void Process(Type type, PluginGraph graph)
    {
        if (!typeof (IValidator).IsAssignableFrom(type)) return;
        var validatorName = type.Name.Replace("Validator", "");
        graph.AddType(typeof(IValidator), type, validatorName);
    }
}

今、IPromptがその命名規則に従うビューによって常に要求されると仮定する場合、レジストリは次のようになります。

public class ValidatorRegistry : Registry
{
    public ValidatorRegistry()
    {
        Scan(scan =>
        {
            scan.TheCallingAssembly();
            scan.With<ValidatorScanner>();
        });

        ForRequestedType<IPrompt>().TheDefault.Is.ConstructedBy(ctx =>
        {
            var viewName = ctx.Root.RequestedType.Name.Replace("View", "");
            ctx.RegisterDefault(typeof(IValidator), ctx.GetInstance<IValidator>(viewName));
            return ctx.GetInstance<GenericPrompt>();
        });
    }
}

適切なバリデーターでビューを取得するには、具象型をリクエストする必要があります:

var view = container.GetInstance<MyView>();

これは&quot; Root.RequestedType&quot;に依存するため、コンテナ(サービスの場所)への直接呼び出しでビューを取得する場合にのみ機能することに注意してください。ビューの取得方法に応じて、BuildStackを上に移動して、ビューを探します(常にルートであると想定する代わりに)。

ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top