ASP.NET MVC三个重要的描述对象:ControllerDescriptor与ActionDescriptor2012-08-28 博客园 ArtechControllerDescriptor与ActionDescriptor的创建不论是用于描述Controller的ControllerDescriptor,还是用于描述Action方 法的ActionDescriptor,都具有同步和异步两个版本,那么这些不同类型的 ControllerDescriptor的ActionDescriptor是在什么情况下创建的呢?一、ControllerActionInvoker与AsyncControllerActionInvokerControllerDescriptor的创建设计到一个重要的名为ActionInvoker的组件, 顾名思义,ActionInvoker专门用于Action方法的执行。我们会在本书第7章 “Action方法的执行”中对ActionInvoker进行深入介绍,在这里我们只需要对其 作一个简单的了解。ActionInvoker实现了具有如下定义的IActionInvoker接口,唯一的方法实现 了对指定Action方法的执行,而作为Controller的默认基类的Controller具有一 个ActionInvoker属性,该属性表示的ActionInvoker被真正用于定义在该 Controller类型中的所有Action方法的执行。
1: public interface IActionInvoker
2: {
3: bool InvokeAction(ControllerContext controllerContext, string actionName);
4: }
5:
6: public abstract class Controller
7: {
8: //其它成员
9: public IActionInvoker ActionInvoker { get; set; }
10: }
而具有如下定义的System.Web.Mvc.Async.IAsyncActionInvoker接口是 ActionInvoker的异步版本。IAsyncActionInvoker继承了IActionInvoker接口, 并在此基础上定义了两个BeginInvokeAction/EndInvokeAction方法用于Action方 法的异步执行。
1: public interface IAsyncActionInvoker : IActionInvoker
2: {
3: IAsyncResult BeginInvokeAction(ControllerContext controllerContext,string actionName, AsyncCallback callback, object state);
4: bool EndInvokeAction(IAsyncResult asyncResult);
5: }
ASP.NET MVC真正用于Action方法同步和异步执行的ActionInvoker分别是 ControllerActionInvoker和AsyncControllerActionInvoker。如下面的代码片断 所示,ControllerActionInvoker定义了一个受保护的方法 GetControllerDescriptor用于根据指定的Controller上下文获取相应的 ControllerDescriptor,它的子类AsyncControllerActionInvoker对这个方法进 行了重写。
1: public class ControllerActionInvoker : IActionInvoker
2: {
3: //其它成员
4: protected virtual ControllerDescriptor GetControllerDescriptor( ControllerContext controllerContext);
5: }
6:
7: public class AsyncControllerActionInvoker : ControllerActionInvoker,IAsyncActionInvoker, IActionInvoker
8: {
9: //其它成员
10: protected override ControllerDescriptor GetControllerDescriptor( ControllerContext controllerContext);
11: }
我们所有要了解的是在默认情况下(没有对Controller类型的ActionInvoker 属性进行显式设置)采用的ActionInvoker类型是哪个。ASP.NET MVC对Conroller 采用的ActionInvoker类型的选择机制是这样的:通过当前的DependencyResolver以IAsyncActionInvoker接口去获取注册的 ActionInvoker,如果返回对象不为Null,则将其作为默认的ActionInvoker。通过当前的DependencyResolver以IActionInvoker接口去获取注册的 ActionInvoker,如果返回对象不为Null,则将其作为默认的ActionInvoker。