2017-02-20 66 views
2

在angular1中,我們經常使用工廠來注入類,而不是實例。在angular2中,我可以做同樣的事情:使用DI進行類注入有什麼意義嗎

{provide: MyClass, useFactory:() => { return MyClass }} 

... 
constructor(MyClass) { 
    let instance = new MyClass(); 
} 

但是,我記得讀到,這是由JS模塊的缺席是合理的。現在我們使用ES6模塊,我想知道是否需要使用DI進行類注入?我看到許多不使用角度DI獲取類的庫,但通過import語句訪問它們。

回答

1
{provide: MyClass, useFactory:() => { return MyClass }} 

{provide: MyClass, useValue: MyClass } 

在本質上是一樣的。是的,對於應該手動實例化的類使用DI是有意義的。

它創建時,DI在JS(ES.Next)不執行的問題:

constructor(@Inject(MyClass) MyClass) { 
    this.MyClass = new MyClass; 
} 

但由於類型應適當規定它可能是打字稿使用不太方便:

constructor(@Inject(MyClass) MyClass: typeof MyClass) { 
    this.MyClass = new MyClass; 
} 

讓它作爲提供者可以在不修補原始代碼的情況下隨時替換或增加功能,這是第三方庫的一個很好的特性。

而且它提供了更好的可測性,MyClass可以用stub類或間諜功能所取代。當不涉及DI時,這使得測試更加複雜並且需要在導入級別上實施DI,例如,與rewire-webpack

+0

'{provide:MyClass,useValue:MyClass}'應該是'{provide:MyClass,useClass:MyClass}'或者'MyClass',可能''提供:MyClass,useFactory:()=> {返回MyClass}}'也被認爲是'{提供:MyClass,useFactory:()=> {return new MyClass()}}' –

+0

@GünterZöchbauer,nope ,他的例子是正確的,他想提供一個類,而不是一個實例 –

+0

@GünterZöchbauer應該嗎?在useValue的情況下,一個類被注入。在useClass的情況下,一個類實例被注入。 – estus

1

您需要使用打字稿import語句做出*.ts文件中已知的類型。這與DI完全不同,並且與DI沒有真正的關聯,只不過這種導入的類型可以用作DI提供者密鑰來請求依賴關係。

您可以使用new MyClass()創建類實例。

如果你的類有來自Angulars HttpModuleHttp依賴就像使用DI是方便,因爲你得到通過DI創建的MyClass實例,也是Http參數自動傳遞

class MyClass { 
    constructor(this.http:Http) {} 
} 

DI(反轉控制)也是常見的編程模式,其使測試更容易,因爲你的所得類不緊密耦合的。

DI是hiearchical並可以很容易地共享特定範圍實例(例如一個組件實例和它所有的孩子)

+0

謝謝,_這與DI完全不同,並且與DI_無關 - 在anglular1中,這是向DI注入類的常見模式。所以我從你的答案中瞭解到,如果一個班級沒有依賴關係,那麼使用DI沒有意義,對嗎? –

+0

這也是相反的方式。如果其他課程取決於你的班級,DI也是有用的。如果您想共享具有不同組件,指令,管道或其他服務的實例,那麼DI非常方便,因爲DI需要注意特定實例的注入。注入類從Angular1中取代'$ scope'。另見https://angular.io/docs/ts/latest/cookbook/component-communication.html#!#bidirectional-service和https://angular.io/docs/ts/latest/cookbook/dependency-injection。 html –

+0

是的,謝謝。不確定我是否清楚地表達了自己的問題,因爲你在談論實例,我正在上課。 _注入的類將從Angular1_中取代$ scope - 我們在angular1中使用了該模式以及:) –