2011-01-05 94 views
0

我想知道是否有人知道是否可以通過Unity注入正在使用的方法上的Attribute類?Unity - 注入屬性類

更確切地說,我工作的項目是一個MVC2 ASP.NET類型,其中控制器實例通過Unity注入。所有依賴關係(例如數據庫上下文)均在Unity配置文件中配置。

我的問題是,我如何注入自定義的Attribute類,它也使用數據庫上下文,即它有一個依賴?

這裏的控制器類的抽象:

public class MyController : Controller 
    { 
     public IDBContext MyDBContext { get; set; } 
... 

    [CustomAuthorize] 
    public ActionResult Index() 
    { 
... 

    public class CustomAuthorize : AuthorizeAttribute 
    { 
     public IDBContext2 MyDBContext2 { get; set; } 
... 

預先感謝幫助。

N.

回答

0

這不是完全不可能的,但它是非常困難的。

問題是屬性對象本身是由CLR創建的(特別是反射API,如果我理解正確),所以沒有辦法在那裏獲取容器來調用構造函數。而當你創建屬性實例時,你無法真正控制,所以你甚至不能保證你的容器是否能及時做好準備。

你可以編寫一個自定義的ActionInvoker,它可以旋轉屬性並在每個屬性上調用BuildUp,然後將其插入到MVC管道中。儘管這很艱難。

Jimmy Bogard has a series on getting more DI into an MVC app,鏈接指向動作過濾器上的特定主題。

1

什麼,你需要做的是讓你的CustomAuthorize屬性繼承Microsoft.Practices.Unity.InterceptionExtension.HandlerAttribute 和 覆蓋「ICallHandler CreateHandler(IUnityContainer容器)」方法。

public class CustomAuthorizeAttribute: HandlerAttribute 
{ 
    public IAuthorizeAttributeHandler AuthorizationHandler { get; set; } 

    public override ICallHandler CreateHandler(IUnityContainer container) 
    { 
     AuthorizationHandler= new AuthorizationAttributeHandler 
    { 
     DBContext = container.Resolve<IDBContext>() 
    }; 
    return AuthorizationHandler; 
    } 
} 

現在創建從Microsoft.Practices.Unity.InterceptionExtension.ICallHandler派生接口並添加IDBContext 作爲成員。

public interface IAuthorizeAttributeHandler : ICallHandler 
{ 
IDBContext DBContext; 
} 

IAuthorizationAttributeHandler實施

public class AuthorizationAttributeHandler : IAuthorizeAttributeHandler 
{ 
public IDBContext DBContext 
     { 
      get; set; 
     } 

    public IMethodReturn Invoke(IMethodInvocation input, GetNextHandlerDelegate getNext) 
    { 
     var result = DBContext.DoWork(input.Arguments..); 

//// Invoke the handler 
      IMethodReturn output = getNext()(input, getNext); 

return getNext()(input, getNext); 
    } 
} 

要在統一配置添加簡單的攔截擴展。

unityContainer 
       .AddNewExtension<Interception>() 
       .Configure<Interception>() 
       .SetInterceptorFor<IYourPageInterface>(new InterfaceInterceptor()); 

將屬性添加到希望執行方面的接口方法。

[CustomAuthorize] 
     ActionResult Index() 
     { 
    } 

希望這有助於 乾杯 斯廷