[ASP.NET MVC] Model Binding With NameValueCollectionValueProvider

范例下载

范例程序代码:点此下载

问题情景

一般Web网站,都是以HTTP Request做为数据输入、HTTP Response做为数据输出,来完成一个网页要求响应的工作流程。

而ASP.NET MVC所建构的网站,在收到HTTP Request封包之后,会依照HTTP Request封包的Request URL内容,来选择对应的Controller以及Action,并且透过Model Binding机制来将HTTP Request封包剖析成为Action的函式参数。最后ASP.NET MVC会使用这些函式参数来执行Action函式,并且依照Action执行结果以及对应的View内容,来产生HTTP Response封包回传给浏览器,藉此完成HTTP Request输入、HTTP Response输出的工作流程。

本篇文章说明HTTP Request封包内容,如何被ASP.NET MVC的Model Binding机制使用,并且剖析成为Action的函式参数,为自己留个纪录也希望能帮助到有需要的开发人员。

数据源

HTTP Request封包内容,如何被ASP.NET MVC的Model Binding机制使用,并且剖析成为Action的函式参数;这一连串的工作流程,可以从用户点击浏览器页面中Sumit按钮来开始说明。

下列范例是一个HTML网页,这个网页中的Form窗体包含许多排版卷标、两个Text卷标以及一个 Submit标签。其中用来提供用户输入数据的两个Text卷标,名称分别为companyId及productId。

  1. <form action="/Receive/Echo_Multi_DataTypeArgument/" method="post">
  2. CompanyId : <input type="text" name="companyId" value="AAAAA" /><br />
  3. <br />
  4. ProductId : <input type="text" name="productId" value="BBBBB" /><br />
  5. <br />
  6. <input type="submit" value="Submit" />
  7. <br />
  8. </form>

当用户输入数据完毕之后,可使用鼠标点击页面上的Submit按钮,通知浏览器将Form窗体中的内容,封装成为HTTP Request封包来传送给Web服务器。

在这个阶段,浏览器会将Form窗体中输入卷标的卷标名称、卷标内容,以Name-Value的方式编码成为一个数据字符串。接着依照Form窗体上所定义的Method模式,来将这个数据字符串封装成为HTTP Request封包。

  1. companyId=AAAAA&productId=BBBBB
  • 当Method模式定义为Post的时候,浏览器会将HTTP Request封包的Content-Type内容定义为application/x-www-form-urlencoded,并且将数据字符串设定为HTTP Request封包的Form Data内容。

    1. <form action="/Receive/Echo_Multi_DataTypeArgument/" method="post">
    2. CompanyId : <input type="text" name="companyId" value="AAAAA" /><br />
    3. <br />
    4. ProductId : <input type="text" name="productId" value="BBBBB" /><br />
    5. <br />
    6. <input type="submit" value="Submit" />
    7. <br />
    8. </form>

  • 当Method模式定义为Get的时候,浏览器会将数据字符串设定为HTTP Request封包的Query String内容。

    1. <form action="/Receive/Echo_Multi_DataTypeArgument/" method="get">
    2. CompanyId : <input type="text" name="companyId" value="AAAAA" /><br />
    3. <br />
    4. ProductId : <input type="text" name="productId" value="BBBBB" /><br />
    5. <br />
    6. <input type="submit" value="Submit" />
    7. <br />
    8. </form>

服务器端的ASP.NET在收到HTTP Request封包之后,会撷取HTTP Request封包所定义的Form Data内容、Query String内容,以Name-Value的方式译码成为数据内容,并且使用这些数据内容建立为对应的NameValueCollection对象。

  • Form Data内容以Name-Value的方式译码成为数据内容之后,服务器端的ASP.NET会将数据内容建立为NameValueCollection对象,并且定义为System.Web.HttpContext.Current.Request.Form属性的内容。

  • Query String内容以Name-Value的方式译码成为数据内容之后,服务器端的ASP.NET会将数据内容建立为NameValueCollection对象,并且定义为System.Web.HttpContext.Current.Request.QueryString属性的内容。

而这两个NameValueCollection物件,在ASP.NET MVC中会被统一封装成为NameValueCollectionValueProvider对象,来做为Model Binding机制的数据源。

资料系结

在ASP.NET MVC中使用NameValueCollectionValueProvider对象,做为Model Binding机制的数据源时,会依照下列规则来剖析NameValueCollectionValueProvider所提供的Name-Value数据内容,并且生成对应的Action函式参数。(为了降低学习曲线,空白前缀、数组跳号...等等进阶规则暂先排除。)

单一值类型

