ASP.NET MVC以ValueProvider為核心的值提供系統(tǒng): ValueProviderFactory
在ASP.NET Model綁定系統(tǒng)中,用于提供數(shù)據(jù)值的ValueProvider對(duì)象通過(guò)ValueProviderFactory來(lái)創(chuàng)建。在ASP.NET MVC應(yīng)用編程接口中,ValueProviderFactory繼承自ValueProviderFactory類。本篇文章只要介紹基于ValueProviderFactory的ValueProvider的提供機(jī)制,以及如何通過(guò)自定義ValueProviderFactory實(shí)現(xiàn)我們需要的數(shù)據(jù)值的綁定方式。[本文已經(jīng)同步到《How ASP.NET MVC Works?》中]
目錄
一、ValueProviderFactory
二、ValueProviderFactory的注冊(cè)
三、實(shí)例演示:創(chuàng)建一個(gè)自定義ValueProviderFactory
一、ValueProviderFactory
如下面的代碼片斷所示,ValueProviderFactory是一個(gè)抽象類,唯一的抽象方法GetValueProvider用于實(shí)現(xiàn)基于指定Controller上下文的ValueProvider創(chuàng)建。
1: public abstract class ValueProviderFactory
2: {
3: public abstract IValueProvider GetValueProvider(ControllerContext controllerContext);
4: }
下面的列表列出了定義在Model綁定系統(tǒng)中的6個(gè)原生的ValueProviderFactory:
- ChildActionValueProviderFactory:根據(jù)給定的Controller上下文創(chuàng)建一個(gè)ChildActionValueProvider對(duì)象。
- FormValueProviderFactory:根據(jù)給定的Controller上下文創(chuàng)建一個(gè)FormValueProvider對(duì)象。
- JsonValueProviderFactory:將以JSON形式表示的請(qǐng)求數(shù)據(jù)轉(zhuǎn)換成一個(gè)Dictionary<string, object>對(duì)象,并最終創(chuàng)建一個(gè)DictionaryValueProvider<object>對(duì)象。
- RouteDataValueProviderFactory:根據(jù)給定的Controller上下文創(chuàng)建一個(gè)RouteDataValueProvider對(duì)象。
- QueryStringValueProviderFactory:根據(jù)給定的Controller上下文創(chuàng)建一個(gè)QueryStringValueProvider對(duì)象。
- HttpFileCollectionValueProviderFactory:根據(jù)給定的Controller上下文創(chuàng)建一個(gè)HttpFileCollectionValueProvider對(duì)象。
二、ValueProviderFactory的注冊(cè)
ValueProviderFactory在ASP.NET MVC應(yīng)用中的注冊(cè)通過(guò)靜態(tài)類型ValueProviderFactories實(shí)現(xiàn)。如下面的代碼片斷所示,ValueProviderFactories具有一個(gè)靜態(tài)只讀屬性Factories返回一個(gè)表示ValueProviderFactory集合的ValueProviderFactoryCollection類型。
1: public static class ValueProviderFactories
2: {
3: public static ValueProviderFactoryCollection Factories { get; }
4: }
5:
6: public class ValueProviderFactoryCollection : Collection<ValueProviderFactory>
7: {
8: public ValueProviderFactoryCollection();
9: public ValueProviderFactoryCollection(IList<ValueProviderFactory> list);
10: public IValueProvider GetValueProvider(ControllerContext controllerContext);
11: }
ValueProviderFactoryCollection的GetValueProvider方法返回的是一個(gè)ValueProviderCollection對(duì)象,集合中的每個(gè)ValueProvider通過(guò)對(duì)應(yīng)的ValueProviderFactory來(lái)創(chuàng)建。ValueProviderFactory在ValueProviderFactoryCollection集合中的先后次序決定了創(chuàng)建的ValueProvider在ValueProviderCollection中的次序,而次序決定了使用優(yōu)先級(jí)。
在默認(rèn)的情況下ValueProviderFactories的Factories屬性表示的ValueProviderFactoryCollection包含了上面我們介紹的6種ValueProviderFactory,次序(優(yōu)先級(jí))為:ChildActionValueProviderFactory、FormValueProviderFactory、JsonValueProviderFactory、RouteDataValueProviderFactory、QueryStringValueProviderFactory和。如果具有相同的名稱的請(qǐng)求書去同時(shí)存在于請(qǐng)求表單和查詢字符串中,前者會(huì)被選用。
以ValueProvider為核心的值提供系統(tǒng)中涉及到了三類組件/類型,即用于具體實(shí)現(xiàn)數(shù)據(jù)值提供的ValueProvider,ValueProvider通過(guò)ValueProviderFactotry,而ValueProviderFactotry通過(guò)ValueProviderFactotries進(jìn)行注冊(cè)。圖5-4所示的UML體現(xiàn)了三者之間的關(guān)系。
三、實(shí)例演示:創(chuàng)建一個(gè)自定義ValueProviderFactory
ASP.NET MVC提供的6種ValueProviderFactory基本上已經(jīng)可以滿足我們絕大部分Model綁定需求,不過(guò)對(duì)于一些比較極端的場(chǎng)景,我們有可能需要自定義ValueProviderFactory。作為演示,我們創(chuàng)建一個(gè)以HTTP請(qǐng)求報(bào)頭集合作為數(shù)據(jù)源的自定義ValueProviderFactory。
我們將自定義的ValueProviderFactory命名為HttpHeaderValueProviderFactory。如下面的代碼片斷所示,HttpHeaderValueProviderFactory的定義非常簡(jiǎn)單,在重寫的GetValueProvider方法中,我們將針對(duì)指定的Controller上下文得到HTTP報(bào)頭集合,并借此創(chuàng)建NameValueCollection對(duì)象。由于作為報(bào)頭名稱具有“-”字符,為了與參數(shù)命名規(guī)則相匹配,我們將該字符剔除。最終創(chuàng)建的實(shí)際上是一個(gè)NameValueCollectionValueProvider對(duì)象。
1: public class HttpHeaderValueProviderFactory : ValueProviderFactory
2: {
3: public override IValueProvider GetValueProvider(ControllerContext controllerContext)
4: {
5: NameValueCollection requestData = new NameValueCollection();
6: var headers = controllerContext.RequestContext.HttpContext.Request.Headers;
7: foreach (string key in headers.Keys)
8: {
9: requestData.Add(key.Replace("-",""),headers[key]);
10: }
11: return new NameValueCollectionValueProvider(requestData, CultureInfo.InvariantCulture);
12: }
13: }
我們通過(guò)Visual Studio的ASP.NET MVC項(xiàng)目模板創(chuàng)建一個(gè)空Web應(yīng)用,并創(chuàng)建一個(gè)具有如下定義的HomeController。默認(rèn)的Action方法Index具有一系列的參數(shù),從參數(shù)名稱我們可以看出它們代表一些常用的HTTP報(bào)頭。我們最終將代表HTTP報(bào)頭的參數(shù)值呈現(xiàn)出來(lái)。
1: public class HomeController : Controller
2: {
3: public void Index(string connection, string accept, string acceptCharset, string acceptEncoding ,string acceptLanguage,
4: string host, string userAgent)
5: {
6: Response.Write(string.Format("{0}: {1}<br/>", "Connection", accept));
7: Response.Write(string.Format("{0}: {1}<br/>", "Accept-Charset", acceptCharset));
8: Response.Write(string.Format("{0}: {1}<br/>", "Accept Encoding", acceptEncoding));
9: Response.Write(string.Format("{0}: {1}<br/>", "Accept-Language", acceptLanguage));
10: Response.Write(string.Format("{0}: {1}<br/>", "Host", "host"));
11: Response.Write(string.Format("{0}: {1}<br/>", "User-Agent", userAgent));
12: }
13: }
然后利用Global.asax中按照如下的方式利用靜態(tài)類型對(duì)我們自定義的HttpHeaderValueProviderFactory進(jìn)行注冊(cè)。
1: public class MvcApplication : System.Web.HttpApplication
2: {
3: //其他成員
4: protected void Application_Start()
5: {
6: //其他操作
7: ValueProviderFactories.Factories.Add(new HttpHeaderValueProviderFactory());
8: }
9: }
當(dāng)我們運(yùn)行該程序的時(shí)候,會(huì)在瀏覽器中呈現(xiàn)如下的輸出結(jié)果,而輸出的結(jié)果正是當(dāng)前請(qǐng)求的HTTP報(bào)頭列表。
1: Connection: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
2: Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.3
3: Accept Encoding: gzip,deflate,sdch
4: Accept-Language: en-US,en;q=0.8
5: Host: host
6: User-Agent: Mozilla/5.0 (Windows NT 6.1) AppleWebKit/535.19 (KHTML, like Gecko) Chrome/18.0.1025.162 Safari/535.19
ASP.NET MVC以ValueProvider為核心的值提供系統(tǒng): NameValueCollectionValueProvider
ASP.NET MVC以ValueProvider為核心的值提供系統(tǒng): DictionaryValueProvider
ASP.NET MVC以ValueProvider為核心的值提供系統(tǒng): ValueProviderFactory


在ASP.NET Model綁定系統(tǒng)中,用于提供數(shù)據(jù)值的ValueProvider對(duì)象通過(guò)ValueProviderFactory來(lái)創(chuàng)建。在ASP.NET MVC應(yīng)用編程接口中,ValueProviderFactory繼承自ValueProviderFactory類。本篇文章只要介紹基于ValueProviderFactory的ValueProvider的提供機(jī)制,以及如何通過(guò)自定義ValueProviderFactory實(shí)現(xiàn)我們需要的數(shù)據(jù)值的綁定方式

浙公網(wǎng)安備 33010602011771號(hào)