




版權說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權,請進行舉報或認領
文檔簡介
如何開始用DWR有兩種方法開始DWR,簡單的方式是下載WAR文件然后看看。但是這不能幫你知道如何輕松的把DWR整合到你的web應用中,所以還是推薦你按照下面的3個步驟做:1.安裝DWR的Jar包\o"VisitpageoutsideConfluence"下載dwr.jar文件。把它放到你的webapp的WEB-INF/lib目錄下。那里可能已經(jīng)有很多其他的jar文件了。2.編輯配置文件需要把下面的代碼加到WEB-INF/web.xml文件中。<servlet>那部分需要和其他的<servlet>在一起,<servlet-mapping>部分也一樣。<servlet><servlet-name>dwr-invoker</servlet-name><display-name>DWRServlet</display-name><servlet-class>uk.ltd.getahead.dwr.DWRServlet</servlet-class><init-param><param-name>debug</param-name><param-value>true</param-value></init-param></servlet><servlet-mapping><servlet-name>dwr-invoker</servlet-name><url-pattern>/dwr/*</url-pattern></servlet-mapping>在WEB-INF目錄下的web.xml旁邊創(chuàng)建一個dwr.xml文件。可以從最簡單的配置開始:<!DOCTYPEdwrPUBLIC"-//GetAheadLimited//DTDDirectWebRemoting1.0//EN""http://www.getahead.ltd.uk/dwr/dwr10.dtd"><dwr><allow><createcreator="new"javascript="JDate"><paramname="class"value="java.util.Date"/></create><createcreator="new"javascript="Demo"><paramname="class"value="your.java.Bean"/></create></allow></dwr>DWR配置文件定義了那些DWR會創(chuàng)建提供遠程調(diào)用的Javascript類。在上面的例子中我們定義了兩個類來提供遠程調(diào)用,并為其提供的Javascript類的名字。在上面我們使用了new創(chuàng)建器,它會調(diào)用沒有參數(shù)的構造函數(shù)來創(chuàng)建實例,但是所有JavaBean必須有這一構造函數(shù)。還要注意DWR有一些限制:不要出現(xiàn)Javascript保留關鍵字;和保留關鍵字同名的函數(shù)指定被排除。多數(shù)Javascript的關鍵字和Java是相同的。所以你不可能有一個方法叫做"try()"。但是該死"delete()"對與Javascript有著特殊意義,而對Java則不是。Javascript方法重載是不支持的,所以盡量不要再Java中使用。3.訪問下面的URLhttp://localhost:8080/[YOUR-WEBAPP]/dwr/你可以看見一個頁面,里面有第二步中的類。接著往里點,你會看到所有可以調(diào)用的方法列表。這個頁面是動態(tài)生成用來測試的例子。自己動手試一下!怎么在你的web應用中使用在文檔中有很多例子演示如何動態(tài)更改頁面中的文字、更新列表、操作表單,還有直接更改table中的內(nèi)容。每一個都有如何實現(xiàn)的介紹。另一種方式是看剛才的頁面中提供的代碼:到http://localhost:8080/\[YOUR-WEBAPP\]/dwr/頁面,點擊你的類。查看源碼,找到執(zhí)行方法的那幾行,把那些文字粘貼到你的HTML或JSP中。要包括下面這些能產(chǎn)生神奇效果的Javascript文件的鏈接。<scriptsrc='/[YOUR-WEBAPP]/dwr/interface/[YOUR-SCRIPT].js'></script><scriptsrc='/[YOUR-WEBAPP]/dwr/engine.js'></script>你也可以把其中/[YOUR-WEBAPP]/替換成你的web頁面的相對路徑。DWR根據(jù)dwr.xml生成和Java代碼類似的Javascript代碼。相對而言Java同步調(diào)用,創(chuàng)建與Java代碼匹配的Ajax遠程調(diào)用接口的最大挑戰(zhàn)來至與實現(xiàn)Ajax的異步調(diào)用特性。DWR通過引入回調(diào)函數(shù)來解決這個問題,當結果被返回時,DWR會調(diào)用這個函數(shù)。有兩種推薦的方式來使用DWR實現(xiàn)遠程方法調(diào)用。可以通過把回調(diào)函數(shù)放在參數(shù)列表里,也可以把回調(diào)函數(shù)放到元數(shù)據(jù)對象里。當然也可以把回調(diào)函數(shù)做為第一個參數(shù),但是不建議使用這種方法。因為這種方法在處理\o"AccessingServletObjects"自動處理http對象時(查看"AlternativeMethod")上會有問題。這個方法主要是為向下兼容而存在的。簡單的回調(diào)函數(shù)假設你有一個這樣的Java方法:publicclassRemote{publicStringgetData(intindex){...}}我們可以在Javascript中這樣使用:<scripttype="text/javascript"src="[WEBAPP]/dwr/interface/Remote.js"></script><scripttype="text/javascript"src="[WEBAPP]/dwr/engine.js"></script>...functionhandleGetData(str){alert(str);}Remote.getData(42,handleGetData);42是Java方法getData()的一個參數(shù)。此外你也可以使用這種減縮格式:Remote.getData(42,function(str){alert(str);});調(diào)用元數(shù)據(jù)對象(Meta-Data)另外一種語法時使用"調(diào)用元數(shù)據(jù)對象"來指定回調(diào)函數(shù)和其他的選項。上面的例子可以寫成這樣:Remote.getData(42,{callback:function(str){alert(str);}});這種方法有很多優(yōu)點:易于閱讀,更重要的指定額外的調(diào)用選項。超時和錯誤處理在回調(diào)函數(shù)的元數(shù)據(jù)中你可以指定超時和錯誤的處理方式。例如:Remote.getData(42,{callback:function(str){alert(str);},timeout:5000,errorHandler:function(message){alert("Oops:"+message);}});查找回調(diào)函數(shù)有些情況下我們很難區(qū)分各種回調(diào)選項(記住,Javascript是不支持函數(shù)重載的)。例如:Remote.method({timeout:3},{errorHandler:somefunc});這兩個參數(shù)之一是bean的參數(shù),另一個是元數(shù)據(jù)對象,但是我們不能清楚的告訴DWR哪個是哪個。為了可以跨瀏覽器,我們假定null==undefined。所以當前的情況,規(guī)則是:如果第一個或最后一個是一個函數(shù),那么它就是回調(diào)函數(shù),沒有元數(shù)據(jù)對象,并且其他參數(shù)都是Java的方法參數(shù)。另外,如果最后一個參數(shù)是一個對象,這個對象中有一個callback成員,并且它是個函數(shù),那么這個對象就是元數(shù)據(jù)對象,其他的都是Java方法參數(shù)。另外,如果第一個參數(shù)是null,我們就假設沒有回調(diào)函數(shù),并且其他的都是Java方法參數(shù)。盡管如此,我們會檢查最后一個參數(shù)是不是null,如果是就發(fā)出警告。最后如果最后一個參數(shù)是null,那么就沒有callback函數(shù)。另外,發(fā)出錯誤信號是個糟糕的請求格式。創(chuàng)造一個與Java對象匹配的Javascript對象假設你有這樣的Java方法:publicclassRemote{publicvoidsetPerson(Personp){this.person=p;}}Person對象的結構是這樣的:publicPerson{privateStringname;privateintage;privateDate[]appointments;//gettersandsetters...}那么你可以在Javascript中這樣寫:varp={name:"FredBloggs",age:42,appointments:[newDate(),newDate("1Jan2008")]};Remote.setPerson(p);在Javascript沒有出現(xiàn)的字段,在Java中就不會被設置。因為setter都是返回'void',我們就不需要使用callback函數(shù)了。如果你想要一個返回void的服務端方法的完整版,你也可以加上callback函數(shù)。很明顯DWR不會向它傳遞任何參數(shù)。TransformerFactoryConfigurationError這個問題的現(xiàn)象是在啟動有DWR的Web應用時出現(xiàn)如下stacktrace:rootcausejavax.xml.transform.TransformerFactoryConfigurationError:Providercessor.TransformerFactoryImplnotfoundjavax.xml.transform.TransformerFactory.newInstance(UnknownSource)這個問題和DWR沒有什么關系,那是因為Tomcat沒有配置好。比較簡單的解決辦法是下載Xalan替換掉$TOMCAT-HOME/common/lib目錄下的xalan.jar文件。DWR2.0能更好的處理這個問題,但是本質(zhì)的問題還是因為DWR的XML序列化需要有XSLT解析器的支持。如果你用JDK5還是有這個問題的話,你可以增加以下VM參數(shù)來使Tomcat正常工作。-Djavax.xml.transform.TransformerFactory=ernal.xsltc.trax.TransformerFactoryImplXML解析錯誤在剛開始用DWR的時候經(jīng)常遇到的一個錯誤就是XML解析錯誤。其實這和DWR沒有多大關系,主要是因為Tomcat里面自帶的Xerces的問題,要不是該有的時候沒有,要不是不該有的時候有了。JDK1.3自身沒有XML解析器,所以你需要xercesImpl.jar和xml-apis.jar.JDK1.4.0和JDK1.4.1雖然有了XML解析器,但是有很多bug,所以你還是需要把xercesImpl.jar放到tomcat\common\endorsed目錄下。JDK1.4.2和JDK5自帶的XML解析器工作的很好,你就不需要再加其他的了。
另外要提的一點是,不同版本的Tomcat需要的XML解析器不一樣。所以要注意檢查它和JDK的版本兼容性。用BEAWeblogic的Classpath問題Weblogic8.1(有可能其他版本同樣)可能找不到DWR的類。這大多出現(xiàn)在dwr.jar放在APP-INF目錄下(APP_INF/lib)的情況。在這種情況下DWR依然可以工作,例如debug頁面可以看見,但是DWR找不到你的類。解決辦法是把dwr.jar放到WEB-INF/lib目錄下。沒有cookies的情況下用DWR當不能用cookies時,servlet規(guī)范通過URL重寫來支持HttpSession。DWR2.x通過它生成的URL來支持這項功能。但是DWR1.x沒有這個功能。你可以通過以下辦法讓DWR1.x也支持cookies:從dwr.jar中提取engine.js,保存到你的文件系統(tǒng)中,就像jsp文件一樣.修改"DWREngine._sendData=function(batch)"方法,加入一行:statsInfo+=";jsessionid="+<%="'"+session.getId()+"'"%>這樣就可以讓DWR1.x支持url重寫了。DWR2+默認支持。傳遞額外的數(shù)據(jù)到callback函數(shù)通常我們需要傳遞額外的數(shù)據(jù)到callback函數(shù),但是因為所有的回調(diào)函數(shù)都只有一個參數(shù)(遠程方法的返回結果),這就需要一些小技巧了。解決方案就是使用Javascript的\o"VisitpageoutsideConfluence"閉包特性。例如,你的回調(diào)函數(shù)原本需要像這個樣子:functioncallbackFunc(dataFromServer,dataFromBrowser){//用dataFromServer和dataFromBrowser做些事情}那么你可以像這個組織你的函數(shù):vardataFromBrowser=...;//定義一個閉包函數(shù)來存儲dataFromBrowser的引用,并調(diào)用dataFromServervarcallbackProxy=function(dataFromServer){callbackFunc(dataFromServer,dataFromBrowser);};varcallMetaData={callback:callbackProxy};Remote.method(params,callMetaData);(調(diào)用元數(shù)據(jù)在\o"ScriptingIntroduction"腳本介紹中有解釋)換句話說,現(xiàn)在你作為callback函數(shù)傳遞過來的不是一個真正的callback,他只是一個做為代理的閉包,用來傳遞客戶端的數(shù)據(jù)。你可以用更簡介的形式:vardataFromBrowser=...;Remote.method(params,{callback:function(dataFromServer){callbackFunc(dataFromServer,dataFromBrowser);}});服務器性能優(yōu)化CPU瓶頸:經(jīng)過嚴格的測試DWR的性能沒什么問題。DWR上性能消耗同web服務器和網(wǎng)絡比起來可以忽略不計。如果你真的需要提升DWR的性能的話,可以把log級別設置ERROR或FATAL,但是主要還是要看你的編碼情況。Network瓶頸:DWR沒有管理你的瀏覽器緩存的功能,所以它會不斷的重復讀取DWR的javascript文件。這里有一個簡單的解決辦法,把javascript文件復制到你的web-app中,這樣web服務器就可以更好的利用它了。你也可以考慮把所有的javascript文件合并成一個文件,然后用\o"VisitpageoutsideConfluence"DOJO的壓縮程序處理一個來節(jié)省流量。我們可以做一個補丁,讓DWR在web-app啟動的時候用時間做為javascript文件的時間戳,但是這個并不十分重要,因為上面的補丁太簡單了而且可以壓縮合并Javascript文件。WEB-INF/web.xml參考手冊在web.xml中最簡單的配置就是簡單加入DWR的servlet,沒有這個配置DWR就不會起作用:<servlet><servlet-name>dwr-invoker</servlet-name><servlet-class>uk.ltd.getahead.dwr.DWRServlet</servlet-class></servlet><servlet-mapping><servlet-name>dwr-invoker</servlet-name><url-pattern>/dwr/*</url-pattern></servlet-mapping>此外還可以加入一些重要和有用的參數(shù)。LoggingDWR可以工作在JDK1.3上,而JDK1.3不支持java.util.logging,但是我們想強迫任何人使用commons-logging或者log4j,所以當沒有l(wèi)ogging類的時候DWR就使用HttpServlet.log()方法。盡管如此,如果DWR發(fā)現(xiàn)了commons-logging,就是使用它。Commons-Logging幾乎每一個人都在使用\o"VisitpageoutsideConfluence"commons-logging,因為大多數(shù)的servlet容器在使用它。所以如果你的web應用中沒有明顯的加入commons-logging包,它也會默認的配置好。在這種情況下,logging是由\o"VisitpageoutsideConfluence"java.util.logging或者\o"VisitpageoutsideConfluence"log4j配置文件控制的。詳細配置查看文檔。HttpServlet.log()如果你用HttpServlet.log(),下面的配置控制logging:<init-param><param-name>logLevel</param-name><param-value>DEBUG</param-value></init-param>可用的值有:FATAL,ERROR,WARN(默認),INFO和DEBUG。多個dwr.xml文件和J2EE安全一般來說,你只需要一個dwr.xml文件,并且放置在默認的位置:WEB-INF/dwr.xml。如果那樣的話,你可以不用了解下面的配置。有三個原因使你希望指定不同位置的dwr.xml文件。你希望讓dwr.xml文件和它能訪問到的資源在一起。在這種情況下你需要一個這樣的配置:<param-value>WEB-INF/classes/com/yourco/dwr/dwr.xml</param-value>。你有大量的遠程調(diào)用類,希望把他們分成多個文件。在這種情況下你需要重復下面的配置幾次,每一個中有不同的param-name,并且以'config'開頭。DWR會依次把他們都讀進來。DWR可以使用Servlet規(guī)范的J2EE的URL安全機制來給不同的用戶不同的訪問權限。你只需要簡單的定義多個dwrservlet,并且制定不同的名字,url和訪問權限。如果你希望使用這一功能,那么語法是這樣的:<init-param><param-name>config*****</param-name><param-value>WEB-INF/dwr.xml</param-value><description>Whatconfigfiledoweuse?</description></init-param>在這里config*****意思是param-name要以字符串config開頭。這個參數(shù)可以根據(jù)需要使用多次,但是不能相同。一個使用J2EE的安全機制的例子:<servlet><servlet-name>dwr-user-invoker</servlet-name><servlet-class>uk.ltd.getahead.dwr.DWRServlet</servlet-class><init-param><param-name>config-user</param-name><param-value>WEB-INF/dwr-user.xml</param-value></init-param></servlet><servlet><servlet-name>dwr-admin-invoker</servlet-name><servlet-class>uk.ltd.getahead.dwr.DWRServlet</servlet-class><init-param><param-name>config-admin</param-name><param-value>WEB-INF/dwr-admin.xml</param-value></init-param></servlet><servlet-mapping><servlet-name>dwr-admin-invoker</servlet-name><url-pattern>/dwradmin/*</url-pattern></servlet-mapping><servlet-mapping><servlet-name>dwr-user-invoker</servlet-name><url-pattern>/dwruser/*</url-pattern></servlet-mapping><security-constraint><display-name>dwr-admin</display-name><web-resource-collection><web-resource-name>dwr-admin-collection</web-resource-name><url-pattern>/dwradmin/*</url-pattern></web-resource-collection><auth-constraint><role-name>admin</role-name></auth-constraint></security-constraint><security-constraint><display-name>dwr-user</display-name><web-resource-collection><web-resource-name>dwr-user-collection</web-resource-name><url-pattern>/dwruser/*</url-pattern></web-resource-collection><auth-constraint><role-name>user</role-name></auth-constraint></security-constraint>使用插件(Plug-in)DWR里的很多部件都是可插入的,所以可以通過替換掉DWR的默認實現(xiàn)類來改變其功能。你可以在<init-param>中的param-name中指定你要替換的接口,并在param-value中指定自己的接口實現(xiàn)類。可插入點是:uk.ltd.getahead.dwr.AccessControluk.ltd.getahead.dwr.Configurationuk.ltd.getahead.dwr.ConverterManageruk.ltd.getahead.dwr.CreatorManageruk.ltd.getahead.dwr.Processoruk.ltd.getahead.dwr.ExecutionContext這些可插入點默認的實現(xiàn)都在uk.ltd.getahead.dwr.impl中。使用debug/test模式你可以通過下面的參數(shù)讓DWR進入debug/test模式:<init-param><param-name>debug</param-name><param-value>true</param-value></init-param>在debug模式里,DWR會為每一個遠程調(diào)用類生成一個測試頁面。這對于檢查DWR是否工作和工作的怎么樣是很有用的。這個模式還可以警告你一些存在的問題:javascript保留字問題,或者函數(shù)重載問題。盡管如此,這個模式不應該使用在實際部署環(huán)境里面,因為它可以為攻擊者提供你的服務的大量信息。如果你的網(wǎng)站設計的好的話,這些信息不會幫助攻擊者窺視你的網(wǎng)站內(nèi)容,但是還是不要給任何人一個找到你錯誤的機會好。DWR就是照上面的樣子做的,沒有任何保證,所以你的網(wǎng)站的安全是你的責任。請小心。配置DWR-dwr.xmldwr.xml是DWR的配置文件。默認情況下,應該把它放到WEB-INF目錄(web.xml的目錄)下。DTD這里還有一個dwr.xml對應的\o"VisitpageoutsideConfluence"DTD文檔以及一個用\o"VisitpageoutsideConfluence"DTDDoc生成的\o"VisitpageoutsideConfluence"參考手冊。創(chuàng)建dwr.xml文件dwr.xml文件的結構如下:<!DOCTYPEdwrPUBLIC"-//GetAheadLimited//DTDDirectWebRemoting1.0//EN""http://www.getahead.ltd.uk/dwr/dwr10.dtd"><dwr><!--initisonlyneededifyouareextendingDWR--><init><creatorid="..."class="..."/><converterid="..."class="..."/></init><!--withoutallow,DWRisn'tallowedtodoanything--><allow><createcreator="..."javascript="..."/><convertconverter="..."match="..."/></allow><!--youmayneedtotellDWRaboutmethodsignatures--><signatures>...</signatures></dwr>術語這里是一些必須理解的術語-參數(shù)會被converted,遠程Bean會被created。所以如果你有一個叫A的bean,它有一個方法叫A.blah(B)那么你需要一個A的creator和一個B的converter。<allow>allow段落里面定義的試DWR可以創(chuàng)建和轉(zhuǎn)換的類。Creators我們要調(diào)用的每個類都需要一個<create...>定義。creator有幾種。比較通用的是new關鍵字和Spring。更多的信息可以參見[Creaters]文檔。Converters我們必須保證所有的參數(shù)都可以被轉(zhuǎn)換。JDK中的多數(shù)類型已經(jīng)有轉(zhuǎn)換器了,但是你需要給DWR轉(zhuǎn)換你的代碼的權利。一般來說JavaBean的參數(shù)需要一個<convert...>定義。默認情況下,如下類型不需要定義就可以轉(zhuǎn)換:所有的原生類型boolean,int,double,等等原生類型的對象類型Boolean,Integer,等等java.lang.Stringjava.util.Date和SQL中的Date以上類型組成的數(shù)組以上類型的集合類型(Lists,Sets,Maps,Iterators,等)從DOM,XOM,JDOM和DOM4J中的DOM對象(類似Element和Document)要了解如何轉(zhuǎn)換你的JavaBean或者其他類型的參數(shù)請查看\o"Converters"Converters文檔。<init>可選的init部分用來聲明創(chuàng)造bean的類和轉(zhuǎn)換bean的類。多數(shù)情況下你不需要用到他們。如果你需要定義一個新的Creator[\o"VisitpageoutsideConfluence"JavaDoc]和Converter[\o"VisitpageoutsideConfluence"JavaDoc],那么你就需要在這里定義他們。但是建議你現(xiàn)檢查一下DWR是不是已經(jīng)支持了。在init部分里有了定義只是告訴DWR這些擴展類的存在,給出了如何使用的信息。這時他們還沒有被使用。這中方式很像Java中的import語句。多數(shù)類需要在使用前先import一下,但是只有import語句并不表明這個類已經(jīng)被使用了。每一個creator和converter都用id屬性,以便后面使用。<signatures>DWR使用反射來找出在轉(zhuǎn)換時應該用那種類型。有時類型信息并不明確,這時你可以在這里寫下方法的簽名來明確類型。詳細信息查看\o"Signatures"Signatures部分。多個dwr.xml文件可以有多個dwr.xml文件(詳細信息見\o"WEB-INFConfiguration"web.xml文檔)。每個文件中的定義會被加在一起。DWR用這個功能來加載基礎配置文件。我們可以看看標準被配置文件來了解dwr.xml的內(nèi)容。轉(zhuǎn)換器轉(zhuǎn)換器在客戶端和服務器之間轉(zhuǎn)換數(shù)據(jù).下面這些轉(zhuǎn)換器有單獨章節(jié)介紹\o"ArrayConverter"ArrayConverter\o"BeanandObjectConverters"BeanandObjectConverters\o"CollectionConverter"CollectionConverter\o"EnumConverter"EnumConverter\o"DOMObjects"DOMObjects\o"HibernateIntegration"Hibernate整合\o"AccessingServletObjects"ServletObjects(HttpServletRequest,HttpSession,etc)基礎的轉(zhuǎn)換器原生類型,String,像BigDecimal這樣的簡單對象的轉(zhuǎn)換器已經(jīng)有了。你不需要在dwr.xml中<allow>部分的<convert>中定義。它們默認支持。默認支持的類型包括:boolean,byte,short,int,long,float,double,char,java.lang.Boolean,java.lang.Byte,java.lang.Short,java.lang.Integer,java.lang.Long,java.lang.Float,java.lang.Double,java.lang.Character,java.math.BigInteger,java.math.BigDecimal和java.lang.StringDate轉(zhuǎn)換器Date轉(zhuǎn)換器負責在Javascript的Date類型與Java中的Date類型(java.util.Date,java.sql.Date,java.sql.Timesorjava.sql.Timestamp)之間進行轉(zhuǎn)換。同基礎的轉(zhuǎn)換器一樣,DateConverter默認是支持的。如果你有一個Javascript的字符串(例如"01Jan2010"),你想把它轉(zhuǎn)換成Java的Date類型有兩個辦法:在javascript中用Date.parse()把它解析成Date類型,然后用DWR的DateConverter傳遞給服務器;或者把它作為字符串傳遞給Server,再用Java中的SimpleDateFormat(或者類似的)來解析。同樣,如果你有個Java的Date類型并且希望在HTML使用它。你可以先用SimpleDateFormat把它轉(zhuǎn)換成字符串再使用。也可以直接傳Date給Javascript,然后用Javascript格式化。第一種方式簡單一些,盡管浪費了你的轉(zhuǎn)換器,而且這樣做也會是瀏覽器上的顯示邏輯受到限制。其實后面的方法更好,也有一些工具可以幫你,例如:\o"VisitpageoutsideConfluence"TheJavascriptToolboxDateformatter\o"VisitpageoutsideConfluence"WebDevelopersNotesonDateformatting其他對象其實創(chuàng)建自己的轉(zhuǎn)換器也很簡單。Converter接口的Javadoc包含了信息。其實這種需要很少出現(xiàn)。在你寫自己的Converter之前先看看BeanConverter,它有可能就是你要的。TheCreators–創(chuàng)造器dwr.xml文件中的create元素的結構如下:<allow><createcreator="..."javascript="..."scope="..."><paramname="..."value="..."/><authmethod="..."role="..."/><excludemethod="..."/><includemethod="..."/></create>...</allow>這里的多數(shù)元素都是可選的-你真正必須知道的是指定一個creator和一個javascript名字。creator屬性是必須的-它用來指定使用那種創(chuàng)造器。默認情況下DWR1.1有8種創(chuàng)造器。它們是:\o"NewCreator"new:用Java的new關鍵字創(chuàng)造對象。\o"NoneCreatoronCreators"none:它不創(chuàng)建對象,看下面的原因。(v1.1+)\o"ScriptedCreator"scripted:通過BSF使用腳本語言創(chuàng)建對象,例如BeanShell或Groovy。\o"SpringIntegration"spring:通過Spring框架訪問Bean。\o"JSFIntegration"jsf:使用JSF的Bean。(v1.1+)\o"StrutsIntegration"struts:使用Struts的FormBean。(v1.1+)\o"BeehiveIntegration"pageflow:訪問Beehive或Weblogic的PageFlow。(v1.1+)如果你需要寫自己的創(chuàng)造器,你必須在init部分注冊它。javascript屬性用于指定瀏覽器中這個被創(chuàng)造出來的對象的名字。你不能使用Javascript的關鍵字。scope屬性非常類似servlet規(guī)范中的scope。它允許你指定這個bean在什么生命范圍。選項有"application","session","request"和"page"。這些值對于Servlet和JSP開發(fā)者來說應該相當熟悉了。scope屬性是可選的。默認是"page"。如果要使用"session"需要cookies。當前的DWR不支持ULR重寫。param元素被用來指定創(chuàng)造器的其他參數(shù),每種構造器各有不同。例如,"new"創(chuàng)造器需要知道要創(chuàng)建的對象類型是什么。每一個創(chuàng)造器的參數(shù)在各自的文檔中能找到。請查看上面的鏈接。include和exclude元素允許創(chuàng)造器來限制類中方法的訪問。一個創(chuàng)造器必須指定include列表或exclude列表之一。如果是include列表則暗示默認的訪問策略是"拒絕";如果是exclude列表則暗示默認的訪問策略是"允許"。例如要拒絕防范除了setWibble()以外的所有方法,你應該把如下內(nèi)容添加到dwr.xml中。<createcreator="new"javascript="Fred"><paramname="class"value="com.example.Fred"/><includemethod="setWibble"/></create>對于加入到create元素中的類的所有方法都是默認可見的。auth元素允許你指定一個J2EE的角色作為將來的訪問控制檢查:<createcreator="new"javascript="Fred"><paramname="class"value="com.example.Fred"/><authmethod="setWibble"role="admin"/></create>'none'創(chuàng)造器'none'創(chuàng)造器不創(chuàng)建任何對象-它會假設你不需要創(chuàng)建對象。這有可能是對的,有兩個原因。你可能在使用的scope不是"page"(看上面),并在在前面已經(jīng)把這個對象創(chuàng)建到這個scope中了,這時你就不需要再創(chuàng)建對象了。還有一種情況是要調(diào)用的方法是靜態(tài)的,這時也不需要創(chuàng)建對象。DWR會在調(diào)用創(chuàng)建器之前先檢查一下這個方法是不是靜態(tài)的。對于上訴兩種情況,你仍然需要class參數(shù),用來告訴DWR它是在操作的對象類型是什么。使用靜態(tài)方法DWR會在調(diào)用創(chuàng)建器之前先檢查一下這個方法是不是靜態(tài)的,如果是那么創(chuàng)造器不會被調(diào)用。很顯然這個邏輯適用于所有創(chuàng)造器,盡管如此"null"創(chuàng)造器是最容易配置的。適用單例類對于單例類的創(chuàng)建,最好適用BeanShell和BSF來實例化對象。詳細信息參見\o"ScriptedCreator"'Scripted'創(chuàng)造器其他創(chuàng)造器我么偶爾也需要一些新的創(chuàng)造器,最常見的是一個EjbCreator。討論新的創(chuàng)造器的好地方是在\o"VisitpageoutsideConfluence"郵件列表。DWR和HttpSessionBindingListenersDWR1.x中存貯已經(jīng)創(chuàng)造的Bean的方法需要注意,它在每次請求時都會調(diào)用相同的setAttribute()方法。就是說,如果一個Bean在dwr.xml中的聲明周期設置為session,再每次調(diào)用bean中的方法時,DWR都會執(zhí)行一次session.setAttribute(yourBean)。這看上去沒有什么危害,但是如果你要使用servlet的事件機制的,就是說用了HttpSessionBindingListener接口,你就會發(fā)現(xiàn)valueBound和valueUnbound事件在每次調(diào)用時都會發(fā)生,而不是你想像的在bean被創(chuàng)建時以及session過期時。DWR2只在第一次創(chuàng)建對象時調(diào)用setAttribute()。dwr.xml中的簽名(Signatures)signatures段使DWR能確定集合中存放的數(shù)據(jù)類型。例如下面的定義中我們無法知道list中存放的是什么類型。publicclassCheck{publicvoidsetLotteryResults(Listnos){...}}signatures段允許我們暗示DWR應該用什么類型去處理。格式對以了解JDK5的泛型的人來說很容易理解。<signatures><![CDATA[importjava.util.List;importcom.example.Check;Check.setLotteryResults(List<Integer>nos);]]></signatures>DWR中又一個解析器專門來做這件事,所以即便你的環(huán)境時JDK1.3DWR也能正常工作。解析規(guī)則基本上會和你預想規(guī)則的一樣(有兩個例外),所以java.lang下面的類型會被默認import。第一個是DWR1.0中解析器的bug,某些環(huán)境下不能返回正確類型。所以你也不用管它了。第二個是這個解析器時"陽光(sunnyday)"解析器。就是說它非常寬松,不想編譯器那樣嚴格的保證你一定正確。所以有時它也會允許你丟失import:<signatures><![CDATA[importjava.util.List;Check.setLotteryResults(List<Integer>);]]></signatures>將來的DWR版本會使用一個更正式的解析器,這個編譯器會基于官方Java定義,所以你最好不要使用太多這個不嚴格的東西。signatures段只是用來確定泛型參數(shù)中的類型參數(shù)。DWR會自己使用反射機制或者運行時類型確定類型,或者假設它是一個String類型。所以:不需要signatures-沒有泛型參數(shù):publicvoidmethod(Stringp);publicvoidmethod(String[]p);需要signatures-DWR不能通過反射確定:publicvoidmethod(List<Date>p);publicvoidmethod(Map<String,WibbleBean>p);不需要signatures-DWR能正確的猜出:publicvoidmethod(List<String>p);publicvoidmethod(Map<String,String>p);不需要signatures-DWR可以通過運行時類型確定:publicList<Date>method(Stringp);沒有必要讓Javascript中的所有對象的key都是String類型-你可以使用其他類型作為key。但是他們在使用之前會被轉(zhuǎn)換成String類型。DWR1.x用Javascript的特性把key轉(zhuǎn)換成String。DWR2.0可能會用toString()方法,在服務段進行這一轉(zhuǎn)換。engine.jsFunctionsengine.js對DWR非常重要,因為它是用來轉(zhuǎn)換來至動態(tài)生成的接口的javascript函數(shù)調(diào)用的,所以只要用到DWR的地方就需要它。Theengine.jsfile每一個頁面都需要下面這些語句來引入主DWR引擎。<scripttype='text/javascript'src='/[YOUR-WEB-APP]/dwr/engine.js'></script>使用選項下面這些選項可以通過DWREngine.setX()函數(shù)來設置全局屬性。例如:DWREngine.setTimeout(1000);或者在單次調(diào)用級別上(假設Remote被DWR暴露出來了):Remote.singleMethod(params,{callback:function(data){...},timeout:2000});遠程調(diào)用可以\o"CallBatching"批量執(zhí)行來減少反應時間。endBatch函數(shù)中可以設置選項。DWREngine.beginBatch();Remote.methodInBatch1(params,callback1);Remote.methodInBatch2(params,callback2);DWREngine.endBatch({timeout:3000});可以混合這幾種方式,那樣的話單次調(diào)用或者批量調(diào)用級別上的設置可以復寫全局設置(就像你希望的那樣)。當你在一個批量處理中多次設置了某個選項,DWR會保留最后一個。所以如果Remote.singleMethod()例子在batch里面,DWR會使用3000ms做為超時的時間。callback和exceptionHandler兩個選項只能在單次調(diào)用中使用,不能用于批量調(diào)用。preHook和postHook選項兩個選項是可添加的,就是說你可以為每一次調(diào)用添加多個hook。全局的preHook會在批量調(diào)用和單次調(diào)用之前被調(diào)用。同樣全局的postHook會在單次調(diào)用和批量調(diào)用之后被調(diào)用。如果以上敘述讓你感到混亂,不用擔心。DWR的的設計往往和你想象中的一樣,所以其實這些并不復雜。選項索引下面是可用選項列表。OptionGlobalBatchCallSummary\o"RemotingOptions"async設置是否為異步調(diào)用,不推薦同步調(diào)用headers2.02.02.0在XHR調(diào)用中加入額外的頭信息parameters2.02.02.0可以通過Meta-datarequest.getParameter()取得的元數(shù)據(jù)\o"RemotingOptions"httpMethod2.02.02.0選擇GET或者POST.1.x中叫'verb'\o"RemotingOptions"rpcType2.02.02.0選擇是使用xhr,iframe或者script-tag來實現(xiàn)遠程調(diào)用.1.x中叫'method'\o"CallBatching"skipBatch1.0*2.1?-某個調(diào)用是否應該設置為batch中的一部分或者直接的。這個選項和上面都有些不同。
*沒有setSkipBatch()方法,批量調(diào)用是通過beginBatch()和endBatch()來控制的。timeout1.01.11.1設定超時時長,單位ms處理器(Handler)OptionGlobalBatchCallSummary\o"Errors,WarningsandTimeouts"errorHandler1.01.11.1當出了什么問題時的動作。1.x中還包括服務端的異常。從2.0開始服務端異常通過'exceptionHandler'處理\o"Errors,WarningsandTimeouts"warningHandler1.02.02.0當因為瀏覽器的bug引起問題時的動作,所以默認這個設置為null(關閉)textHtmlHandler2.02.02.0當?shù)玫讲徽5膖ext/html頁面時的動作(通常表示超時)調(diào)用處理器(CallHandler)(注冊到單獨調(diào)用上的,而不是batch中的所有調(diào)用)OptionGlobalBatchCallSummary\o"ScriptingIntroduction"callback--1.0調(diào)用成功以后的要執(zhí)行的回調(diào)函數(shù),應該只有一個參數(shù):遠程調(diào)用得到的數(shù)據(jù)exceptionHandler--2.0遠程調(diào)用失敗的動作,一般是服務端異常或者數(shù)據(jù)轉(zhuǎn)換問題。Hooks(一個batch中可以注冊多個hook)OptionGlobalBatchCallSummary\o"RemotingHooks"preHook1.01.11.1遠程調(diào)用前執(zhí)行的函數(shù)\o"RemotingHooks"postHook1.01.11.1遠程調(diào)用后執(zhí)行的函數(shù)全局選項(在單次調(diào)用或者批量調(diào)用中不可用)OptionGlobalBatchCallSummary\o"CallOrdering"ordered1.0--DWR是否支持順序調(diào)用pollType2.0--選擇xhr或者iframe的反轉(zhuǎn)AjaxreverseAjax2.0--是否查找inbound調(diào)用廢棄的選項OptionGlobalBatchCallSummaryverb1.0廢棄。使用'httpMethod'代替method1.0廢棄。使用'rpcType'代替將來的OptionGlobalBatchCallSummaryonBackButton2.1?2.1?-用戶按了back按鈕后的動作onForwardButton2.1?2.1?-用戶按了forward按鈕的動作保證的責任DWR的目的是讓你確切的知道所有調(diào)用的動作。知道了瀏覽器存在的bug,這是可以做到了。如果你設置了callback,exceptionHandler,errorHandler,warningHandler和textHtmlHandler,DWR就應該總是為每一個請求提供響應。CallBatching你可以使用batch來批量的執(zhí)行遠程調(diào)用。這樣可以減少與服務器的交互次數(shù),所以可以提交反應速度。一個batch以DWREngine.beginBatch()開始,并以DWREngine.endBatch()結束。當DWREngine.endBatch()被調(diào)用,我們就結束了遠程調(diào)用的分組,這樣DWR就在一次與服務器的交互中執(zhí)行它們。DWR會小心的處理保證所有的回調(diào)函數(shù)都會被調(diào)用,所以你可以明顯的打開和關閉批處理。只要別忘了調(diào)用endBatch(),否則所有的遠程調(diào)用永遠的處于列隊中。警告很明顯,把一些遠程調(diào)用放在一起執(zhí)行也會產(chǎn)生一些影響。例如不能在batch里面執(zhí)行同步調(diào)用。所有的元數(shù)據(jù)選項,例如hooks,timeouts和errorHandlers都在batch級別的,而不是單次調(diào)用級別上的。所以如果一個batch中有兩個調(diào)用設置了不同的超時,除了最后一個其他的都被忽略。順序調(diào)用因為Ajax一般是異步調(diào)用,所以遠程調(diào)用不會按照發(fā)送的順序返回。DWREngine.setOrdered(boolean)允許結果嚴格按照發(fā)送的順序返回。DWR在舊的請求安全返回以后才去發(fā)送新的請求。我們一定需要保證請求按照發(fā)送的順序返回嗎?(默認為false)警告:把這個設置為true會減慢你的應用程序,如果一個消息丟失,瀏覽器就會沒有響應。很多時候即使用異步調(diào)用也有更好的解決辦法,所以在用這一功能之前先好好考慮一下。處理錯誤和警告當因為一些原因調(diào)用失敗,DWR就會調(diào)用錯誤和警告handler(根據(jù)錯誤的激烈程度),并傳遞錯誤消息。你可以用這種方法來在alert窗口或狀態(tài)來中顯示錯誤信息。你可以使用DWREngine.setErrorHandler(function)來改變錯誤處理方式,同樣通過DWREngine.setWarningHandler(function)來改變警告處理方式。更多關于處理錯誤和警告,請查看\o"ErrorHandling"錯誤處理頁面。設置超時DWREngine.setTimeout(),單次調(diào)用和批量調(diào)用級別的元數(shù)據(jù)選項,允許你設置一個超時值。全局的DWREngine.setTimeout()函數(shù)設置全局超時。如果設置值為0(默認)可以將超時關掉。setTimeout()的單位是毫秒。如果調(diào)用超時發(fā)生,錯誤處理器就會被調(diào)用。一個例子:Remote.method(params,{callback:function(data){alert("itworked");},errorHandler:function(message){alert("itbroke");},timeout:1000});如果Remote.method()調(diào)用超過了1分鐘還沒有返回,"itbroke"消息就會被顯示。遠程調(diào)用HooksDWREngine.setPreHook(function)和DWREngine.setPostHook(function)。如果你想在DWR調(diào)用之前出現(xiàn)一個提示,你可以設置pre-hook函數(shù)。它將會被調(diào)用,但是沒有參數(shù)傳遞到這個函數(shù)。當你希望讓一些按鈕在調(diào)用期間變灰來防止被再次使用,這一功能將會很有用。post-hook用來和pre-hook一起使用來逆轉(zhuǎn)pre-hook產(chǎn)生的做的一些改變。一個使用pre和posthook的例子就是DWRUtil.useLoadingMessage()函數(shù)。遠程調(diào)用選項DWR有一些選項用來控制遠程調(diào)用的處理方式。method和verb對于用戶應該時透明的,但是不同的瀏覽器效果的可能不一樣。一般來說DWR會選擇正確方法來處理,但是這些選項對于在不同效果的瀏覽器之間開發(fā)很有用。DWREngine.setAsync(flag)DWR1.0不支持。我們指定讓XHR異步調(diào)用了嗎?默認為true。警告如果你使用的時IFrame或者ScriptTag這一選項被忽略。一般來說把他變成false是個糟糕的做法。因為那樣會使你的瀏覽器變慢。要設置全局同步機制:DWREngine.setAsync(true);或者設置單次調(diào)用同步:Remote.method(params,{callback:function(data){...},async:true});或者在batch里面:DWREngine.beginBatch();Remote.method1(params,callback1);Remote.method2(params,callback2);DWREngine.endBatch({async:true});DWREngine.setMethod(newmethod)用來設置恰當?shù)姆椒āetMethod()不能把正使用你選擇的方法,它只是保證首先嘗試使用那個方法。newmethod必須是DWREngine.XMLHttpRequest或者DWREngine.IFrame,或者2.0以后的DWREngine.ScriptTag。XMLHttpRequest時默認的,并且大多情況下可用。當ActiveX禁用IFrame就有用了,盡管DWR能自動檢測出這種情況并切換到IFrame。當你要突破跨域調(diào)用的限制,ScriptTag就很有用了。例如,要設置全局的遠程調(diào)用方法:DWREngine.setMethod(DWREngine.IFrame);或者單次調(diào)用:Remote.method(params,{callback:function(data){...},method:DWREngine.IFrame});或者批量調(diào)用:DWREngine.beginBatch();Remote.method1(params,callback1);Remote.method2(params,callback2);DWREngine.endBatch({method:DWREngine.IFrame});DWREngine.setVerb(verb)這個選項允許你選擇POST和GET,無論時用iframe還是XMLHttpRequest方法。一些瀏覽器(例如,舊版的Safari)不支持XHR-POST所以DWR就自動切換到GET,即使你設置POST為verb。所以setVerb()應當被僅僅做為一個堤示。如果使用ScriptTag來遠程調(diào)用,設置verb時沒有的。例如,設置全局遠程調(diào)用的verb:DWREngine.setVerb("GET");設置單次調(diào)用:Remote.method(params,{callback:function(data){...},verb:"GET"});設置批量調(diào)用:DWREngine.beginBatch();Remote.method1(params,callback1);Remote.method2(params,callback2);DWREngine.endBatch({verb:"GET"});util.jsutil.js包含了一些工具函數(shù)來幫助你用javascript數(shù)據(jù)(例如從服務器返回的數(shù)據(jù))來更新你的web頁面。你可以在DWR以外使用它,因為它不依賴于DWR的其他部分。你可以下載整個\o"VisitpageoutsideConfluence"DWR或者\o"VisitpageoutsideConfluence"單獨下載.4個基本的操作頁面的函數(shù):getValue[s]()和setValue[s]()可以操作大部分HTML元素除了table,list和image。getText()可以操作selectlist。要修改table可以用addRows()和removeAllRows()。要修改列表(select列表和ul,ol列表)可以用addOptions()和removeAllOptions()。還有\(zhòng)o"Submissionbox"一些其他功能不是DWRUtil的一部分。但它們也很有用,它們可以用來解決一些小問題,但是它們不是對于所有任都通用的。$()$()函數(shù)(它是合法的Javascript名字)是從Protoype偷來的主意。大略上的講:$=document.getElementById。因為在Ajax程序中,你會需要寫很多這樣的語句,所以使用$()會更簡潔。通過指定的id來查找當前HTML文檔中的元素,如果傳遞給它多個參數(shù),它會返回找到的元素的數(shù)組。所有非String類型的參數(shù)會被原封不動的返回。這個函數(shù)的靈感來至于prototype庫,但是它可以在更多的瀏覽器上運行。可以看看DWRUtil.toDescriptiveString的演示。從技術角度來講他在IE5.0中是不能使用的,因為它使用了Array.push,盡管如此通常它只是用來同engine.js一起工作。如果你不想要engine.js并且在IE5.0中使用,那么你最好為Array.push找個替代品。util.js:生成列表DWR的一個常遇到的任務就是根據(jù)選項填充選擇列表。下面的例子就是根據(jù)輸入填充列表。下面將介紹DWRUtil.addOptions()的幾種是用方法。如果你希望在你更新了select以后,它仍然保持運來的選擇,你要像下面這樣做:varsel=DWRUtil.getValue(id);DWRUtil.removeAllOptions(id);DWRUtil.addOptions(id,...);DWRUtil.setValue(id,sel);如果你想加入一個初始的"Pleaseselect..."選項那么你可以直接加入下面的語句:DWRUtil.addOptions(id,\["Pleaseselect..."]);然后再下面緊接著加入你真正的選項數(shù)據(jù)。DWRUtil.addOptions有5種模式數(shù)組:DWRUtil.addOptions(selectid,array)會創(chuàng)建一堆option,每個option的文字和值都是數(shù)組元素中的值。對象數(shù)組(指定text):DWRUtil.addOptions(selectid,data,prop)用每個數(shù)組元素創(chuàng)造一個option,option的值和文字都是在prop中指定的對象的屬性。對象數(shù)組(指定text和value值):DWRUtil.addOptions(selectid,array,valueprop,textprop)用每個數(shù)組元素創(chuàng)造一個option,option的值是對象的valueprop屬性,option的文字是對象的textprop屬性。對象:DWRUtil.addOptions(selectid,map,reverse)用每個屬性創(chuàng)建一個option。對象屬
溫馨提示
- 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
- 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權益歸上傳用戶所有。
- 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預覽,若沒有圖紙預覽就沒有圖紙。
- 4. 未經(jīng)權益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
- 5. 人人文庫網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負責。
- 6. 下載文件中如有侵權或不適當內(nèi)容,請與我們聯(lián)系,我們立即糾正。
- 7. 本站不保證下載資源的準確性、安全性和完整性, 同時也不承擔用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。
最新文檔
- 設備設施包保管理制度
- 設計公司內(nèi)控管理制度
- 設計單位現(xiàn)場管理制度
- 設計項目人員管理制度
- 診所醫(yī)療器械管理制度
- 診斷試劑風險管理制度
- 試驗示范基地管理制度
- 財務資金收支管理制度
- 貨倉搬運安全管理制度
- 貨物海關代理管理制度
- 2024年黃岡團風縣招聘城區(qū)社區(qū)工作者真題
- 2025年山東省高考歷史試卷真題
- 2025至2030中國農(nóng)膜行業(yè)發(fā)展分析及發(fā)展前景與投資報告
- 2025圖解《政務數(shù)據(jù)共享條例》V1.0學習解讀
- 2025電商平臺店鋪轉(zhuǎn)讓合同模板
- 2025年人教版(2024)初中英語七年級下冊期末考試測試卷及答案
- (2025)事業(yè)編考試題庫(附含答案)
- 女性美學課堂企業(yè)制定與實施新質(zhì)生產(chǎn)力項目商業(yè)計劃書
- 高端私人定制服務方案
- 2025年保密知識競賽考試題庫300題(含答案)
- 部編版2024-2025學年四年級下冊語文期末測試卷(含答案)
評論
0/150
提交評論