当Action函式,包含一个值类型的函式参数时。Model Binding核心会依照这个函式参数的「参数名称」作为Key数据,来从NameValueCollectionValueProvider对象中取得对应的Value数据,并且尝试将Value资料转型为函式参数的「参数型别」,当成功转型之后就生成一个「函式参数」。后续ASP.NET MVC就会使用这个函式参数执行Action函式,并且完成接续的工作流程来产生HTTP Response封包回传给浏览器。

  1. <form action="/Receive/Echo_Single_DataTypeArgument/" method="post">
  2. CompanyId : <input type="text" name="companyId" value="AAAAA" /><br />
  3. <br />
  4. <input type="submit" value="Submit" />
  5. <br />
  6. </form>

多个值类型

当Action函式,包含多个值类型的函式参数时。Model Binding核心透过生成单一值类型的流程,依序生成每个对应「参数名称」的函式参数。后续ASP.NET MVC就会使用这些函式参数执行Action函式,并且完成接续的工作流程来产生HTTP Response封包回传给浏览器。

  1. <form action="/Receive/Echo_Multi_DataTypeArgument/" method="post">
  2. CompanyId : <input type="text" name="companyId" value="AAAAA" /><br />
  3. <br />
  4. ProductId : <input type="text" name="productId" value="BBBBB" /><br />
  5. <br />
  6. <input type="submit" value="Submit" />
  7. <br />
  8. </form>

值类型集合

当Action函式,包含值类型集合的函式参数时。Model Binding核心会依照这个函式参数的「参数名称」作为Prefix数据,来从NameValueCollectionValueProvider对象中取得所有符合「Prefix数据[索引]」格式的一组Key数据。接着Model Binding核心会先依照函式参数的「参数型别」建立一个集合,并且透过生成单一值类型的流程,依序生成每个对应「Key数据」的数据,来做为这个集合的项目。最后ASP.NET MVC就会使用这个集合作为函式参数来执行Action函式,并且完成接续的工作流程来产生HTTP Response封包回传给浏览器。

  1. <form action="/Receive/Echo_Array_DataTypeArgument/" method="post">
  2. CompanyIdArray[0] : <input type="text" name="companyIdArray[0]" value="AAAAA" /><br />
  3. CompanyIdArray[1] : <input type="text" name="companyIdArray[1]" value="BBBBB" /><br />
  4. <br />
  5. ProductIdArray[0] : <input type="text" name="productIdArray[0]" value="CCCCC" /><br />
  6. ProductIdArray[1] : <input type="text" name="productIdArray[1]" value="DDDDD" /><br />
  7. <br />
  8. <input type="submit" value="Submit" />
  9. <br />
  10. </form>

单一参考型别

当Action函式,包含一个参考型别的函式参数时。Model Binding核心会先依照函式参数的「参数型别」建立一个对象,并且依序将函式参数的「参数名称」、对象的「属性名称」,组合成为「参数名称.属性名称」格式的Key数据,接着透过生成单一值类型的流程,依序生成每个对应「Key数据」的对象属性。最后ASP.NET MVC就会使用这个对象作为函式参数来执行Action函式,并且完成接续的工作流程来产生HTTP Response封包回传给浏览器。

  1. <form action="/Receive/Echo_Single_ObjectTypeArgument/" method="post">
  2. Company.Id = <input type="text" name="company.Id" value="AAAAA" /><br />
  3. Company.Name = <input type="text" name="company.Name" value="BBBBB" /><br />
  4. Company.Address = <input type="text" name="company.Address" value="12345" /><br />
  5. <br />
  6. <input type="submit" value="Submit" />
  7. <br />
  8. </form>

多个参考型别

当Action函式,包含多个参考型别的函式参数时。Model Binding核心透过生成单一参考型别的流程,依序生成每个对应「参数名称」的函式参数。后续ASP.NET MVC就会使用这些函式参数执行Action函式,并且完成接续的工作流程来产生HTTP Response封包回传给浏览器。

  1. <form action="/Receive/Echo_Multi_ObjectTypeArgument/" method="post">
  2. Company.Id = <input type="text" name="company.Id" value="AAAAA" /><br />
  3. Company.Name = <input type="text" name="company.Name" value="BBBBB" /><br />
  4. Company.Address = <input type="text" name="company.Address" value="12345" /><br />
  5. <br />
  6. Product.Id = <input type="text" name="product.Id" value="CCCCC" /><br />
  7. Pproduct.Name = <input type="text" name="product.Name" value="DDDDD" /><br />
  8. Product.Price = <input type="text" name="product.Price" value="67890" /><br />
  9. <br />
  10. <input type="submit" value="Submit" />
  11. <br />
  12. </form>

参考型别集合

