その1では、TransparentPolicyInjectorを使ってアノテーションベースで処理をインジェクションしてた。
この方法だと、100クラスあると100個属性つけてコンテナ側でも100個TransparentPolicyInjectorを設定しないといけない。
これは、とても使う気になれない!と思って調べてみると、楽する方法があった。
 MatchingRuleとPolicyDefinitionというものでいけそう。MatchingRuleで、対象にするクラスのルールを作って、PolicyDefinitionでルールに該当するクラスに何の処理を差し込むか決めれる。
早速実験だ。
 UnityEdication2という名前でプロジェクトを作って、前回作ったIGreeterとPersonとLoggingHandlerをコピーする。名前空間はUnityEducationの部分をUnityEducation2に変更しておく。
 とりあえずさくっと作る。
  
class Program
{
    static void Main(string[] args)
    {
        IUnityContainer c = new UnityContainer();
        // Interceptionの拡張を追加
        c.AddNewExtension<Interception>();
        // コンテナにマッチングルールを登録する
        c.RegisterInstance<NamespaceMatchingRule>(
            "test",
            new NamespaceMatchingRule("UnityEducation2.Entities"));
        // Interceptionの設定
        c.Configure<Interception>().
            // IGreeterにはTransparentProxyInterceptorを使う
            SetInterceptorFor<IGreeter>(new TransparentProxyInterceptor()).
            // UnityEducation2.Entities名前空間のクラスに
            // LoggingHandlerを適用するポリシーを作成
            AddPolicy("EntitiesLoggingPolicy").
                AddMatchingRule<NamespaceMatchingRule>("test").
                AddCallHandler<LoggingHandler>();
        // インスタンスをコンテナに登録
        c.RegisterInstance<IGreeter>(new Person { Name = "大田" });
        // インスタンスをコンテナから取得して挨拶文を表示
        var ohta = c.Resolve<IGreeter>();
        Console.WriteLine(ohta.Greet());
    }
}
21行目のAddPolicyから3行がポイント。これをすることで、Personクラスへのアノテーションが不要になる。
クラスの数が増えてくると、ぐぐっと楽さ加減が変わってくるかな。
でも残念なのが、SetInterceptorForメソッドは、インターフェース単位でしか指定できない。これは100個あったら100行書けってことなのかな???
とりあえずIBaseみたいなマーカーインターフェースを作って、そいつを必ず実装すること!みたいなルールで実装するようにしてSetInterceptorFor<IBase>(new TransparentProxyInterceptor())をするのが楽なのかな。
好みのやり方ではないけど…
悩ましい。