一、题外话

上一篇:MVC中Action的执行过程

ControllerContext

封装有了与指定的 RouteBase 和 ControllerBase 实例匹配的 HTTP 请求的信息。

二、Model绑定者

2.1相关说明

http请求中的参数绑定到Model,是由实现了IModelBinder的类来完成的。我们称这样的类叫做Model绑定者

using System;
namespace System.Web.Mvc
{/// <summary>Defines the methods that are required for a model binder.</summary>public interface IModelBinder{/// <summary>Binds the model to a value by using the specified controller context and binding context.</summary>/// <returns>The bound value.</returns>/// <param name="controllerContext">The controller context.</param>/// <param name="bindingContext">The binding context.</param>object BindModel(ControllerContext controllerContext, ModelBindingContext bindingContext);}
}

2.2Model绑定者实现绑定的途径

1)直接在参数上绑定

using System;
using System.Web;
using System.Web.Mvc;namespace MVC_ST_2.Controllers
{public class Person{public string Name { get; set; }public int Age { get; set; }}public class PersonModelBinder : IModelBinder{public object BindModel(ControllerContext controllerContext, ModelBindingContext bindingContext){HttpRequestBase request = controllerContext.HttpContext.Request;var p = new Person();p.Name = request["Name"];p.Age =int.Parse( request["Age"]);return p;}}public class HomeController : Controller{//通过参数标记public ActionResult Index([ModelBinder(typeof(PersonModelBinder))] Person p){return View();}public ActionResult Index2(Person p){return View();}}
}

2)在model上加标记

    [ModelBinder(typeof(PersonModelBinder))] public class Person{public string Name { get; set; }public int Age { get; set; }}

3)ModelBinders.Binders中注册

protected void Application_Start(){ModelBinders.Binders[typeof(Person)] = new PersonModelBinder();
}

 

2.3 Action中是如何调用绑定者的?

以下是

private IModelBinder GetModelBinder(ParameterDescriptor parameterDescriptor)
{return parameterDescriptor.BindingInfo.Binder ?? this.Binders.GetBinder(parameterDescriptor.ParameterType);
}

说明:通过参数标记的方式优先,如果没有则使用this.Binders.GetBinder(parameterDescriptor.ParameterType);

this.Binders的定义

protected internal ModelBinderDictionary Binders
{get{if (this._binders == null){this._binders = ModelBinders.Binders;}return this._binders;}set{this._binders = value;}
}

从上图可以看出,最终的绑定操作交给了ModelBinderDictionary(注意了,下面会接着讲)

正好我们回到前两章讲的ControllerActionInvoker,其中的参数绑定赋值过程GetParameterValues,如何获取的过程即绑定的过程

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)
{return parameterDescriptor.BindingInfo.Binder ?? this.Binders.GetBinder(parameterDescriptor.ParameterType);
}

 this.Binders 其类型正好是ModelBinderDictionary(上面提到过),他的方法如下
    public IModelBinder GetBinder(Type modelType){return this.GetBinder(modelType, true);}/// <summary>Retrieves the model binder for the specified type or retrieves the default model binder.</summary>/// <returns>The model binder.</returns>/// <param name="modelType">The type of the model to retrieve.</param>/// <param name="fallbackToDefault">true to retrieve the default model binder.</param>/// <exception cref="T:System.ArgumentNullException">The <paramref name="modelType" /> parameter is null.</exception>public virtual IModelBinder GetBinder(Type modelType, bool fallbackToDefault){if (modelType == null){throw new ArgumentNullException("modelType");}return this.GetBinder(modelType, fallbackToDefault ? this.DefaultBinder : null);       //this.DefaultBinder 是下一章我们需要讲的内容。也是整个MVC核心的默认的绑定者}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;//DefaultBinder 很多情况下,前面的几个if都不会执行,所以使用系统默认的绑定者}

三、下一章接着介绍DefaultModelBinder

转载于:https://www.cnblogs.com/humble/p/3805565.html

