Castle IOC容器内幕故事(下)
主要内容
1.ComponentModelBuilder 和 Contributors
2.Contributors分析
3.Handles分析
4.ComponentActivator分析
一.ComponentModelBuilder 和 Contributors
在前一篇中介绍组件的注册流程时说到了,创建ComponentModel的过程就是调用contributor来对组件进行处理的过程。Contributor就是我们这个内幕故事的第一个主角,在DefaultComponentModelBuilder一共注册了八个Contributor,每一个Contributor都专门负责处理某一方面的事情。如下代码所示:
| 1 2 3 4 5 6 7 8 9 10 11 12 | protected virtual void InitializeContributors(){  AddContributor( new ConfigurationModelInspector() );  AddContributor( new LifestyleModelInspector() );  AddContributor( new ConstructorDependenciesModelInspector() );  AddContributor( new PropertiesDependenciesModelInspector() );  AddContributor( new MethodMetaInspector() );  AddContributor( new LifecycleModelInspector() );  AddContributor( new ConfigurationParametersInspector() );  AddContributor( new InterceptorInspector() );} | 
1.ConfigurationModelInspector:用来处理配置,它使用ConfigurationStore在Kernel中注册来保持一个组件的连接。
2.LifestyleModelInspector:生命周期处理方式,主要有Singleton、Thread、Transient、Pooled、Custom这些都可以在配置文件中指定,后续文章会讲到。
3.ConstructorDependenciesModelInspector:处理构造函数依赖,收集所有的Public构造函数,并它们交给ComponentModel的Constructors集合。
4.PropertiesDependenciesModelInspector:处理属性依赖,收集所有的可写的属性,Kernel也许不会在组件注册时就设置所有的属性,也有可能在请求获取组件时来设置。
5.MethodMetaInspector:检测组件配置中的Method节点,每一个节点都将添加到ComponentModel的Method集合中。
6.LifecycleModelInspector:处理组件生命周期,即在组件装载,初始化,销毁所出发的行为,分别对应三个接口:IInitializable,ISupportInitialize,IDisposable,如果组件实现了这些接口,容器会自动在不同的生命周期调用它们。
7.ConfigurationParametersInspector:处理配置文件中的parameters元素内容,每一个parameters都将创建一个ParameterModel,并添加到ComponentModel的Parameters集合中。
8.InterceptorInspector:处理InterceptorAttribute或者配置文件中的interceptors元素的信息。
在有些情况下,我们可能并不需要这么多的Contributors,或者说我们想添加自定义的Contributors,可以用ComponentModelBuilder的如下两个方法来实现对Contributors的管理:
| 1 2 3 4 5 6 7 8 9 | public void AddContributor(IContributeComponentModelConstruction contributor){  contributors.Add(contributor);}public void RemoveContributor(IContributeComponentModelConstruction contributor){  contributors.Remove(contributor);} | 
二.Contributors分析
通过上面的分析可以看到八个Contributors按一定顺序组合构成了整个组件的处理流程,现在我们来看一下Contributors是如何实现的?每一个Contributors都必须实现于接口IcontributeComponentModelConstruction,通过这个,我们可以创建自己的Contributors:
| 1 2 3 4 5 | public interface IContributeComponentModelConstruction{  void ProcessModel(IKernel kernel, ComponentModel model);} | 
来看一下其中LifecycleModelInspector的实现代码:
| 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 | [Serializable]public class LifecycleModelInspector : IContributeComponentModelConstruction{  public LifecycleModelInspector()  {  }  public virtual void ProcessModel(IKernel kernel, ComponentModel model)  {    if (typeof (IInitializable).IsAssignableFrom(model.Implementation))    {      model.LifecycleSteps.Add( LifecycleStepType.Commission, InitializationConcern.Instance );    }    if (typeof (ISupportInitialize).IsAssignableFrom(model.Implementation))    {      model.LifecycleSteps.Add( LifecycleStepType.Commission, SupportInitializeConcern.Instance );    }    if (typeof (IDisposable).IsAssignableFrom(model.Implementation))    {      model.LifecycleSteps.Add( LifecycleStepType.Decommission, DisposalConcern.Instance );    }  }} | 
至此,第一个主角Contributors的故事就完了。
三.Handles分析
在组件注册流程中,还提到了一个重要的角色就是Handles。对Handles的描述引用Castle官方网站的一句话来说就是“They don't construct the component themselves, but they know who does”。Handles它有两个状态,分别标识组件是否可以被请求还是需要继续等待相关的依赖,所有的Handles都必须实现IHandles接口,通过这个也可以创建自己的Handle。
| 1 2 3 4 5 6 7 8 9 10 11 12 13 14 | public enum HandlerState{  Valid,  WaitingDependency}public interface IHandler{  void Init(IKernel kernel);  object Resolve();  void Release(object instance);  HandlerState CurrentState { get; }  ComponentModel ComponentModel { get; }} | 
Handles通过下面两个方法来检查哪些组件可以被请求,而哪些组件需要继续等待相关依赖,但是它并不做具体的组件创建工作。
| 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | public override object Resolve(){  if (CurrentState == HandlerState.WaitingDependency)  {    String message =      String.Format("Can't create component '{1}' as it has dependencies to be satisfied. {0}",        ObtainDependencyDetails(), ComponentModel.Name );    throw new HandlerException(message);  }   return lifestyleManager.Resolve();}public override void Release(object instance){  lifestyleManager.Release( instance );} | 
四.ComponentActivator分析
介绍完前面三位角色之后,今天最后一位登场的主角就是ComponentActivator,组件激活器。每一个组件都和一个Activator相关联。Castle IOC为我们提供了默认的Activator,Castle IOC已经为我们提供了默认的Activator,但有时候也需要自己去实现Activator,比如说创建组件的实例并不是new出来的,而是通过我们自定义的Factory方法创建的,或者说我们需要创建的组件一个Remoting组件。创建自定义的Activator需要继承于AbstractComponentActivator基类或者DefaultComponentActivator。
| 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 | [Serializable]public abstract class AbstractComponentActivator : IComponentActivator{  private IKernel kernel;  private ComponentModel model;  private ComponentInstanceDelegate onCreation;  private ComponentInstanceDelegate onDestruction;  public AbstractComponentActivator(ComponentModel model, IKernel kernel,    ComponentInstanceDelegate onCreation,    ComponentInstanceDelegate onDestruction)  {    this.model = model;    this.kernel = kernel;    this.onCreation = onCreation;    this.onDestruction = onDestruction;  }  public IKernel Kernel  {    get { return kernel; }  }  public ComponentModel Model  {    get { return model; }  }  public ComponentInstanceDelegate OnCreation  {    get { return onCreation; }  }  public ComponentInstanceDelegate OnDestruction  {    get { return onDestruction; }  }  protected abstract object InternalCreate();  protected abstract void InternalDestroy(object instance);  IComponentActivator Members#region IComponentActivator Members  public virtual object Create()  {    object instance = InternalCreate();    onCreation(model, instance);    return instance;  }  public virtual void Destroy(object instance)  {    InternalDestroy(instance);    onDestruction(model, instance);  }  #endregion} | 
关于Castle IOC内部主角分析就到这里了,至此Castle IOC的内幕故事也告一段落了,通过这两篇文章我们对Castle IOC的内幕有了一个简单的认识,这对于我们使用Castle IOC有很大的好处,后续文章会讲到。
Castle IOC容器内幕故事(下)的更多相关文章
- Castle IOC容器内幕故事(上)
		主要内容 1.WindsorContainer分析 2.MicroKernel分析 3.注册组件流程 一.WindsorContainer分析 WindsorContainer是Castle的IOC容 ... 
- Castle IOC容器组件生命周期管理
		主要内容 1.生命处理方式 2.自定义生命处理方式 3.生命周期处理 一.生命处理方式 我们通常创建一个组件的实例使用new关键字,这样每次创建出来的都是一个新的实例,如果想要组件只有一个实例,我们会 ... 
- Castle IOC容器与Spring.NET配置之比较
		我本人对于Spring.NET并不了解,本文只是通过一个简单的例子来比较一下两者配置之间的区别.在Castle IOC容器中,提出了自动装配(Auto-Wiring)的概念,即由容器自动管理组件之间的 ... 
- Castle IOC容器构建配置详解(二)
		主要内容 1.基本类型配置 2.Array类型配置 3.List类型配置 4.Dictionary类型配置 5.自定义类型转换 一.基本类型配置 在Castle IOC的配置文件中,大家可能都已经注意 ... 
- Castle IOC容器构建配置详解(一)
		主要内容 1.配置什么 2.几种配置方式 3.Include 介绍 4.Properties介绍 5.条件状态 一.配置什么 Castle IOC中并不像Spring.net那样贯穿着一个思想就是一切 ... 
- Castle IOC容器快速入门
		主要内容 1.为什么要IOC 2.什么是Castle IOC容器 3.快速入门示例 4.几个重要的概念 一,为什么要IOC IOC(控制反转或者叫依赖注入)Martin Fowler大师在他的文章中已 ... 
- Castle IOC容器实践之FactorySupport Facility
		PDF版本下载:http://file.ddvip.com/2008_10/1223538519_ddvip_4853.rar示例代码下载:http://file.ddvip.com/2008_10/ ... 
- Castle学习笔记----初探IOC容器
		通常IOC实现的步骤为-->建立容器-->加入组件-->获取组件-->使用组件. 1.建立容器 建立容器也就是IWindsorContainer.接着我门要向容器中注册服务,并 ... 
- .net core2.0下Ioc容器Autofac使用
		.net core发布有一段时间了,最近两个月开始使用.net core2.0开发项目,大大小小遇到了一些问题.准备写个系列介绍一下是如何解决这些问题以及对应技术.先从IOC容器Autofac开始该系 ... 
随机推荐
- 20160128.CCPP体系详解(0007天)
			以下内容有所摘取,进行了某些整理和补充 论浮点数的存储原理:float浮点数与double浮点数的二进制存储原理–>阶码 浮点数转二进制 1.整数int类型和浮点数float类型都是占用4个字节 ... 
- HDU 1015 Safecracker
			解题思路:这题相当诡异,样例没过,交了,A了,呵呵,因为理论上是可以通过的,所以 我交了一发,然后就神奇的过了.首先要看懂题目. #include<cstdio> #include< ... 
- SAS使用SPD引擎并报Encoding错误
			ERROR: Unable to open data file because its file encoding differs from the SAS session encoding and ... 
- mysql 表空间及索引的查看方法
			CONCAT : concat() 方法用于连接两个或多个数组. database : 数据库(11张) 数据库,简单来说是本身可视为电子化的文件柜——存储电子文件的处所,用户可以对文件 ... 
- FPGA代码设计规范整理
			1.设计中的FIFO.状态机接口需要有异常恢复状态和状态上报机制,格雷码电路防止被综合电路优化掉. a)自行设计的格雷码FIFO(一般用于连续数据流跨时钟域)用Synplify综合时,为了防止被优化需 ... 
- 两个异步处理AsyncTask和Handler的优缺点
			AsyncTask和Handler对比 1 ) AsyncTask实现的原理,和适用的优缺点 AsyncTask,是android提供的轻量级的异步类,可以直接继承AsyncTask,在类中实现异步操 ... 
- The Network Adapter could not establish the connection解决办法
			用 oracle net manager 将监听改为IP地址,将服务命名也改为IP地址,然后数据库连接改为IP地址方式不要用localhost 
- C#操作Excel,对Sheet插入次序的控制 (有待完善)
			C#对Excel文件的操作,插入工作表(Worksheet)的方法是 Workbook.Worksheets.Add().通常情况下,我们在EXCEL的工作薄中,使用菜单操作:插入一个新的工作表,那么 ... 
- 7、NFC技术:让Android自动运行程序
			用于描述NDEF格式数据的两个重要的类 NdefMessage:描述NDEF格式的信息 NdefRecord:描述NDEF信息的一个信息段 NdefMessage和NdefRecord是Androi ... 
- 《深入理解C#》第3版 学习进度备忘
			学习资源:<深入理解C#>第3版 知识基础支持: <C# in a nutshell> O Reilly出版社,是一本从头介绍C#的优秀图书.<Essential C#5 ... 
