本文是關(guān)于使用 web 服務(wù)的 — 簡(jiǎn)單服務(wù)和 RESTful web 服務(wù) — 使用 Dojo Toolkit。為了更好地理解本文,您需要在您的系統(tǒng)進(jìn)行以下安裝和配置:
- 一個(gè)文本編輯器或集成開發(fā)環(huán)境(IDE)
(本文使用 Eclipse JavaScript IDE。) - 一個(gè) web 服務(wù)器
Dojo Toolkit 概述
隨著人們對(duì)構(gòu)建更好的 Rich Internet Applications (RIAs) 的關(guān)注。JavaScript 架構(gòu)的出現(xiàn)使得 web 開發(fā)人員可以將它們的應(yīng)用程序開發(fā)得更具吸引力。
預(yù)先包裝的 JavaScript 庫(kù)擁有諸多優(yōu)點(diǎn)。第一,使用在不同瀏覽器和不同平臺(tái)上驗(yàn)證過的代碼可以極大地減少在許多不同瀏覽器上驗(yàn)證功能需要的測(cè)試次數(shù),因而也減少了代碼中缺陷。第二,使用已編寫且測(cè)試的代碼節(jié)省了大量時(shí)間,使您可以更快地完成您的應(yīng)用程序。
Ajax 概述
Ajax 是一個(gè)用來描述一個(gè)組合技術(shù)的術(shù)語,在加載用戶 web 頁(yè)面時(shí)用來調(diào)用(異步)服務(wù)器。這項(xiàng)技術(shù)在今天的 web 頁(yè)中無處不在,在提供豐富的 Web 體驗(yàn)方面起著重要的作用。
在本文的示例中,每一次用戶只要修改文本框中的文本內(nèi)容,JavaScript 代碼都會(huì)進(jìn)行一個(gè)服務(wù)器調(diào)用來獲取參考值。一方面,這個(gè)附加函數(shù)將產(chǎn)生一些流量。另一方面,如果用戶通過提交整個(gè)表單進(jìn)行重復(fù)的搜索,該技術(shù)將節(jié)省很多流量。
回頁(yè)首 創(chuàng)建項(xiàng)目
本例使用最新版 Eclipse 以及已安裝的 JavaScript 工具。這些工具提供改進(jìn)功能來編輯 JavaScript 和 HTML 頁(yè)面。
根據(jù)下面步驟創(chuàng)建一個(gè)項(xiàng)目,然后利用這個(gè)項(xiàng)目創(chuàng)建幾個(gè) HTML 文件,來完成這個(gè)示例:
-
使用 File > New > Project 創(chuàng)建一個(gè)新的靜態(tài) web 項(xiàng)目。
-
選擇 Web\Static Web Project 并單擊 Next.
-
輸入您的項(xiàng)目名稱(例如,MyDojoExample )。
-
單擊 New Runtime。
-
從列表中選擇 New Server,然后選擇 Create a new local server 復(fù)選框。
-
根據(jù)服務(wù)器列表中顯示輸入服務(wù)器名稱,然后輸入您想要發(fā)布文件的目錄名。通常,這應(yīng)該是一個(gè)目錄位置,您可以在其中發(fā)布用戶的 web 文件。
-
在 Static Web Project 向?qū)е袉螕?Next。
-
讓上下文根路徑同項(xiàng)目名稱保持一致,并將 web 目錄文件夾命名為 WebContent。
-
單擊 Finish。Eclipse 為您創(chuàng)建了新項(xiàng)目。
當(dāng)您向您的項(xiàng)目添加文件時(shí),Eclipse 自動(dòng)將文件發(fā)布到為服務(wù)器配置的目錄下。您可以通過在該項(xiàng)目中創(chuàng)建您的第一個(gè) HTML 文件(是一個(gè) index.html 文件)來了解這些,您需要修改該文件來包含實(shí)例所用的搜索框。
按照以下步驟創(chuàng)建新 HTML 文件:
- 在您的新項(xiàng)目中選擇 WebContent 文件夾,然后用備用鼠標(biāo)按鈕打開上下文菜單。
- 從菜單中選擇 New > HTML file。
- 在 File name 字段輸入文件名,然后單擊 Next 來查看 HTML 模板選擇器。
- 對(duì)于這個(gè)示例,選擇 New XHTML File (1.0 strict) 選項(xiàng),然后單擊 Finish 按鈕。
新文件看起來像清單 1 這樣。
清單1. 新 index.html 文件
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www./TR/xhtml1/DTD/xhtml1-strict.dtd"> <html xmlns="http://www./1999/xhtml"> <head> <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" /> <title>Insert title here</title> </head> <body>
</body> </html>
|
現(xiàn)在,您已經(jīng)有一個(gè)靜態(tài) web 項(xiàng)目和一個(gè) HTML 頁(yè)了,是時(shí)候向 HTML 頁(yè)中添加一個(gè)輸入控件了。HTML 文件包含一些 div 標(biāo)記,定位輸入控件并使建議選項(xiàng)容易些。結(jié)果生成清單 2 所示的 HTML 文件。
清單 2. 有控件的 index.html 文件
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www./TR/xhtml1/DTD/xhtml1-strict.dtd"> <html xmlns="http://www./1999/xhtml"> <head> <title>Test web page</title> <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" /> <link rel="stylesheet" type="text/css" href="styles/main.css" /> </head> <body> <div id="wrapper"> <form> <div id="search"><input id="searchBox" type="text" maxlength="2048" name="criteria" title="Search" onkeyup="update()" /></div> <div id="suggestions"></div> </form> </div> </body> </html>
|
在這一點(diǎn)上,與空白版本有很大的區(qū)別。大部分工作可以通過使用 web 頁(yè)中的 JavaScript 代碼完成。
回頁(yè)首 包含 Dojo Toolkit
您可以以兩種方式包含 Dojo Toolkit:
- 使用一個(gè)公開托管(publicly hosted)的 Dojo 文件位置。
- 自己下載 Dojo Toolkit JavaScript 文件然后同您的代碼一并包含在其中。
哪個(gè)方法更好取決于您的需求。
使用一個(gè)公開托管文件
使用公開托管文件有兩個(gè)很好的理由:
- 使用一個(gè)內(nèi)容分發(fā)網(wǎng)絡(luò)(CDN)來簡(jiǎn)單地托管文件,對(duì)您來說減少了本地跟蹤文件的需求。
- 您可以少部署一個(gè)文件。
使用一個(gè)公開托管的文件主要優(yōu)勢(shì)是,如果 CDN 不可用(這種情況未必會(huì)發(fā)生,但是也有可能)您將不需要任何控件。如果由于某種原因 CDN
關(guān)閉了,您的網(wǎng)站也就不起作用了。如果您的內(nèi)部 web 應(yīng)用程序需要確保運(yùn)行正常,考慮維護(hù) Dojo 腳本文件來減少您應(yīng)用程序的單點(diǎn)故障。
要從一個(gè) CDN 中鏈接 Dojo 文件系統(tǒng),修改您的 index.html 文件使其看起來如清單 3 所示。
清單 3. 包含到 Dojo CDN 位置的鏈接
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www./TR/xhtml1/DTD/xhtml1-strict.dtd"> <html xmlns="http://www./1999/xhtml"> <head> <title>Test web page</title> <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" /> <link rel="stylesheet" type="text/css" href="styles/main.css" /> <script src="http://ajax./ajax/libs/dojo/1.5/dojo/dojo.xd.js" type="text/javascript"></script> </head> <!-- snipped... --> </html>
|
下載和包含 Dojo Toolkit 基本文件
如果您想下載和包含 Dojo Toolkit 基本文件,而不是鏈接它,您可以從 參考資料 中鏈接的網(wǎng)站下載 Dojo JavaScript 代碼。下載完這個(gè)文件之后,您可以使用 File > Import 將其導(dǎo)入到 Eclipse 中的項(xiàng)目中。按照慣例,通常創(chuàng)建一個(gè)名為 js 或 script 的文件夾比較好,您不僅可以將您的 JavaScript 代碼放在其中,也可以將您下載的文件放在其中。
為了將您下載的文件包含到您的 Web 頁(yè),像這樣修改 index.html,如清單 4 所示。
清單 4. 包含一個(gè)本地引用到已下載的 dojo.js
<script src="js/dojo.js" type="text/javascript"></script>
|
現(xiàn)在您有了一個(gè)基本 web 頁(yè),您要準(zhǔn)備添加更多的功能,通過添加調(diào)用服務(wù)的 JavaScript 代碼來完成。
回頁(yè)首 調(diào)用一個(gè)服務(wù)
現(xiàn)在您已經(jīng)創(chuàng)建了 index.html 文件,并將 Dojo JavaScript 文件鏈接到您的 index.html 文件了,是時(shí)候調(diào)用一個(gè)簡(jiǎn)單服務(wù),來為用戶提供建議選項(xiàng)了。
本文提供兩個(gè)不同的調(diào)用服務(wù)和得到結(jié)果的示例。第一個(gè)是一個(gè)簡(jiǎn)單的服務(wù),不一定要符合常見 RESTful web 服務(wù) URL 習(xí)慣。REST
不是一個(gè)標(biāo)準(zhǔn),但是有很多方法可以巧妙地獲取 URL,為客戶端和 RESTful web 服務(wù)提供一個(gè)較好的互操作性。第二個(gè)實(shí)例是一個(gè)使用
dojox.rpc.Rest 方法的介紹。
使用一個(gè)簡(jiǎn)單服務(wù)
因?yàn)閬碜苑?wù)的響應(yīng)根據(jù)查詢字符串進(jìn)行改變,服務(wù)不需要您以一個(gè)動(dòng)態(tài) web 應(yīng)用程序技術(shù)寫入其中(參考 參考資料,了解更多關(guān)于動(dòng)態(tài) web 應(yīng)用程序的信息)。清單 5 中顯示的是一個(gè)簡(jiǎn)單的 PHP 腳本,有一個(gè)名稱數(shù)組。根據(jù)用戶所提供的,從名稱列表中過濾出來,然后將它們添加到 Extensible Markup Language (XML) 響應(yīng)。
清單 5. 使用 PHP 編寫一個(gè)簡(jiǎn)單的服務(wù)
<?php header("Content-type: text/xml");
$data = array( "Bilbo Baggins", "Frodo Baggins", "Samwise (Sam) Gamgee", "Meriadoc (Merry) Brandybuck", "Peregrin (Pippin) Took");
$resultXML = ''; $resultsXML .= '<suggestions>';
foreach ($data as $d) { $pattern = '/'.$_GET['s'].'/'; if (preg_match($pattern, $d)) { $resultsXML .= '<item>'.$d.'</item>'; } }
$resultsXML .= '</suggestions>';
print($resultsXML);
|
您可以以其他任何語言編寫一個(gè)簡(jiǎn)單的腳本,返回一個(gè)類似的響應(yīng)來測(cè)試 JavaScript 代碼。
從 Dojo Toolkit 調(diào)用 URL 并不是很容易。如清單 6 所示簡(jiǎn)單地設(shè)置參數(shù)進(jìn)行調(diào)用,然后將它們傳遞到服務(wù)。
清單 6. 為 dojo.xhrGet 設(shè)置參數(shù)
var args = { url:"mockService.php?s=" + dojo.byId("searchBox").value, handleAs:"xml", preventCache:true, load:function(data) { // handle the data... }, error:function(error) { target.innerHTML = "Error:" + error; }
|
這些參數(shù)將在表 1 中進(jìn)一步說明。
表 1. dojo.xhrGet 參數(shù)
參數(shù) | 說明 |
---|
url | 此參數(shù)包括 URL(記住,這個(gè) URL 不是一個(gè) RESTful URL)。 | handleAs | json、text 或 xml 之一。PHP 腳本使用 XML 響應(yīng),所以用在這里。 | preventCache | 如果您不想緩存數(shù)據(jù),使用 ture。緩存數(shù)據(jù)可以執(zhí)行得更快,但是,如果結(jié)果是完全自動(dòng)化的,這也不可取。 | load | 該回調(diào)函數(shù)在服務(wù)返回?cái)?shù)據(jù)時(shí)執(zhí)行。 | error | 該回調(diào)函數(shù)在出現(xiàn)錯(cuò)誤時(shí)執(zhí)行。 |
如果已經(jīng)正確設(shè)置了參數(shù),將它們傳遞到 dojo.xhrGet 方法。全部代碼如清單 7 所示。
清單 7. 全部 JavaScript 代碼
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www./TR/xhtml1/DTD/xhtml1-strict.dtd"> <html xmlns="http://www./1999/xhtml"> <head> <title>Test web page</title> <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" /> <link rel="stylesheet" type="text/css" href="styles/main.css" /> <script src="http://ajax./ajax/libs/dojo/1.5/dojo/dojo.xd.js" type="text/javascript"></script> <script type="text/javascript"> //<![CDATA[ // You could move all this code to a JavaScript file and include it... dojo.require("dojox.xml.parser"); function update() {
if (dojo.byId("searchBox").value.length < 3 ) return; var target = dojo.byId("suggestions");
var args = { url:"mockService.php?s=" + dojo.byId("searchBox").value, handleAs:"xml", preventCache:true, load:function(data) { // handle the data... }, error:function(error) { target.innerHTML = "Error:" + error; } }; var ajaxCall = dojo.xhrGet(args); } //]]> </script> </head> <body> <div id="wrapper"> <form> <div id="search"><input id="searchBox" type="text" maxlength="2048" name="criteria" title="Search" onkeyup="update()" /></div> <div id="suggestions"></div> </form> </div> </body> </html>
|
除了調(diào)用標(biāo)準(zhǔn) Ajax 風(fēng)格服務(wù)之外,您也要使用 Dojo Toolkit 調(diào)用 RESTful web 服務(wù)。
使用一個(gè) RESTful 服務(wù)
除了用于發(fā)送請(qǐng)求的 HTTP 方法之外,大部分 RESTful web 服務(wù)的 URL 構(gòu)建方式都遵守為特定類型請(qǐng)求構(gòu)建 URL
的方式。如果您構(gòu)建一個(gè)符合這些傳統(tǒng)習(xí)慣的 RESTful 服務(wù),您可以使用 dojo.rpc.Rest
對(duì)象為您進(jìn)行調(diào)用。dojo.rpc.Rest 對(duì)象進(jìn)一步簡(jiǎn)化了傳統(tǒng)服務(wù)調(diào)用。
清單 8 是一個(gè)使用 Dojo Toolkit 調(diào)用 RESTful web 服務(wù)的示例。
清單 8. 使用 dojo.rpc.Rest 調(diào)用一個(gè) RESTful web 服務(wù)
// Calling this access the URL hobbits/1 (see Table 2) var service = dojox.rpc.Rest("hobbits"); service("1");
|
表 2 列出了固有的 RESTful URL 和 HTTP 動(dòng)作的示例,應(yīng)該同每個(gè)類型的服務(wù)相匹配。注意,不是每一個(gè)瀏覽器都支持所有 HTTP 方法,因此您應(yīng)該根據(jù)您的需要進(jìn)行測(cè)試和驗(yàn)證,對(duì)于多數(shù)用戶,使用 GET 和 POST 方法可能是最佳選擇。
表 2. RESTful 傳統(tǒng) URL
動(dòng)作 | HTTP 方法 | 示例 URL |
---|
查找一個(gè)對(duì)象 | GET | http://www./hobbits/1 | 查找所有對(duì)象 | GET | http://www./hobbits/ | 刪除一個(gè)對(duì)象 | DELETE | http://www./hobbits/1 | 創(chuàng)建一個(gè)對(duì)象 | POST | http://www./hobbits/ | 更新一個(gè)新對(duì)象 | PUT | http://www./hobbits/1 |
如果您想創(chuàng)建一個(gè) RESTful web 服務(wù)的全部實(shí)現(xiàn),框架有助于指導(dǎo)您構(gòu)建符合 RESTful URL 習(xí)慣的 URL。參見 參考資料,尋找不同語言的各種框架的更多信息。
回頁(yè)首 精確地顯示結(jié)果
既然您將要使用 Dojo 代碼調(diào)用服務(wù),您也可以更新 div 元素的內(nèi)容來包含查詢結(jié)果。這使得用戶可以根據(jù)其類型查看建議選項(xiàng)。
想要更新包含建議選項(xiàng)的 div 元素的值,使用 dojo.byId 方法通過 ID 獲取 div 的參考資料,并如清單 9 所示設(shè)置 innerHTML 屬性。dojo.byId 方法是傳統(tǒng) JavaScript 的 document.getElementById 方法的別名。
清單 9. 更新元素的內(nèi)容
// the full load function... load:function(data) { var rootEl = data.documentElement; var resultHTML = "<ul>"; for (var i = 0; i < rootEl.childNodes.length;i++) { resultHTML += "<li>" + dojox.xml.parser.textContent(rootEl.childNodes[i]) + "</li>"; } resultHTML+="</ul>"; target.innerHTML = resultHTML; },
|
現(xiàn)在,您的代碼已經(jīng)可以正常運(yùn)行了,您可以在瀏覽器中查看您的 index.html 頁(yè)。當(dāng)您輸入一個(gè)值時(shí) — 例如 Bag
— 建議選項(xiàng)將自動(dòng)出現(xiàn)在您的 div 元素中。盡管本文并不能涵蓋全部的,您也應(yīng)該使用 Cascading Style Sheets (CSS) 使這些 div 整齊地排列在下拉框中,根據(jù)用戶的輸入提供建議選項(xiàng)。
回頁(yè)首 處理長(zhǎng)期運(yùn)行的服務(wù)
當(dāng)從一個(gè) web 瀏覽器處理長(zhǎng)期運(yùn)行服務(wù)時(shí),主要關(guān)注兩方面的問題:
用戶體驗(yàn)
在服務(wù)執(zhí)行時(shí),如果在瀏覽器中沒有明顯的改變,用戶體驗(yàn)將受長(zhǎng)期運(yùn)行服務(wù)的影響。如果您的 web 頁(yè)含有一個(gè)按鈕,可以進(jìn)行一個(gè) Ajax 或
RESTful
服務(wù)調(diào)用或者顯示結(jié)果,您應(yīng)該利用這些瀏覽器來顯示用戶即將發(fā)生的事情。否則您將要冒這樣的風(fēng)險(xiǎn),一個(gè)用戶多次提交表單或者您將對(duì)網(wǎng)站很不耐煩甚至離開。
為了應(yīng)對(duì)用戶體驗(yàn)問題,使用一個(gè)動(dòng)畫(Dojo Toolkit 有針對(duì)這些的方法)或者禁用提交按鈕,使用戶不能多次提交。有了動(dòng)畫視覺(例如,旋轉(zhuǎn)時(shí)鐘)
,用戶可以意識(shí)到將要發(fā)生什么,更愿意等待進(jìn)程完成。
可靠性
期待長(zhǎng)期運(yùn)行的服務(wù)來使用 Ajax 調(diào)用可能有問題,但是它們可能是有效的示例。長(zhǎng)期運(yùn)行服務(wù)的示例是那些聚集數(shù)據(jù)、生成文檔或者存檔文件示例。
在這種情況下,簡(jiǎn)單調(diào)用服務(wù)并等待 — 特別是如果服務(wù)要運(yùn)行好幾秒,不是一個(gè)最佳實(shí)踐。如果您的連接是混亂的,或者您的瀏覽器關(guān)閉了,那么在服務(wù)完成時(shí),您將不能依賴回調(diào)機(jī)制來觸發(fā)。
如果您可以控制服務(wù),可以考慮向您的調(diào)用者返回一個(gè)惟一的限定符,使用一種后來向不同服務(wù)詢問請(qǐng)求狀態(tài)的方式。您的瀏覽器可以將這些數(shù)字放到本地的一個(gè) cookie 存儲(chǔ)設(shè)備中,也可以讓瀏覽器和服務(wù)一起來保存用戶數(shù)量。
調(diào)用服務(wù)的這種方法允許您在服務(wù)器端開始長(zhǎng)期運(yùn)行的進(jìn)程。在瀏覽器端,您可以對(duì)請(qǐng)求狀態(tài)使用輪詢來訪問服務(wù)層。(您可以對(duì)此使用 Dojo Toolkit's Timer 對(duì)象),該方法為用戶提供靈活性和穩(wěn)定性。
回頁(yè)首 結(jié)束語
除此之外,Dojo Toolkit 使您可以在您的 web 應(yīng)用程序中進(jìn)行 Ajax
調(diào)用,來提供 RIA 函數(shù)。不管是使用一個(gè) CDN 或者是您自己下載 Dojo Toolkit 文件,您都可以利用預(yù)先寫入的且已測(cè)試的函數(shù)的優(yōu)勢(shì)。
Dojo Toolkit 使用 Ajax 和 RESTful web 服務(wù)提供調(diào)用純 web 服務(wù)的方法。這個(gè)工具包允許您處理 JSON、XML 和來自 Ajax 服務(wù)的文本響應(yīng)。
參考資料 學(xué)習(xí) 獲得產(chǎn)品和技術(shù) 討論
|