C# 關於依賴注入中的Scpoe概念

依賴注入AddScoped()方法

Singleton和transient兩種依賴注入方式比較容易懂。今天專門講一下依賴注入Scope域的概念。
直接上例子:

using System;
using Microsoft.Extensions.DependencyInjection;
namespace vscode_test5
{

    interface IMyInfo
    {
        void PrintID();      
    } 

    public class MyInfo:IMyInfo,IDisposable
    {
        private string id; 
        public MyInfo(string guid)
        {
            id = guid;
        }

        public MyInfo():this(Guid.NewGuid().ToString())
        {
            
        }

        public void PrintID()
        {
            System.Console.WriteLine(id);
        }

        public void Dispose()
        {
            System.Console.WriteLine($"disposed:{id}");
        }
    }

    class Program
    {
        static void Main(string[] args)
        {
            IServiceCollection s = new ServiceCollection();
            s.AddScoped(typeof(IMyInfo), typeof(MyInfo));
            IServiceProvider sp = s.BuildServiceProvider(); // 這叫  “根provider”
            using(IServiceScope iss1 = sp.CreateScope()) // 創建第一個Scope域,此時會根據“根provider”生成一個新的provider副本
            {
                IMyInfo mf1 = iss1.ServiceProvider.GetService<IMyInfo>();//從副本中獲取IMyInfo服務
                mf1.PrintID();
                IMyInfo mf2= iss1.ServiceProvider.GetService<IMyInfo>();//從副本中獲取IMyInfo服務
                mf2.PrintID();
            }
            
            using(IServiceScope iss2 = sp.CreateScope())
            {
                IMyInfo mf1 = iss2.ServiceProvider.GetService<IMyInfo>();//從副本中獲取IMyInfo服務
                mf1.PrintID();
                IMyInfo mf2= iss2.ServiceProvider.GetService<IMyInfo>();//從副本中獲取IMyInfo服務
                mf2.PrintID();
            }
            
            using(IServiceScope iss3 = sp.CreateScope())
            {
                IMyInfo mf1 = iss3.ServiceProvider.GetService<IMyInfo>();//從副本中獲取IMyInfo服務
                mf1.PrintID();
                IMyInfo mf2= iss3.ServiceProvider.GetService<IMyInfo>();//從副本中獲取IMyInfo服務
                mf2.PrintID();
            }         

        }
    }
}

執行結果:

8a77cb3e-f675-40d1-bd72-666e77630f40
8a77cb3e-f675-40d1-bd72-666e77630f40
disposed:8a77cb3e-f675-40d1-bd72-666e77630f40
40baa6e5-9d05-4838-ad1c-152d30290909
40baa6e5-9d05-4838-ad1c-152d30290909
disposed:40baa6e5-9d05-4838-ad1c-152d30290909
f0cfd64d-f0f8-437b-95d5-3830913d0bef
f0cfd64d-f0f8-437b-95d5-3830913d0bef
disposed:f0cfd64d-f0f8-437b-95d5-3830913d0bef

每個using語句會創建一個IServiceScope域,在這個區域內取兩次都是一樣的值。using語句之外,會自動執行相應服務的Dispose()方法,這是由於using語句塊之外會自動釋放所獲取的Scoped服務。當然,服務實現是允許不實現IDisposable接口的。

總之這個using塊內IServiceScoped所在的生存週期,就是Scoped服務的生存週期。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章