2016-11-28 14 views
11

ASP.NETコアは、依存性注入を設定するにはIServiceCollectionに拡張メソッドを使用するタイプが必要になったとき、それは新しいインスタンスを作成するために、適切な方法を使用しています。.NETコア依存性注入インスタンスはいつ廃棄されますか?

  • AddTransient<T> - 再びそれぞれ作成されたタイプを追加しますそれが要求される時間。
  • AddScoped<T> - 要求のスコープに対して保持されるタイプを追加します。
  • AddSingleton<T> - 最初に要求されたときにタイプを追加し、それを保持します。

Disposeが実際に呼び出されたときに、それらのパターンのそれぞれに廃棄されていないと問題が発生するのは、IDisposableです。

インスタンスが常に破棄されるようにするために追加する必要があるものはありますか(例外処理など)?

答えて

16

解決されたオブジェクトのコンテナと同じライフタイム/廃棄サイクルがあります。usingステートメントまたは.Dispose()メソッドを使用して一時的なサービスをコードに手動で配置しない限りです。

ASP.NETコアでは、リクエストごとにインスタンス化され、リクエストの最後に処理されるスコープ付きコンテナを取得します。現時点では、このコンテナによって作成されたスコープ付きおよび一時的な依存関係も処理されます(つまり、IDisposableインターフェイスを実装している場合)。ソースコードhereにも表示されます。親コンテナが配置されますとき

public void Dispose() 
{ 
    lock (ResolvedServices) 
    { 
     if (_disposeCalled) 
     { 
      return; 
     } 
     _disposeCalled = true; 
     if (_transientDisposables != null) 
     { 
      foreach (var disposable in _transientDisposables) 
      { 
       disposable.Dispose(); 
      } 

      _transientDisposables.Clear(); 
     } 

     // PERF: We've enumerating the dictionary so that we don't allocate to enumerate. 
     // .Values allocates a ValueCollection on the heap, enumerating the dictionary allocates 
     // a struct enumerator 
     foreach (var entry in ResolvedServices) 
     { 
      (entry.Value as IDisposable)?.Dispose(); 
     } 

     ResolvedServices.Clear(); 
    } 
} 

シングルトンは、アプリケーションのシャットダウン時に通常は意味し、配置されます。

TL; DR:アプリケーションの起動時に限り、あなたはスコープのインスタンス化はしないと/過渡サービス(app.ApplicationServices.GetService<T>()を使用)し、あなたのサービスが正しく使い捨てインタフェースを実装(のようなpointed in MSDNは)あなたが世話をする必要は何もありません。

親コンテナはConfigure(IApplicationBuilder app)メソッドの外では使用できません。外部にアクセスできるようにするためにファンキーなことをしない限り(これはどうにかする必要はありません)。

もちろん、一時的なサービスを可能な限り早く解放することを奨励します。特に、多くのリソースを消費する場合は特にそうです。