2016-07-20 9 views
5

私はAutoFacを使用して、現在のプリンシパルを必要なオブジェクトに挿入します。セキュリティチェックを実行するオブジェクト(AuthorizationValidator)があるとします。 AuthorizationValidatorが登録されている私のWebアプリケーションではAutoFac:NULL値を挿入

public AuthorizationValidator : IAuthorizationValidator 
{ 
    public AuthorizationValidator(IDataAccess dataAccess, IPrincipal principal) 
    { 
    // Save injected objects 
    ... 
    } 

    public bool CheckPermission(Guid objectId, Action action) 
    { 
    // Check if we are authorized at all 
    if (this.principal == null) 
     return false; 

    // Check the permission in the database 
    ... 
    } 
} 

と私は校長注入するには、以下の登録を使用します:それは次のようになり、アプリケーションの

builder.Register<IPrincipal>((c, p) => HttpContext.Current?.User); 

他のタイプが使用スレッドの元本または似たような。プリンシパルを必要とするオブジェクトはすべて、適切なプリンシパルを注入します。

許可なく呼び出しを行った場合、AutoFacは工場がnullを返したため、IPrincipalオブジェクトを提供できないという例外が発生します。この場合、空のプリンシパルは正常であり、例外は発生しません。

public AuthorizationValidator : IAuthorizationValidator 
{ 
    public AuthorizationValidator(IDataAccess dataAccess, IPrincipalFactory principalFactory) 
    { 
    // Save injected objects 
    _dataAccess = dataAccess; 
    _principal = principalFactory.GetCurrentPrincipal(); 
    } 

    public bool CheckPermission(Guid objectId, Action action) 
    { 
    // Same as previous example 
    ... 
    } 
} 

public interface IPrincipalFactory 
{ 
    IPrincipal GetCurrentPrincipal(); 
} 

を私はIPrincipalFactoryとして次のオブジェクトを登録しますASP.NETアプリケーションの場合:

+0

私はAutofacの内部を知ることはできませんが、これがうまくいく可能性があります: 'builder.Register ((c、p)=>(IPrincipal)HttpContext.Current?User);' –

+0

一般的IoCフレームワークでは意図的にヌルを注入することはできません。それは単なるオートファックのことではありません。 –

+0

私の答えで示唆したように、[Null Object Pattern](https://en.wikipedia.org/wiki/Null_Object_pattern)が選択肢になりますか? – fknx

答えて

5

Autofac documentationでは、このようなシナリオではNull Object patternを使用することをお勧めします。 NullPrincipalクラスを作成するには、IPrincipalインターフェイスから継承し、既定のインスタンスを提供するreadonlystaticフィールドを公開する専用コンストラクタを使用します。そして、あなたの代わりにヌルのこのインスタンスを返すことができます。もちろん

builder.Register<IPrincipal>((c, p) => HttpContext.Current?.User ?? NullPrincipal.Default); 

あなたは校長がnullの場合は、チェックしているあなたのコード内のすべての場所を更新し、それが代わりにNullPrincipal.Defaultに等しいかどうかを確認する必要があります。

1

この問題を解決するために、私はAutoFacを経由せずに現在のプリンシパルを取得することができIPrincipalFactoryインターフェースを作成しました

public class IAspNetPrincipalFactory : IPrincipalFactory 
{ 
    public IPrincipal GetCurrentPrincipal() => HttpContext.Current?.User; 
} 

これは機能しますが、私はこの解決策に完全に満足していません。