MVC中Action参数绑定的过程相关推荐

  1. ASP.NET WebAPI 中的参数绑定

    当 WebAPI 调用 Controller 上的方法时, 必须为其参数赋值, 这个过程就是参数绑定. 本文介绍 WebAPI 如何绑定参数, 以及如何进行自定义. WebAPI 默认使用下面的规则进 ...

  2. 【SpringMVC学习05】SpringMVC中的参数绑定总结——较乱后期准备加入 同一篇幅他人的参数绑定...

    众所周知,springmvc是用来处理页面的一些请求,然后将数据再通过视图返回给用户的,前面的几篇博文中使用的都是静态数据,为了能快速入门springmvc,在这一篇博文中,我将总结一下springm ...

  3. asp.net中URL参数加密解密过程

    asp.net中URL参数加密解密过程 加密代码 public static string Encode(string str, string key){DESCryptoServiceProvide ...

  4. ASP.NET Web API中的参数绑定总结

    ASP.NET Web API中的action参数类型可以分为简单类型和复杂类型. HttpResponseMessage Put(int id, Product item) id是int类型,是简单 ...

  5. Asp.Net MVC中Action跳转小结

    https://www.cnblogs.com/surfing/p/3542826.html 首先我觉得action的跳转大致可以这样归一下类,跳转到同一控制器内的action和不同控制器内的acti ...

  6. MVC中Html.Partial, RenderPartial, Action,RenderAction 区别

    1.  Html.partial和RenderPartial的区别 Html.partial和RenderPartial都是输出html片段,区别在于: @Html.Partial用于将分部视图渲染为 ...

  7. MVC中@Html.Partial,@Html.Action,@Html.RenderPartial,@Html.RenderAction区别

    Html.RenderPartial与Html.RenderAction这两个方法都是用来在界面上嵌入用户控件的. 1. Html.RenderPartial是直接将用户控件嵌入到界面上: <% ...

  8. SpringMVC之Controller和参数绑定

    在上一篇Spring+SpringMVC+Mybatis整合中说到了SSM的整合,并且在其中添加了一个简单的查询功能,目的只是将整个整合的流程进行一个梳理,下面在上一篇中工程的基础上再说一些关于Spr ...

  9. springmvc(三) 参数绑定、

    前面两章就介绍了什么是springmvc,springmvc的框架原理,并且会简单的使用springmvc以及ssm的整合,从这一章节来看,就开始讲解springmvc的各种功能实现,慢慢消化 --W ...

  10. requestmapping里面的参数_golang web开发——参数绑定(上)之用Go实现简单的Trie

    背景 上一篇文章简单地介绍了使用golang如何完成内存中的增删改查,其实在实际工作中用处不是很大,旨在帮助大家了解一些golang的一些基本语法,和golang http包的基本使用,如何获取GET ...

最新文章

  1. mysql城市联动表怎么建_MVC4.0搭建的省市县三联动,包含数据库
  2. 《视频直播技术详解》之(四):编码和封装
  3. JS的自定义事件(观察者模式)
  4. win2008无法用计算机名共享,Windows Server 2008 R2中文件共享
  5. curl, apt-get, apt
  6. jsonpath学习链接
  7. 商友ERP系统---结算方面几项事宜
  8. 基于FPGA实践之呼吸灯(含程序)
  9. homework5_ZhankunLuo
  10. Xshell5连接服务器
  11. 轻松学网络设备之思科交换机搭建虚拟局域网
  12. 【vue】webapp移动端模板
  13. Linux远程访问的方法
  14. Regin恶意软件:何以潜伏如此久?
  15. 计算机输入d为啥返回桌面,按D键空格键就退出输入回到桌面
  16. 网络安全毕业设计选题题目大全
  17. MySQL最重要的日志-binlog详解
  18. wazuh agent功能详解
  19. 小鸡农场种植小游戏开发
  20. Spring Boot教程(十二)整合elk(1)

热门文章

  1. DNS在企业网络中的应用(一)
  2. (一)伤不起--java调用dll
  3. graphx 基础算法
  4. 卧槽!二维码要被扫完了吗?疫情期间竟用掉了1400亿个!
  5. 互联网创业公司残酷一幕:全员降薪,裁员凶猛与一夜解散
  6. 百亿级日访问量的应用如何做缓存架构设计?
  7. 一分钟了解微服务的好处和陷阱
  8. BAT 解密:一张图概括互联网公司的标准技术架构
  9. BGP超级失误:Verizon 搞垮 Cloudflare 和 AWS 等巨头,导致“连锁灾难性故障”
  10. 今天,强行打个广告!