当Action函式,包含参考型别集合的函式参数时。Model Binding核心会依照这个函式参数的「参数名称」作为Prefix数据,来从NameValueCollectionValueProvider对象中取得所有符合「Prefix数据[索引]」格式的一组Key数据。接着Model Binding核心会先依照函式参数的「参数型别」建立一个集合,并且透过生成单一参考型别的流程,依序生成每个对应「Key数据」的数据,来做为这个集合的项目。最后ASP.NET MVC就会使用这个集合作为函式参数来执行Action函式,并且完成接续的工作流程来产生HTTP Response封包回传给浏览器。

  1. <form action="/Receive/Echo_Array_ObjectTypeArgument/" method="post">
  2. CompanyArray[0].Id = <input type="text" name="companyArray[0].Id" value="AAAAA" /><br />
  3. CompanyArray[0].Name = <input type="text" name="companyArray[0].Name" value="BBBBB" /><br />
  4. CompanyArray[0].Address = <input type="text" name="companyArray[0].Address" value="12345" /><br />
  5. CompanyArray[1].Id = <input type="text" name="companyArray[1].Id" value="CCCCC" /><br />
  6. CompanyArray[1].Name = <input type="text" name="companyArray[1].Name" value="DDDDD" /><br />
  7. CompanyArray[1].Address = <input type="text" name="companyArray[1].Address" value="67890" /><br />
  8. <br />
  9. ProductArray[0].Id = <input type="text" name="productArray[0].Id" value="EEEEE" /><br />
  10. ProductArray[0].Name = <input type="text" name="productArray[0].Name" value="FFFFF" /><br />
  11. ProductArray[0].Price = <input type="text" name="productArray[0].Price" value="54321" /><br />
  12. ProductArray[1].Id = <input type="text" name="productArray[1].Id" value="GGGGG" /><br />
  13. ProductArray[1].Name = <input type="text" name="productArray[1].Name" value="HHHHH" /><br />
  14. ProductArray[1].Price = <input type="text" name="productArray[1].Price" value="09876" /><br />
  15. <br />
  16. <input type="submit" value="Submit" />
  17. <br />
  18. </form>

多个混合型别

当Action函式,包含多个值类型、参考型别的函式参数时。Model Binding核心会依需透过生成单一值类型、生成单一参考型别的流程,依序生成每个对应「参数名称」的函式参数。后续ASP.NET MVC就会使用这些函式参数执行Action函式,并且完成接续的工作流程来产生HTTP Response封包回传给浏览器。

  1. <form action="/Receive/Echo_Multi_MixTypeArgument/" method="post">
  2. CompanyId : <input type="text" name="companyId" value="AAAAA" /><br />
  3. <br />
  4. Product.Id = <input type="text" name="product.Id" value="BBBBB" /><br />
  5. Product.Name = <input type="text" name="product.Name" value="CCCCC" /><br />
  6. Product.Price = <input type="text" name="product.Price" value="12345" /><br />
  7. <br />
  8. <input type="submit" value="Submit" />
  9. <br />
  10. </form>

混合型别集合

当Action函式,包含多个值类型集合、参考型别集合的函式参数时。Model Binding核心会依需透过生成值类型集合、生成参考型别集合的流程,依序生成每个对应「参数名称」的函式参数。后续ASP.NET MVC就会使用这些函式参数执行Action函式,并且完成接续的工作流程来产生HTTP Response封包回传给浏览器。

  1. <form action="/Receive/Echo_Array_MixTypeArgument/" method="post">
  2. CompanyIdArray[0] : <input type="text" name="companyIdArray[0]" value="AAAAA" /><br />
  3. CompanyIdArray[1] : <input type="text" name="companyIdArray[1]" value="BBBBB" /><br />
  4. <br />
  5. ProductArray[0].Id = <input type="text" name="productArray[0].Id" value="CCCCC" /><br />
  6. ProductArray[0].Name = <input type="text" name="productArray[0].Name" value="DDDDD" /><br />
  7. ProductArray[0].Price = <input type="text" name="productArray[0].Price" value="12345" /><br />
  8. ProductArray[1].Id = <input type="text" name="productArray[1].Id" value="EEEEE" /><br />
  9. ProductArray[1].Name = <input type="text" name="productArray[1].Name" value="FFFFF" /><br />
  10. ProductArray[1].Price = <input type="text" name="productArray[1].Price" value="67890" /><br />
  11. <br />
  12. <input type="submit" value="Submit" />
  13. <br />
  14. </form>

参考数据

