2012-05-07 7 views
3

私は現在、当社のAutofacをテスト中です。2つ以上のインプリントを持つインターフェイスを登録しないようにします。

は、我々は次のルールを持っているしたいと思います:インタフェースは一度しか実施されている

  1. 場合は、自動的にbuilder.RegisterAssemblyTypes(下記参照)を使用して、それを追加します。

  2. それ以外の場合は、どの実装が「デフォルト」実装であるかを決定するルールを手動で作成する必要があります。

私は次のコードを持っている:今

var builder = new ContainerBuilder(); 
builder.RegisterAssemblyTypes(Assembly 
    .Load("Lunch.Service")).As(t => t.GetInterfaces()[0]); 
builder.RegisterType<ConsoleLoggerService>() 
    .As<ILoggerService>().SingleInstance(); 
builder.RegisterModule(new DestinationModule()); 
builder.RegisterType<TransportationService>() 
    .As<ITransportationService>().PropertiesAutowired(); 

を、それが働いているが、それは最初の実装であるかを決定し、自動的にそれを作成します。これを手作業で行い、手動で「ルール」を作成しないとエラーがスローされます。これは可能ですか?

答えて

1

あなたはこのような何かを行うことができます:

cb.RegisterAssemblyTypes(assembly).Where(type => 
{ 
    var implementations = type.GetInterfaces(); 

    if (implementations.Length > 0) 
    { 
     var iface = implementations[0]; 

     var implementers = 
      from t in assembly.GetTypes() 
      where t.GetInterfaces().Contains(iface) 
      select t; 

     return implementers.Count() == 1; 
    } 

    return false; 
}) 
.As(t => t.GetInterfaces()[0]); 

は、これが唯一の実装が存在するすべての実装を登録し、それらを手動で登録することができますので、複数の実装とのインタフェースを無視します。私はこれが何らかの方法で効率的であると主張していないことに注意してください(例えば、サービスの数によっては、実装者のキャッシングを見たいかもしれません)。

+0

「これは効率的であるとは言いません。登録段階のパフォーマンスが問題になることはほとんどありませんでした。アセンブリ内のすべての型を反復処理するのは、通常はかなり高速です。このコードは、実行時のパフォーマンス(インスタンスの解決に要する時間)に悪影響を与えませんので、問題はありません。ありがとう。 – Steven

+0

ありがとうございます。私はこれをチェックします。ユースケースが理にかなっているかどうかわかります。基本的に、私たちは時には何が起こっているのか分からないほど多くの参考文献に問題があります。間違ったクラスが注入されたためです。だから、これは1つを持っているすべてのためにそれをデフォルトにし、複数の場合は、手動でケースを作成する必要があります。 – Cyfer13

+0

複数の実装者が見つかる正当な理由はありますか、それとも倍数を見つけようとしているのは本当にエラー状態でしょうか?実際にエラーが発生した場合や予期しない状況が発生した場合は、複数の実装が見つかった場合には、例外をスローするか、エラーを記録する必要があります(これは、展開された)?それとも、実際には複数の実装が利用可能で、設定に基づいて手動で選択する必要がありますか?後者の場合、これは合理的な使用例のようです。 –

関連する問題