abp vnext2.0核心组件之.Net Core默认DI组件切换到AutoFac源码解析

老版Abp对Castle的严重依赖在vnext中已经获得了解决,vnext中DI容器能够任意更换,为了实现这个功能,底层架构相较于老版abp,能够说是进行了高度重构.固然这得益于.Net Core的DI容器组件自己的优点.接着abp vnext2.0核心组件之模块加载组件源码解析上文,上文中我跳过了DI切换这个流程,由于我以为这是整个框架的亮点之一,因此单独写了这篇随笔.html

 .Net Core2.2以后,切换DI的实现换了,改为实现以下接口架构

 

一、核心ServiceProviderFactory接口实现框架

核心原理很是的简单,看看vnext如何实现这个工厂约束接口,并返回指定provider.ide

 大体的逻辑是传入ServiceCollection,遍历ServiceCollection使用autofac的containerbuilder进行注入.最后调用containerbuilder实例的builder的build方法,返回provider.一鼓作气,很简单.post

接着,重点来了,看看Populate方法,看看其如何将ServiceCollection中的类型注入autofac容器的.ui

先将原生DI的相关功能转换成Autofac的,接着进行类型注册.url

 第一步获取模块加载类型中全部的模块,模块信息以下:3d

第二步释出DI容器中的ServiceRegistrationActionList,这个list很是重要.在DI默认容器转中的类型注入Autofac容器时,会遍历全部类型,并将类型的类型和实现生成上下文,传递给指定的action,实现代码以下:htm

 看看vnext的示例代码以下:blog

 

 简单的工做单元.

介绍了ServiceRegistrationActionList以后,接着看以下代码:

 

 遍历全部的services集合,根据注入的方式和注入类型的差别进行区分,并注入到Autofac的ContainerBuilder中.代码很简单,挑个重点说下,以下:

 红框中的第一行,代码以下:

 若是当前类型所在的程序集属于应用程序集,不是与第三方程序集,则启动属性注入(反射的方式).

红框中的第二行就是上面介绍的遍历全部类型,生成上下文,并执行DI中注入的ServiceRegistrationActionList中的action,这里注意拦截器的注入,以下:

在执行完全部的Action以后,其中有部分Action,以下:

 

 是向上下文中的拦截器集合追加拦截器的,因此当全部的action执行完毕以后,全部的拦截器也被写入到了拦截器集合中.下一步初始化拦截器。以下:

 这边后续会写一篇随笔,专门介绍vnext中的拦截器的机制.涉及到另外一个组件.本文就不介绍了.不是本文的重点.

顺便提一句

 有能力的能够作一下这个todo.

ok,到这里全部的默认DI中的类型集合所有注入到了autofac中,而且完成了拦截器的初始化和应用程序框架的自动属性注入功能.

整个Populate方法执行完毕.AbpAutofacServiceProviderFactory的CreateBuilder方法也就结束了.最终将默认DI中的类型集合(IServiceCollection)转换成Autofac中的ContainerBuilder

接着看看CreateServiceProvider方法以下:

 看看AutofacServiceProvider的构造,以下:

 具体参考源码,实现了默认DI的获取Services接口。因此你能够继续用默认DI提供的方法,可是此时DI已被切换成了Autofac.

 

二、模块加载系统如何与之配合

接下去看看vnext的模块加载系统如何配合AbpAutofacServiceProviderFactory完成DI切换

第一步须要注入Autofac服务.

在注入核心的工厂服务后,且整个vnext框架的类型所有注入到默认DI中,那么须要触发核心工厂服务的相关方法以下:

继续观察ServiceCollectionCommonExtensions类下面的BuildServiceProviderFromFactory,以下

 直接调用核心的工厂服务的CreateBuilder方法,这样全部默认DI中的类型所有注入到了autofac的容器中.而且切换默认DI容器到了autofac.替换默认DI的核心接口实现以下:

 最后须要将模块加载系统中预先注入的ServiceProvider替换成核心的工厂服务的CreateBuilder方法执行后生成的ServiceProvider.

 ok,整个DI切换流程到这里结束.abp团队的实现很简洁.若是你须要扩展其余的DI容器,能够参照他们的实现.

 

纯属我的理解,能力有限,有问题请指正!

相关文章
相关标签/搜索