zoukankan      html  css  js  c++  java
  • MVC中Action的执行过程

    接着上一篇:MVC控制器的激活过程

    一、代码现行,该伪代码大致解析了Action的执行的过程

    try 
    { 
       Run each IAuthorizationFilter's OnAuthorization() method 
      
       if(none of the IAuthorizationFilters cancelled execution)  
       { 
          Run each IActionFilter's OnActionExecuting() method 
          Run the action method 
          Run each IActionFilter's OnActionExecuted() method (in reverse order) 
      
          Run each IResultFilter's OnResultExecuting() method 
          Run the action result  
          Run each IResultFilter's OnResultExecuted() method (in reverse order) 
       } 
       else
       { 
          Run any action result set by the authorization filters 
       } 
    } 
    catch(exception not handled by any action or result filter)  
    { 
       Run each IExceptionFilter's OnException() method 
       Run any action result set by the exception filters 
    }

    二、返回主战场Action执行方法中

    public virtual bool InvokeAction(ControllerContext controllerContext, string actionName)
            {
                if (controllerContext == null)
                {
                    throw new ArgumentNullException("controllerContext");
                }
                if (string.IsNullOrEmpty(actionName))
                {
                    throw new ArgumentException(MvcResources.Common_NullOrEmpty, "actionName");
                }
           //描述了控制器的相关信息 ControllerDescriptor controllerDescriptor
    = this.GetControllerDescriptor(controllerContext);
    //描述了相关Action的相关信息 ActionDescriptor actionDescriptor
    = this.FindAction(controllerContext, controllerDescriptor, actionName); if (actionDescriptor != null) {
    //获取该action的所有Filter FilterInfo filters
    = this.GetFilters(controllerContext, actionDescriptor); try { AuthorizationContext authorizationContext = this.InvokeAuthorizationFilters(controllerContext, filters.AuthorizationFilters, actionDescriptor); if (authorizationContext.Result != null) { this.InvokeActionResult(controllerContext, authorizationContext.Result); } else { if (controllerContext.Controller.ValidateRequest) {
    //地球人应该知道这个东西干嘛的,你知道吗? ControllerActionInvoker.ValidateRequest(controllerContext); } IDictionary
    <string, object> parameterValues = this.GetParameterValues(controllerContext, actionDescriptor); ActionExecutedContext actionExecutedContext = this.InvokeActionMethodWithFilters(controllerContext, filters.ActionFilters, actionDescriptor, parameterValues); this.InvokeActionResultWithFilters(controllerContext, filters.ResultFilters, actionExecutedContext.Result); } } catch (ThreadAbortException) { throw; } catch (Exception exception) { ExceptionContext exceptionContext = this.InvokeExceptionFilters(controllerContext, filters.ExceptionFilters, exception); if (!exceptionContext.ExceptionHandled) { throw; } this.InvokeActionResult(controllerContext, exceptionContext.Result); } return true; } return false; }
    //上面的授权过程 
    AuthorizationContext authorizationContext = this.InvokeAuthorizationFilters(controllerContext, filters.AuthorizationFilters, actionDescriptor); if (authorizationContext.Result != null) { this.InvokeActionResult(controllerContext, authorizationContext.Result); }

    protected virtual AuthorizationContext InvokeAuthorizationFilters(ControllerContext controllerContext, IList<IAuthorizationFilter> filters, ActionDescriptor actionDescriptor)
    {
        AuthorizationContext authorizationContext = new AuthorizationContext(controllerContext, actionDescriptor);
        foreach (IAuthorizationFilter current in filters)
        {
            current.OnAuthorization(authorizationContext);//很显然我们在自定义IAuthorizationFilter时,会去做事情在这里定义的。如果
      //此过程,authorizationContext的Result 被你给赋值了,那么所有的其他授权认证将会终止,系统将全力执行 this.InvokeActionResult(controllerContext, authorizationContext.Result);
    if (authorizationContext.Result != null) { break; } } return authorizationContext; }

    三、Action连同过滤器的执行,上面谈了授权过滤器的执行

    IDictionary<string, object> parameterValues = this.GetParameterValues(controllerContext, actionDescriptor);
    ActionExecutedContext actionExecutedContext = this.InvokeActionMethodWithFilters(controllerContext, filters.ActionFilters, actionDescriptor, parameterValues);
    this.InvokeActionResultWithFilters(controllerContext, filters.ResultFilters, actionExecutedContext.Result);
    protected virtual IDictionary<string, object> GetParameterValues(ControllerContext controllerContext, ActionDescriptor actionDescriptor)
    {
        Dictionary<string, object> dictionary = new Dictionary<string, object>(StringComparer.OrdinalIgnoreCase);
        ParameterDescriptor[] parameters = actionDescriptor.GetParameters();
        ParameterDescriptor[] array = parameters;
        for (int i = 0; i < array.Length; i++)
        {
            ParameterDescriptor parameterDescriptor = array[i];
            dictionary[parameterDescriptor.ParameterName] = this.GetParameterValue(controllerContext, parameterDescriptor);
        }
        return dictionary;
    }
    protected virtual object GetParameterValue(ControllerContext controllerContext, ParameterDescriptor parameterDescriptor)
    {
        Type parameterType = parameterDescriptor.ParameterType;
        IModelBinder modelBinder = this.GetModelBinder(parameterDescriptor);
        IValueProvider valueProvider = controllerContext.Controller.ValueProvider;
        string modelName = parameterDescriptor.BindingInfo.Prefix ?? parameterDescriptor.ParameterName;
        Predicate<string> propertyFilter = ControllerActionInvoker.GetPropertyFilter(parameterDescriptor);
        ModelBindingContext bindingContext = new ModelBindingContext
        {
            FallbackToEmptyPrefix = parameterDescriptor.BindingInfo.Prefix == null,
            ModelMetadata = ModelMetadataProviders.Current.GetMetadataForType(null, parameterType),
            ModelName = modelName,
            ModelState = controllerContext.Controller.ViewData.ModelState,
            PropertyFilter = propertyFilter,
            ValueProvider = valueProvider
        };
        object obj = modelBinder.BindModel(controllerContext, bindingContext);
        return obj ?? parameterDescriptor.DefaultValue;
    }
    private IModelBinder GetModelBinder(ParameterDescriptor parameterDescriptor)
    {
    //action参数附带绑定信息了没?如果没有采用系统默认的方式进行绑定
    return parameterDescriptor.BindingInfo.Binder ?? this.Binders.GetBinder(parameterDescriptor.ParameterType); }
    private IModelBinder GetBinder(Type modelType, IModelBinder fallbackBinder)
    {
        IModelBinder modelBinder = this._modelBinderProviders.GetBinder(modelType);
        if (modelBinder != null)
        {
            return modelBinder;
        }
        if (this._innerDictionary.TryGetValue(modelType, out modelBinder))
        {
            return modelBinder;
        }
        modelBinder = ModelBinders.GetBinderFromAttributes(modelType, () => string.Format(CultureInfo.CurrentCulture, MvcResources.ModelBinderDictionary_MultipleAttributes, new object[]
        {
            modelType.FullName
        }));
        return modelBinder ?? fallbackBinder;
    }
    private static ModelBinderDictionary CreateDefaultBinderDictionary()
    {
        return new ModelBinderDictionary
        {
            
            {
                typeof(HttpPostedFileBase),
                new HttpPostedFileBaseModelBinder()
            },
            
            {
                typeof(byte[]),
                new ByteArrayModelBinder()
            },
            
            {
                typeof(Binary),
                new LinqBinaryModelBinder()
            },
            
            {
                typeof(CancellationToken),
                new CancellationTokenModelBinder()
            }
        };
    }

    下一篇: Action中的参数是怎么被赋值的

  • 相关阅读:
    iOS4.3可显著选拔iPhone4和iPad速度
    传iPhone5回归金属机身 形状似touch4
    联发科月度收入跌至四年来冰点
    品评:上海电信业不可被摩登数据蒙住双眼
    分析师以为移动搜集运营商需开发数据赚钱新途径
    智能手机市场输家和赢家:Android手机厥后居上
    人大代表张新建:减速互联网及短信拘留立法
    思科任命尝试副总裁加里摩尔出任首席运营官
    运营商纷繁筹建移动付出公司
    2011年中国3G移动通讯市场瞻望与分析
  • 原文地址:https://www.cnblogs.com/humble/p/3796003.html
Copyright © 2011-2022 走看看