快速啟動一個Java Web編程框架
RSF,不像其他的Java Web框架,主要側(cè)重于標記和網(wǎng)頁設計師的作用。網(wǎng)頁設計師不會被框架產(chǎn)生的標記而限制,也不是被迫圍繞內(nèi)嵌代碼或是偽代碼來設計。模板是純粹的XHTML不需要框架知識來創(chuàng)建或是維護。這個創(chuàng)建了完全分離的顯示和Java代碼隱藏。網(wǎng)頁設計師和開發(fā)者可以獨立工作,而且不需要協(xié)調(diào)他們的工作,這個你將在示例程序中看到。
RSF目的在于用零服務器環(huán)境創(chuàng)建一個框架,這樣可以通過在循環(huán)的***扔掉組件樹來節(jié)省寶貴的服務器資源。這個有別于很多常見的Java框架,例如JSF,憑借框架執(zhí)行的***個動作來恢復使用從先前要求中出現(xiàn)的組件樹。Session狀態(tài)是以此來減小較低利用的服務器資源。
RSF目的是通過遵循一個嚴格的POST->GET重定向以便保留所有的GET請求冪等來遵循在服務器上的正確而有效的瀏覽器行為。這樣,POST純粹是用來發(fā)送數(shù)據(jù)到服務器上的,而GET是用來返回數(shù)據(jù)到瀏覽器上的。這個可以解決很多問題,就是其他框架所面對的瀏覽器返回鈕行為或是深層鏈接問題。
Recipe List Application
為了演示這些RSF核心組件的主要目的,我們來構建一個非常簡單的recipe list應用程序。這個程序?qū)?chuàng)建一個項目列表,通過允許用戶通過網(wǎng)絡形式添加更多的項目。這個簡單的任務將展示很多的功能包括:模板建設,鏈接行為,簡單的國際化和表格粘貼。
為了開始這個簡單的程序,首先你需要為RSF準備好一個環(huán)境。RSF的wiki網(wǎng)站有一個很棒的指導來安裝RSF Development Environment,但是不在本文的討論之內(nèi)。一旦完成安裝,你可以通過在程序中創(chuàng)建XHTML模板來開始程序了。如上述所提到的,這些都是純粹的XHTML模板,用它們唯一所關心的外觀所建立的。對于這個簡單的程序,要有兩頁,所以你需要創(chuàng)建兩個XHTML模板:
recipelist.html
|
itemForm.html
|
正如以上所看到的,這些是幾乎完全有效的XHTML文件,除了額外的一個單一屬性,rsf:id=""。這個是RSF在模板中所代表的唯一機制。事實上,這些模板可以在任何網(wǎng)頁瀏覽器(是忽略額外屬性的瀏覽器)中看到并且可以被驗證。任何在模板中的文本或是其他的特性包括rsf:id屬性將通過RSF被覆蓋,所以模板可以包含如你所希望的"假數(shù)據(jù)"。這是極其有益的,通過允許假內(nèi)容的存在,讓設計者與開發(fā)者對標記結(jié)構的意圖進行溝通。恰當?shù)膔sf:id值列表是唯一的契約可以讓設計者和開發(fā)者必須互相維持。只要相同的ID以語義上相同的方法來運用,這個想法就會工作。
rsf:id標簽指定一個ID讓RSF rendering engine有地方連線它的數(shù)據(jù)。帶有冒號(:)的ID使用是一個特殊的協(xié)議就是告訴rendering engine這個XHTML節(jié)點可能會重復。為了支持國際化,另一個特殊的標簽協(xié)議是用于直接將文本從一個標準的Java屬性組合中提取出來。這個使得開發(fā)者通過簡單定義一個特殊的rsf:id="msg=property_key"直接連線rsf:id到一個properties bundle key 。對于這個應用程序,所有的頁面文本都被拖動到以下的屬性捆綁中。
messages.properties |
一旦你開始使用這些模板,你必須為每一個模板創(chuàng)建一個Component Producer。在RSF中的一個component producer是一種機制讓Java中組件樹可以在其中構建。每一個producer執(zhí)行ViewComponentProducer接口并且有一個相應的ViewID,可以與模板的文件名相匹配。重載方法fillComponents是組件樹構建的地方,用以在模板中符合rsf:ids。參數(shù)UIContainer tofill作為組件樹(這里可以添加所有的組件)的一個父元素。producer將為recipe list的項目構建組件樹,如下:
|
有了這個producer,一些主要的概念被采用了,還有一些RSF的內(nèi)置組件。上述的RecipeListService簡單的恢復了代表每個recipe list項目的字符串列表。以前,根據(jù)研究結(jié)果表明用于國際化的信息包文本可以直接通過模板來利用。但是,如果你需要做的不僅僅是輸出靜態(tài)文本,你可以選擇使用RSF的UIMessage組件來執(zhí)行包查找。這里,在從服務器檢索recipe項目的列表之后,你想要顯示項目的總數(shù),可以使用"current_items_count"信息包。使用UIMessage組件,你可以查找綁定的字符串"current_items_count",編排文本格式添加size()到一個占位符,并且附加它到帶有rsf:id="current_count"的DOM節(jié)點。
下一步是從服務器上顯示每個項目。如以上所提到的,當創(chuàng)建rsf:id屬性到designate(在DOM中重復的元素)的時候,你使用冒號標記。在模板中,你想要對每一個在recipe list上的項目重復一個< li>元素。要做到這一點, 把rsf:id="current_items:"(注意***的冒號) 給在模板中的元素。還有另一個注意的是顯示的分離。在Java中構建的組件樹不會關注使用哪些標記標簽;它只知道DOM元素是被重復的。通過設計者的自由裁量,< p>很容易用來代替< li>。為了創(chuàng)建匹配的組件樹項目,你可以創(chuàng)建一個UIBranchContainer組件。這個組件可以指示rendering engine,其中在DOM中項目被"綁定"允許循環(huán)的發(fā)生。每個反復的循環(huán)都要創(chuàng)建一個新的UIBranchContainer來告訴組件樹有多少個< li>DOM節(jié)點你需要去創(chuàng)建。
一旦你有了分支的< li>,你需要輸出文本項目。使用UIBranchContainer行作為一個父體(parent),你使用UIOutput來輸出recipe list項目的文本到DOM元素,用rsf:id="row_item"。通過設置父體到UIBranchContainer,你會使rsf:id="row_item"元素作為一個子rsf:id="row_item:"元素來呈現(xiàn)。
在producer中的***一步是創(chuàng)建一個內(nèi)部鏈接到itemform.html網(wǎng)頁。所有鏈接通過RSF來進行內(nèi)部管理。為了創(chuàng)建鏈接,附加組件樹上一個UIInternalLink組件到模板的rsf:id="add_item"上。既然你不以GET參數(shù)形式來傳送數(shù)據(jù),你可以利用RSF的SimpleViewParameters。但是,創(chuàng)建自定義的ViewParameters可以傳遞你希望的數(shù)據(jù),但是這超出了本程序的范圍。
下一個你創(chuàng)建的producer將構建組件樹來處理允許recipe項目被添加到列表上的表格:
|
這個簡單的producer構建了需要處理一個成功的POST的表格元素和滾條。首先,使用RFS組件UIForm添加一個表格組件到組件樹中,通過使用在模板中相同的rsf:id="form"。下一步,添加一個組件,UIInput,到UIForm 元素中,這個可以運行用戶可以接收的輸入。同樣的用UICommand組件來構建一個提交按鈕。UIInput 和UICommand組件同時采用一個第三方字符串參數(shù)來創(chuàng)建一個有價值的binding。這就是RFS的Expression Language的形成。這個要比在JSF中同樣的EL簡單得多,RSF的EL僅僅指定一個簡單的bean路徑。這樣,當按下提交按鈕時,在調(diào)用被UICommand value binding 定義的RecipeListBean.processActionSubmit()之前,在UIInput中的值被直接傳遞到RecipeListBean 的"item"屬性。
這個Producer的***一塊就是NavigationCaseReporter接口的執(zhí)行。記住RSF通過一個重定向的GET,遵循每個POST提交。默認情況下,GET請求會遵循來自它們的相同看法。為了重定向用戶到不同的地方,可以利用RSF的NavigationCases。Navigation cases被JSF的同樣的命名功能所激發(fā)并允許來自POST提交的簡單的流。在表格中,在成功的添加一個項目到列表中之后,你想重新定向recipe項目的列表。NavigationCase告訴RSF當POST綁定方法RecipeListBean.processActionSubmit的時候,返回字符串"success"然后GET 重定向需要返回RecipeListProducer。除了這個簡單的方法之外,RSF也允許其他更先進的創(chuàng)建流的方法。
RecipeListBean.java ... |
***一步包括添加eans到在web.xml中定義過的Spring定義中。這個遵循Spring框架的反向控制方法而且非常的直截了當。所有這些配置和整個源代碼提供,以供參考。雖然這個程序非常簡單平常,但是它強調(diào)了RSF的一些核心組件。
【編輯推薦】
【責任編輯:彭凡 TEL:(010)68476606】