ASP.NETWeb應用程序的簡單AJAX實現
提要 本文描述了使用一種簡單的方式來實現在ASP.NET web應用程序中加入AJAX功能。
一、 簡介
本文描述了一種簡單的方式來實現在ASP.NET web應用程序中加入AJAX功能。我們還將討論使用AJAX的優缺點。為了說明問題,本文還提供了一些可用的JavaScript和C#.NET代碼。
二、 為什么使用AJAX
大多數讀者可能已經知道,AJAX代表了異步JavaScript+XML。這種技術首先由微軟在1999年引入,并以"使用遠程調用的DHTML/JavaScript web應用程序"著稱。這一技術的基本思想是,允許一個互聯網瀏覽器向一個遠程頁面/服務作異步的HTTP調用,并且用收到的結果更新一個當前web頁面而不必刷新整個頁面。根據這種技術創建者的意見,這種技術應能夠改進客戶端的體驗-使得HTTP頁面外觀與使用感覺很類似于Windows桌面應用程序。
因為這種技術的核心實現是基于互聯網瀏覽器功能,所以其用途在當時是很有限的。但是,幾年過去了,隨著新一代瀏覽器的支持和大量的應用實踐(例如Google,Amazon.com,eBay等),這種技術已經重新煥發生機。
今天,它以AJAX著名,被作為任何提供高級用戶體驗的動態頁面的自然的構成部分。
三、 方案描述
在本文中我們所推薦的方案盡管很簡單,然而卻十分有效地實現了AJAX功能。這個程序很容易維護和修改,不要求開發者具備任何特別的技巧;而且,根據我們的經驗,它還是跨瀏覽器兼容的。
基本上,一個常規的類似AJAX的實現包括兩個主要組成部分:一個使用JavaScript代碼進行AJAX調用并接收響應的客戶端HTML頁面;一個遠程頁面-它能夠接收一個請求并對請求的信息加以響應。在客戶端頁面中的JavaScript代碼負責實例化一個XmlHttp對象,然后提供給這個對象一個回調方法-它負責處理收到的信息,最后把請求經由XmlHttp對象發送到遠程頁面。所有這些都是通過JavaScript代碼來實現的。
我們的方法主要是針對于ASP.NET應用程序中的應用,并且考慮下列可能的情形:
· AJAX調用可以發生于web應用程序的不同的ASP.NET頁面上甚至是遠程頁面上;
· 一遠程頁面URL可能包含動態計算的參數,并且可能在ASP.NET頁面的code-behind處構建一個URL字符串更為方便些;
· 在更新一個HTML頁面之前,一個遠程頁面可能響應于一個復雜的數據分析要求;
· 一遠程頁面可能或者是一個外部的第三方頁面,或者是該Web應用程序自己的頁面或服務。
所有的這些考慮都顯示在下圖中:
四、 實現
(一) 基本AJAX JavaScript方法
我把所有的JavaScript方法分成兩部分:調用頁面特定的JavaScript方法,和通用于所有調用頁面的AJAX JavaScript方法。特定的方法還包括一個回調函數,由于它負責更新頁面內容。通用的AJAX方法負責實例化一個XmlHttp對象并向遠程頁面發送異步請求。
得到一個XmlHttp對象的過程因瀏覽器的不同而有所不同。我把它們區分為兩種不同的基本類型:微軟瀏覽器(IE家族之一)和Mozilla瀏覽器(它是指Mozilla Firefox,Netscape,或Safari之一)。我還在Opera瀏覽器上測試了本文中的代碼,但是我不可能保證它會一直工作良好。
如你所見,GetXmlHttpObject方法接受一個處理器參數-它是一個應該在頁面特定的代碼定義的回調方法的名字。現在,既然我們已經有了一個XmlHttp對象,那么我們就可以發送異步的請求了。
我使用一個指向一個給定URL的GET HTTP方法,但是這可以通過修改上面的JS代碼加以改變。
(二) 頁面特定的方法
現在,我們已經建立起實現一個到遠程頁面調用的所有方法。為此,我們需要把回調函數名傳遞給GetXmlHttpObject方法,然后把URL串傳遞給SendXmlHttpRequest方法。
CallbackMethod負責更新頁面內容。在我們的示例中,它只是簡單地更新給定HTTP元素的內部HTML。但是,在實際開發中,它可能更為復雜些。
有關于調用頁面實現的最后一個問題是,我們如何調用ExecuteCall JS方法。其實,這依賴于這個頁面正在做什么。在一些情況中,ExecuteCall方法在JS事件被激發時被調用。但是,如果情況不是這樣,我們可以把這個方法注冊為這個頁面的一個啟動腳本-使用在該頁面的code-behind中的相應的C#代碼。
我們可以把這一行代碼添加到ASP.NET code-behind文件的Page_Prerender或Page_Load方法中。
(三) 遠程頁面
下面,讓我們分析一下過程頁面看起來的樣子。如果這是一個ASP.NET頁面(我們假定如此),那么我們僅對它的code-behind感興趣。我們可以很容易地從這個.aspx文件中移去所有代碼:它不會以任何方式影響這個頁面的行為。
例如,我們使用一個公共的web服務-它能夠把溫度值從攝氏轉換為華氏(以及相反的實現)。此處提供了一個這樣的可用的服務。如果你把這個URL作為一個web引用添加到你的工程中,那么Visual Studio將在你的當前的命名空間中生成一個名為com.developerdays.ITempConverterservice的代理類。我們的遠程ASP.NET頁面(假設命名為getTemp.aspx),將接收一個查詢串參數(名為"temp")-它應該包含一個要轉換的攝氏溫度的整型值。所以,到遠程頁面的目標URL看上去類似于:http://localhost/getTemp.aspx?temp=25。下面顯示了這個頁面的code-behind:
根據我們的慣例,現在我們可以為將傳遞到RegisterStartupScript方法中的遠程頁面構建一個URL字符串,象下面這樣:
使用這種方法并結合一個中間ASP.NET頁面調用允許簡化響應處理,特別是在請求分析的時候。在簡單的情況中,當響應僅包含文本數據時,我們可以把遠程服務URL直接傳遞給JS ExecuteCall方法。
五、結論
本文意在向你展示把AJAX技術使用于任何ASP.NET應用程序的簡單性。然而,AJAX也有一些缺點,從用戶體驗角度來看,它也提供了一些優點。這完全要由開發者來決定是否使用AJAX技術,但是我在本文中僅向你展示了簡單的情形,它不需要花費很長時間且不需要任何特定技巧。
一、 簡介
本文描述了一種簡單的方式來實現在ASP.NET web應用程序中加入AJAX功能。我們還將討論使用AJAX的優缺點。為了說明問題,本文還提供了一些可用的JavaScript和C#.NET代碼。
二、 為什么使用AJAX
大多數讀者可能已經知道,AJAX代表了異步JavaScript+XML。這種技術首先由微軟在1999年引入,并以"使用遠程調用的DHTML/JavaScript web應用程序"著稱。這一技術的基本思想是,允許一個互聯網瀏覽器向一個遠程頁面/服務作異步的HTTP調用,并且用收到的結果更新一個當前web頁面而不必刷新整個頁面。根據這種技術創建者的意見,這種技術應能夠改進客戶端的體驗-使得HTTP頁面外觀與使用感覺很類似于Windows桌面應用程序。
因為這種技術的核心實現是基于互聯網瀏覽器功能,所以其用途在當時是很有限的。但是,幾年過去了,隨著新一代瀏覽器的支持和大量的應用實踐(例如Google,Amazon.com,eBay等),這種技術已經重新煥發生機。
今天,它以AJAX著名,被作為任何提供高級用戶體驗的動態頁面的自然的構成部分。
三、 方案描述
在本文中我們所推薦的方案盡管很簡單,然而卻十分有效地實現了AJAX功能。這個程序很容易維護和修改,不要求開發者具備任何特別的技巧;而且,根據我們的經驗,它還是跨瀏覽器兼容的。
基本上,一個常規的類似AJAX的實現包括兩個主要組成部分:一個使用JavaScript代碼進行AJAX調用并接收響應的客戶端HTML頁面;一個遠程頁面-它能夠接收一個請求并對請求的信息加以響應。在客戶端頁面中的JavaScript代碼負責實例化一個XmlHttp對象,然后提供給這個對象一個回調方法-它負責處理收到的信息,最后把請求經由XmlHttp對象發送到遠程頁面。所有這些都是通過JavaScript代碼來實現的。
我們的方法主要是針對于ASP.NET應用程序中的應用,并且考慮下列可能的情形:
· AJAX調用可以發生于web應用程序的不同的ASP.NET頁面上甚至是遠程頁面上;
· 一遠程頁面URL可能包含動態計算的參數,并且可能在ASP.NET頁面的code-behind處構建一個URL字符串更為方便些;
· 在更新一個HTML頁面之前,一個遠程頁面可能響應于一個復雜的數據分析要求;
· 一遠程頁面可能或者是一個外部的第三方頁面,或者是該Web應用程序自己的頁面或服務。
所有的這些考慮都顯示在下圖中:
![]() |
四、 實現
(一) 基本AJAX JavaScript方法
我把所有的JavaScript方法分成兩部分:調用頁面特定的JavaScript方法,和通用于所有調用頁面的AJAX JavaScript方法。特定的方法還包括一個回調函數,由于它負責更新頁面內容。通用的AJAX方法負責實例化一個XmlHttp對象并向遠程頁面發送異步請求。
得到一個XmlHttp對象的過程因瀏覽器的不同而有所不同。我把它們區分為兩種不同的基本類型:微軟瀏覽器(IE家族之一)和Mozilla瀏覽器(它是指Mozilla Firefox,Netscape,或Safari之一)。我還在Opera瀏覽器上測試了本文中的代碼,但是我不可能保證它會一直工作良好。
| function GetXmlHttpObject(handler){ var objXmlHttp = null; if (!window.XMLHttpRequest) { //微軟 objXmlHttp = GetMSXmlHttp(); if (objXmlHttp != null) { objXmlHttp.onreadystatechange = handler; } } else { // Mozilla | Netscape|Safari objXmlHttp = new XMLHttpRequest(); if (objXmlHttp != null) { objXmlHttp.onload = handler; objXmlHttp.onerror = handler; } } return objXmlHttp; } function GetMSXmlHttp(){ var xmlHttp = null; var clsids = ["Msxml2.XMLHTTP.6.0","Msxml2.XMLHTTP.5.0", "Msxml2.XMLHTTP.4.0","Msxml2.XMLHTTP.3.0", "Msxml2.XMLHTTP.2.6","Microsoft.XMLHTTP.1.0", "Microsoft.XMLHTTP.1","Microsoft.XMLHTTP"]; for(var i=0; i<clsids.length && xmlHttp == null; i++) { xmlHttp = CreateXmlHttp(clsids[i]); } return xmlHttp; } function CreateXmlHttp(clsid) { var xmlHttp = null; try { xmlHttp = new ActiveXObject(clsid); lastclsid = clsid; return xmlHttp; } catch(e) {} } |
如你所見,GetXmlHttpObject方法接受一個處理器參數-它是一個應該在頁面特定的代碼定義的回調方法的名字。現在,既然我們已經有了一個XmlHttp對象,那么我們就可以發送異步的請求了。
| function SendXmlHttpRequest(xmlhttp, url) { xmlhttp.open('GET', url, true); xmlhttp.send(null); } |
我使用一個指向一個給定URL的GET HTTP方法,但是這可以通過修改上面的JS代碼加以改變。
(二) 頁面特定的方法
現在,我們已經建立起實現一個到遠程頁面調用的所有方法。為此,我們需要把回調函數名傳遞給GetXmlHttpObject方法,然后把URL串傳遞給SendXmlHttpRequest方法。
| var xmlHttp; function ExecuteCall(url){ try { xmlHttp = GetXmlHttpObject(CallbackMethod); SendXmlHttpRequest(xmlHttp, url); } catch(e){} } //當狀態改變時(例如收到數據時),CallbackMethod將激發 function CallbackMethod() { try { //readyState=4 或'complete' 代表了數據已經返回 if (xmlHttp.readyState == 4 || xmlHttp.readyState == 'complete') { var response = xmlHttp.responseText; if (response.length > 0) { //更新頁面 document.getElementById("elementId").innerHTML= response; } } } catch(e){} } |
CallbackMethod負責更新頁面內容。在我們的示例中,它只是簡單地更新給定HTTP元素的內部HTML。但是,在實際開發中,它可能更為復雜些。
有關于調用頁面實現的最后一個問題是,我們如何調用ExecuteCall JS方法。其實,這依賴于這個頁面正在做什么。在一些情況中,ExecuteCall方法在JS事件被激發時被調用。但是,如果情況不是這樣,我們可以把這個方法注冊為這個頁面的一個啟動腳本-使用在該頁面的code-behind中的相應的C#代碼。
| Page.RegisterStartupScript("ajaxMethod", String.Format("<script>ExecuteCall('{0}');</script>", url)); |
我們可以把這一行代碼添加到ASP.NET code-behind文件的Page_Prerender或Page_Load方法中。
(三) 遠程頁面
下面,讓我們分析一下過程頁面看起來的樣子。如果這是一個ASP.NET頁面(我們假定如此),那么我們僅對它的code-behind感興趣。我們可以很容易地從這個.aspx文件中移去所有代碼:它不會以任何方式影響這個頁面的行為。
例如,我們使用一個公共的web服務-它能夠把溫度值從攝氏轉換為華氏(以及相反的實現)。此處提供了一個這樣的可用的服務。如果你把這個URL作為一個web引用添加到你的工程中,那么Visual Studio將在你的當前的命名空間中生成一個名為com.developerdays.ITempConverterservice的代理類。我們的遠程ASP.NET頁面(假設命名為getTemp.aspx),將接收一個查詢串參數(名為"temp")-它應該包含一個要轉換的攝氏溫度的整型值。所以,到遠程頁面的目標URL看上去類似于:http://localhost/getTemp.aspx?temp=25。下面顯示了這個頁面的code-behind:
| private void Page_Load(object sender, EventArgs e){ Response.Clear(); string temp = Request.QueryString["temp"]; if (temp != null) { try { int tempC = int.Parse(temp); string tempF = getTempF(tempC); Response.Write(tempF); } catch { } } Response.End(); } private string getTempF(int tempC){ com.developerdays.ITempConverterservice svc = new ITempConverterservice(); int tempF = svc.CtoF(tempC); return tempF.ToString(); } |
根據我們的慣例,現在我們可以為將傳遞到RegisterStartupScript方法中的遠程頁面構建一個URL字符串,象下面這樣:
| int tempC = 25; string url=String.Format("http://localhost/"+"getTemp.aspx?temp={0}", tempC); |
使用這種方法并結合一個中間ASP.NET頁面調用允許簡化響應處理,特別是在請求分析的時候。在簡單的情況中,當響應僅包含文本數據時,我們可以把遠程服務URL直接傳遞給JS ExecuteCall方法。
五、結論
本文意在向你展示把AJAX技術使用于任何ASP.NET應用程序的簡單性。然而,AJAX也有一些缺點,從用戶體驗角度來看,它也提供了一些優點。這完全要由開發者來決定是否使用AJAX技術,但是我在本文中僅向你展示了簡單的情形,它不需要花費很長時間且不需要任何特定技巧。
