目錄:
一、簡介
二、如何使用
2.1、基本使用
2.2、接口使用
2.3、 其他注入
2.4、 注入的生命周期
一、簡介
在上一篇文章中講到替換默認服務容器,我們選擇了Autofac
Autofac---Autofac是一款IOC框架,比較於其他的IOC框架,如Spring.NET,Unity,Castle等等所包含的,它很輕量級性能上非常高。
我們在.Net Core 中替換了自帶的默認服務容器,選擇采用Autofac,那么如何去使用它呢?
二、如何使用
TestController控制器
public class TestController : Controller { private static Animals _animals; public IActionResult Index() { ViewBag.Animal = _animals.Cry(); return View(); } }
替換修改后的Startup.cs 中的ConfigureServices
public IServiceProvider ConfigureServices (IServiceCollection services) { services.AddMvc(); // Add other framework services // Add Autofac var containerBuilder = new ContainerBuilder(); containerBuilder.Populate(services); var container = containerBuilder.Build(); return new AutofacServiceProvider(container); }
1.1、 基本使用
創建 Animals 類
public class Animals { public string Cry() { return "小狗,汪汪汪"; } }
ConfigureServices 中添加注冊
containerBuilder.RegisterType<Animals>();
TestController 控制器中添加構造函數
public TestController(Animals animals) { _animals = animals; }
運行起來看下

1.2、 接口使用
創建IAnimals.cs
public interface IAnimals { string Cry(); } public class DogCry : IAnimals { public string Cry() { return "小狗,汪汪汪"; } } public class CatCry : IAnimals { public string Cry() { return "小貓,喵喵喵"; } }
ConfigureServices 中添加注冊
containerBuilder.RegisterType<DogCry>().As<IAnimals>();
TestController 控制器中添加構造函數並修改_animals為對應的類型
public TestController(IAnimals animals) { _animals = animals; }
運行起來

如果一個類型被多次注冊,以最后一個注冊的為准
ConfigureServices 中添加注冊
containerBuilder.RegisterType<DogCry>().As<IAnimals>();
containerBuilder.RegisterType<CatCry>().As<IAnimals>();
運行起來看下

1.3、 其他注入
1、 自動裝配—從容器里面選擇一個構造方法來創建對象
創建Cry類
public class Cry { public Cry() { voice= "小狗,汪汪汪"; } public Cry(string voices) { if (string.IsNullOrWhiteSpace(voices)) { voice = "旺旺旺"; } voice= $"小狗,{voices}"; } public Cry(string name, string voices):this(voices) { if (string.IsNullOrWhiteSpace(voices)) { voice = "旺旺旺"; } if (string.IsNullOrWhiteSpace(name)) { voice = "柴犬"; } voice= $"{name},{voices}"; } public static string voice { get; set; } }
ConfigureServices 中添加注冊
containerBuilder.RegisterType<Cry>().UsingConstructor(typeof(string));
Autofac會默認從容器中選擇參數最多的構造函數,如果想要指定選擇的話可以指定UsingConstructor
2、 實例化注入
還是上面的Cry類
ConfigureServices 中添加注冊
var output = new Cry("叫聲叫聲"); containerBuilder.RegisterInstance(output).ExternallyOwned();
先對對象實例化然后注冊,ExternallyOwned--配置組件,使容器永遠不會處理實例。
修改Test控制器
public IActionResult Index() { ViewBag.Animal = Cry.voice; return View(); }

1.4、 注入的生命周期
1、 Transient(暫時生存期)--暫時生存期服務是每次從服務容器進行請求時創建的。 這種生存期適合輕量級、 無狀態的服務。
2、 Scoped(范圍生存期)--范圍生存期服務是每個客戶端請求連接時創建的一次實例
3、 Singleton(單例生存期)--單例生存期會在程序第一次請求是創建一次實例,不會變化的
我們來利用生成guid來看一下三個的生命周期有什么具體的不一樣
修改Test控制器
public class TestController : Controller { private static IGetTransient _getTransient; private static IGetScoped _getScoped; private static IGetSingleton _getSingleton; public TestController(IGetTransient getTransient, IGetScoped getScoped, IGetSingleton getSingleton) { _getTransient = getTransient; _getScoped = getScoped; _getSingleton = getSingleton; } public IActionResult Index() { ViewBag.getTransient = _getTransient.GuidItem(); ViewBag.getScoped = _getScoped.GuidItem(); ViewBag.getSingleton = _getSingleton.GuidItem(); return View(); } }
修改Index.cshtml
<div>
<span>Transient:</span><span>@ViewBag.getTransient</span>
</div>
<div>
<span>Scoped:</span><span>@ViewBag.getScoped</span>
</div>
<div>
<span>Singleton:</span><span>@ViewBag.getSingleton</span>
</div>
IGuid接口
public interface IGuid { Guid GuidItem(); } /// <summary> /// 暫存生存期 /// </summary> public interface IGetTransient : IGuid { } /// <summary> /// 范圍生存期 /// </summary> public interface IGetScoped : IGuid { } /// <summary> /// 單例生存期 /// </summary> public interface IGetSingleton : IGuid { }
GuidServiceBase類
public class GuidServiceBase: IGuid { private readonly Guid _item; public GuidServiceBase() { _item = Guid.NewGuid(); } public Guid GuidItem() { return _item; } } /// <summary> /// 暫存生存期 /// </summary> public class GuidTransientService : GuidServiceBase, IGetTransient { } /// <summary> /// 范圍生存期 /// </summary> public class GuidScopedService : GuidServiceBase, IGetScoped { } /// <summary> /// 單例生存期 /// </summary> public class GuidSingletonService : GuidServiceBase, IGetSingleton { }
ConfigureServices 中添加注冊
containerBuilder.RegisterType<GuidTransientService>().As<IGetTransient>(); containerBuilder.RegisterType<GuidScopedService>().As<IGetScoped>().InstancePerLifetimeScope();
containerBuilder.RegisterType<GuidSingletonService>().As<IGetSingleton>().SingleInstance();

運行起來發現Singleton(單例生存期)沒有變化,僅產生了一個實例,但是Scoped(范圍生存期) 變化的不一樣,按照理論來說應該刷新之后會變化,但是兩邊應該會是一樣的值。--(因為兩個頁面依然是獨立的,並不是一次請求)。我們換另一種方式驗證這個
修改Test控制器—新增Guid
public IActionResult Guid() { return View(); }
添加Guid.cshtml—通過inject注入依賴
@{ Layout = null; } @inject WebApplication3.IGetTransient TransientService @inject WebApplication3.IGetScoped GuidScopedService @inject WebApplication3.IGetSingleton GuidSingletonService
<!DOCTYPE html> <html> <head> <meta name="viewport" content="width=device-width" /> <title>Guid</title> </head> <body> <div class="row"> <div> <h2>GuidItem Shows</h2> <h3>TransientItem: @TransientService.GuidItem()</h3> <h3>ScopedItem: @GuidScopedService.GuidItem()</h3> <h3>SingletonItem: @GuidSingletonService.GuidItem()</h3> </div> </div> </body> </html>
修改Index.cshtml
@{ ViewData["Title"] = "Index"; } <h1>Index</h1> @Html.Partial("Guid") <h1>Guid</h1> @Html.Partial("Guid")
運行然后打開兩個頁面

我們再次完全吻合的,暫時生命周期在每次使用的時候的Guid(實例)都是變化的,范圍生命周期在同一個請求范圍內Guid是不變化的,不同請求的Guid是會發生變化的。但是單例生命周期的Guid從程序開始就不會發生變化的。
歡迎大家掃描下方二維碼,和我一起學習更多的知識😊