[ASP.NET MVC] Model Binding With NameValueCollectionValueProvider的更多相关文章

  1. [置顶] ASP.NET MVC - Model Binding

    Http Request 到Input Model的绑定按照model的类型可分为四种情况. Primitive type Collection of primitive type Complex t ...

  2. ASP.NET MVC Model绑定(六)

    ASP.NET MVC Model绑定(六) 前言 前面的篇幅对于IValueProvider的使用做个基础的示例讲解,但是没并没有对 IValueProvider类型的实现做详细的介绍,然而MVC框 ...

  3. ASP.NET MVC Model绑定(五)

    ASP.NET MVC Model绑定(五) 前言 前面的篇幅对于IValueProvider的获取位置和所处的生成过程做了讲解,本篇将会对IValueProvider的使用做个基础的示例讲解,读完本 ...

  4. ASP.NET MVC Model绑定(四)

    ASP.NET MVC Model绑定(四) 前言 前面的篇幅对于Model绑定器IModelBinder以及实现类型.Model绑定器提供程序都作了粗略的讲解,可以把Model绑定器想象成一个大的容 ...

  5. ASP.NET MVC Model绑定(三)

    ASP.NET MVC Model绑定(三) 前言 看过前两篇的朋友想必对Model绑定有个大概的了解,然而MVC框架给我们提供了更高的可扩展性的提供程序编程模式,也就是本篇的主题了,会讲解一下Mod ...

  6. ASP.NET MVC Model绑定(二)

    ASP.NET MVC Model绑定(二) 前言 上篇对于Model绑定的简单演示想必大家对Model绑定的使用方式有一点的了解,那大家有没有想过Model绑定器是在什么时候执行的?又或是执行的过程 ...

  7. ASP.NET MVC Model绑定(一)

    ASP.NET MVC Model绑定(一) 前言 ModelMetadata系列的结束了,从本篇开始就进入Model绑定部分了,这个系列阅读过后你会对Model绑定有个比较清楚的了解, 本篇对于Mo ...

  8. ASP.NET MVC Model绑定

    ASP.NET MVC Model绑定(一) 前言 ModelMetadata系列的结束了,从本篇开始就进入Model绑定部分了,这个系列阅读过后你会对Model绑定有个比较清楚的了解, 本篇对于Mo ...

  9. ASP.NET MVC Model验证(五)

    ASP.NET MVC Model验证(五) 前言 上篇主要讲解ModelValidatorProvider 和ModelValidator两种类型的自定义实现, 然而在MVC框架中还给我们提供了其它 ...

随机推荐

  1. C#读取物理网卡信息及其对应的IP地址

    using Microsoft.Win32; using System; using System.Collections; using System.Collections.Generic; usi ...

  2. encfs创建时fuse: failed to exec fusermount: Permission denied错误解决

    今天用encfs创建加密文件夹时碰到提示错误fuse: failed to exec fusermount: Permission denied fuse failed. Common problem ...

  3. 用qt代码怎样编写图片保存格式[qt4.6]

    用qt代码怎样编写图片保存格式 qt提供了多个保存图片的接口,比较常用的接口如下 bool QPixmap::save ( const QString & fileName, const ch ...

  4. HDU 3487 Play with Chain(Splay)

    题目大意 给一个数列,初始时为 1, 2, 3, ..., n,现在有两种共 m 个操作 操作1. CUT a b c 表示把数列中第 a 个到第 b 个从原数列中删除得到一个新数列,并将它添加到新数 ...

  5. 2013年Linux周刊读者投票出炉 Ubuntu、Android榜上有名

    摘要:一年一度的Linux周刊读者投票结果已经登于2013第12期.这是Linux爱好者们自己的“奥斯卡”: Linux周刊的小编们列出一系列Linux相关的“最佳项目”进行面向读者的投票.竞选项目包 ...

  6. 安卓模拟器bluestack 换imei

    有好多种方法,下面介绍2种   第一种方法   通过靠谱助手设置,非常简单.   第二种方法   1.解压 root_20121221文件夹,将Root.fs 覆盖到 win7路径:C:\Progra ...

  7. 清除linux缓存命令

    命令 #sync #echo 3 > /proc/sys/vm/drop_caches 查看内存情况: # more /proc/meminfo Kernels 2.6.16 and newer ...

  8. 云计算之路-阿里云上:消灭“黑色n秒”第二招——给w3wp进程指定CPU核

    虽然昨天的第一招失败了,但是从失败中我们学到了与多核CPU相关的Processor Affinity(处理器关联)的知识. 既然我们可以让.NET程序的不同线程运行于指定的CPU核,那是不是也可以让I ...

  9. Testing - Selenium

    Selenium http://www.seleniumhq.org/ User Guide http://www.seleniumhq.org/docs/ Webdriver中文社区 http:// ...

  10. Linux - Yum的常用方法总结

    简述 rpm是由红帽公司开发的软件包管理方式,使用rpm可以方便的进行软件的安装.查询.卸载.升级等工作. 但是rpm软件包之间的依赖性问题往往会很繁琐,尤其是软件由多个rpm包组成时. Yum(全称 ...