在前面的好多篇幅中都有提到过ControllerDescriptor类型,而且在ASP.NET MVC 过滤器(一)篇幅中简单的描述过,今天咱们就来说一下ControllerDescriptor类型。缓存
在ASP.NET MVC 过滤器(一)篇幅中有过示意图,当时说明了在生成过滤器信息对象集合以前所要作的一些步骤中包含着生成ControllerDescriptor类型,并无详细的说明,咱们先来看一下图1ide
图1函数
关于这个示意图以前的一些部分我就不细说了,咱们就先看一下ControllerDescriptor类型的生成过程;spa
从图1中能够看出ControllerDescriptor类型的由来是由ControllerDescriptorCache控制器描述类型缓存类【系统默认实现类】来生成的,ControllerDescriptorCache类型也是实现了ReaderWriterCache<Type, ControllerDescriptor>类型的,这里只要描述一下ReaderWriterCache<Type, ControllerDescriptor>类型中的实现就行了,由于ControllerDescriptorCache也只是调用了基类的某个函数来实现生成的功能。来讲实现,ReaderWriterCache<Type, ControllerDescriptor>中有个键值队类型的缓存变量【下文中都用缓存一词代替】,用来存贮控制器描述类型的,实现方法的签名和ControllerDescriptorCache的GetDescriptor()方法同样,第一个参数是会根据当前ControllerContext中的Controller来获取当前控制器的类型,第二个参数暂且不谈稍后讲解如今只要把第二个参数是当成生成ControllerDescriptor类型的外插模块,在实现中,首先会根据ControllerType去缓存中查找,若是有的话则返回查找到的控制器描述类型,没有的话,则会根据第二个参数来生成控制器描述类型,而后会先把生成的控制器描述类型设置到缓存中再返回生成的类型。code
看到这里有的朋友会问说来讲去也没说重点,ControllerDescriptor类型到底怎么来的,对的,重点在于第二个参数,上面的描述只是让你们更清晰的认识到Func<ControllerDescriptor>的重要性。对象
看一下系统的默认实现Func<ControllerDescriptor>的方式: () => new ReflectedControllerDescriptor(controllerType),controllerType类型是从当前ControllerContext.Controller.GetType()获取的。blog
对于ReflectedControllerDescriptor类型,在默认实现中都是把它做为ControllerDescriptor类型类使用的。ip
这个时候咱们看一下ControllerDescriptor类型的定义,示例代码1-1.get
代码1-1博客
public abstract class ControllerDescriptor : ICustomAttributeProvider, IUniquelyIdentifiable { protected ControllerDescriptor(); // 摘要: // 获取控制器的名称。 // // 返回结果: // 控制器的名称。 public virtual string ControllerName { get; } // // 摘要: // 获取控制器的类型。 // // 返回结果: // 控制器的类型。 public abstract Type ControllerType { get; } public virtual string UniqueId { get; } // 摘要: // 使用指定的名称和控制器上下文来查找操做方法。 // // 参数: // controllerContext: // 控制器上下文。 // // actionName: // 操做的名称。 // // 返回结果: // 有关操做方法的信息。 public abstract ActionDescriptor FindAction(ControllerContext controllerContext, string actionName); // // 摘要: // 在控制器中检索操做-方法描述符的列表。 // // 返回结果: // 控制器中的操做-方法描述符的列表。 public abstract ActionDescriptor[] GetCanonicalActions(); public virtual object[] GetCustomAttributes(bool inherit); public virtual object[] GetCustomAttributes(Type attributeType, bool inherit); public virtual bool IsDefined(Type attributeType, bool inherit); }
在代码1-1中,你们也都是看到了ControllerDescriptor类型的定义是抽象类型,其中ControllerName属性表示着当前控制器上下文中的控制器名称,ControllerType属性是被定义为抽象的了,须要在派生类中的实现的(ReflectedControllerDescriptor类型),FindAction()也是抽象的,看这个方法的返回类型就知道了它是作什么用的了,对于这部分的细节都是在默认实现类ReflectedControllerDescriptor类型中表示,来看ReflectedControllerDescriptor类型的定义,示例代码1-2
代码1-2
public class ReflectedControllerDescriptor : ControllerDescriptor { // // 参数: // controllerType: // 控制器的类型。 // // 异常: // System.ArgumentNullException: // controllerType 参数为 null。 public ReflectedControllerDescriptor(Type controllerType); public override sealed Type ControllerType { get; } public override ActionDescriptor FindAction(ControllerContext controllerContext, string actionName); public override ActionDescriptor[] GetCanonicalActions(); public override object[] GetCustomAttributes(bool inherit); public override object[] GetCustomAttributes(Type attributeType, bool inherit); public override bool IsDefined(Type attributeType, bool inherit); }
对于ReflectedControllerDescriptor类型的具体实现,在这里只是简要的说明一下,ReflectedControllerDescriptor类型的构造函数参数为Type类型,这里上面也说过这是Controller类型,在构造函数构造的时候,ReflectedControllerDescriptor类型内部还有个ActionMethodSelector类型的私有变量,ActionMethodSelector类型的构造函数所需参数也是Type类型。这里为何要说到ActionMethodSelector类型呢?由于在ReflectedControllerDescriptor类型的FindAction()方法的具体实现中使用的就是ActionMethodSelector类型中的方法。就如图1所示的那样。
做者:金源
出处:http://www.cnblogs.com/jin-yuan/
本文版权归做者和博客园共有,欢迎转载,但未经做者赞成必须保留此段声明,且在文章页面