2020国产成人精品视频,性做久久久久久久久,亚洲国产成人久久综合一区,亚洲影院天堂中文av色

分享

為 WebSphere Application Server Community Edit...

 gyb98 2010-12-21

引言

Ajax(異步 JavaScript 和 XML)術(shù)語用于表示一組支持創(chuàng)建富 Internet 應(yīng)用程序 (Rich Internet Application) 的技術(shù)。通過使用這些技術(shù),可以創(chuàng)建響應(yīng)能力強(qiáng)且具有與桌面應(yīng)用程序類似的豐富用戶界面的 Web 應(yīng)用程序。這些技術(shù)允許在后臺(tái)以異步方式檢索數(shù)據(jù),而不會(huì)影響所顯示的頁面,而且可以僅請(qǐng)求數(shù)據(jù),而不用請(qǐng)求整個(gè) HTML 頁面??梢允褂矛F(xiàn)在的瀏覽器提供的 XmlHttpRequest 或等效對(duì)象進(jìn)行此異步后臺(tái)通信。

IBM WebSphere Application Server Community Edition v2.1.x(以下稱為 Community Edition)的安裝包中提供了一些用于開發(fā)和承載支持 Ajax 的應(yīng)用程序的流行框架。在本文中,我們將了解如何配置和使用其中的三個(gè)框架,即:

  • Dojo 工具包
  • Direct Web Remoting (DWR)
  • Tomcat Comet 支持

我們還將開發(fā)一個(gè)簡(jiǎn)單的 Web 應(yīng)用程序,其中使用了這些技術(shù)來提供得到改善的用戶體驗(yàn)。為了遵循本文所述進(jìn)行操作,您需要 WebSphere Application Server Community Edition v2.1.x。


Dojo 工具包

Dojo 是使用 JavaScript 編寫的開源 DHTML 工具集。Dojo 解決了使用 JavaScript 時(shí)的一些問題,包括處理瀏覽器特定的行為。這些行為已經(jīng)通過 Dojo 工具從用戶層面抽象出來了。

另外,還提供了一組可配置小部件,可將其用于快速開發(fā)獨(dú)立于瀏覽器的動(dòng)態(tài)網(wǎng)頁。Dojo 工具集由一組 JavaScript API 組成,包含在 WebSphere Application Server Community Edition v 2.1 中??梢酝ㄟ^上下文根 /dojo 訪問此工具集。Dojo 還提供了用于進(jìn)行異步 XMLHttpRequest 調(diào)用的 API,以在不刷新頁面的情況下從服務(wù)器獲取數(shù)據(jù)。


Direct Web Remoting (DWR)

DWR 允許開發(fā)人員通過 JavaScript 代理向客戶端公開服務(wù)器端的 Java? 對(duì)象。它會(huì)為所有公開的 Java? 對(duì)象創(chuàng)建代理,以便從客戶端調(diào)用這些對(duì)象。相應(yīng)地,DWR 將在服務(wù)器中調(diào)用對(duì)應(yīng)的 Java 方法,并將響應(yīng)以 JSON (JavaScript Object Notation) 格式返回到調(diào)用方腳本。

您可以配置 DWR 在后臺(tái)以同步或異步方式呼叫服務(wù)器。因此,可以避免與普通 HTTP 請(qǐng)求-響應(yīng)模式關(guān)聯(lián)的頁面刷新。

DWR 還提供了 Reverse Ajax,即用于將信息從服務(wù)器以異步方式發(fā)送到瀏覽器的機(jī)制。通過這樣,服務(wù)器可以采用以下方式定期將響應(yīng)發(fā)送到客戶端:

  • 輪詢:客戶端定期輪詢服務(wù)器。
  • Comet:當(dāng)客戶端發(fā)出請(qǐng)求時(shí),服務(wù)器將保留響應(yīng)句柄,寫入內(nèi)容保存在此句柄中。在這種情況下,客戶端不需要進(jìn)行輪詢。
  • 合并: 多個(gè)響應(yīng)組合在一起,隨客戶端作出的下一個(gè)請(qǐng)求的響應(yīng)一起發(fā)送。

Tomcat Comet 支持

Comet 術(shù)語是 Dojo Foundation 的 Alex Russel 發(fā)明的,用于描述通過 HTTP 協(xié)議進(jìn)行的事件驅(qū)動(dòng)的服務(wù)器推送機(jī)制。在普通 HTTP 通信中,客戶端始終通過打開到服務(wù)器的連接并發(fā)送請(qǐng)求來發(fā)起數(shù)據(jù)傳輸。服務(wù)器將處理此請(qǐng)求,在相同連接上發(fā)送響應(yīng),然后關(guān)閉連接。因此,連接的壽命相對(duì)較短。在 Comet 中,服務(wù)器將連接保持開放狀態(tài),會(huì)在出現(xiàn)相關(guān)事件時(shí)持續(xù)通過其寫入數(shù)據(jù)。Tomcat p通過 NIO 和 APR 連接器提供了此支持。BIO 連接器并不提供 Comet 支持。


創(chuàng)建 NIO 連接器

缺省情況下,Community Edition 并不提供預(yù)安裝的 NIO 連接器。在運(yùn)行使用 Comet 協(xié)議的應(yīng)用程序前,我們需要從管理控制臺(tái)創(chuàng)建新 NIO 連接器并將其啟動(dòng)。我們將首先刪除在 8080 端口上運(yùn)行的 BIO 連接器,然后創(chuàng)建在此端口運(yùn)行的新 NIO 連接器。

請(qǐng)按照以下步驟創(chuàng)建 NIO 連接器:

  1. 啟動(dòng) Community Edition,并在瀏覽器中打開 https://localhost:8443/console/
  2. 輸入用戶名 system,并輸入密碼 manager。點(diǎn)擊 Login,將隨即在管理控制臺(tái)中打開 Welcome 頁。
  3. 在左側(cè)導(dǎo)航窗格中,單擊 Web Server 鏈接,以打開 Web Server Manager 頁,如圖 1 中所示:

    圖 1. Web Server Manager
    Web Server Manager 的屏幕截圖,顯示網(wǎng)絡(luò)偵聽器列表

  4. 刪除名為 TomcatWebConnector 的連接器。

  5. 在 Add New 部分,單擊 Tomcat NIO Connector 鏈接,將隨即打開圖 2 中所示的屏幕。

    圖 2. 添加新的 Tomcat NIO 連接器
    添加新 NIO 連接器的窗口的屏幕截圖

  6. uniqueName 字段中填寫 TomcatNIOConnector 值,并點(diǎn)擊 Save,從而創(chuàng)建并啟動(dòng) NIO 連接器。您的窗口顯示應(yīng)該與圖 3 類似。

    圖 3. 添加到網(wǎng)絡(luò)偵聽器的 TomcatNIOConnector
    顯示網(wǎng)絡(luò)偵聽器列表中的新 NIO 連接器的屏幕截圖


開發(fā) Web 應(yīng)用程序

我們現(xiàn)在已經(jīng)完成了所有準(zhǔn)備工作,可以開始開發(fā) Web 應(yīng)用程序了。這是一個(gè)股票報(bào)價(jià)器應(yīng)用程序,每 5 秒鐘將使用最新的報(bào)價(jià)進(jìn)行一次更新。我們將在 Tomcat 提供的 Comet 實(shí)現(xiàn)上使用 DWR 的 Reverse Ajax 功能。為了顯示報(bào)價(jià),我們將使用 Dojo 工具中提供的一個(gè)現(xiàn)成 Dojo 小部件,即 dojox.Grid 小部件。我們還將編寫一個(gè) Servlet 來使用 Tomcat 中的 Comet 支持打印股票信息。

編寫 Comet Servlet

Apache Tomcat 提供了 org.apache.catalina.CometProcessor 接口,以便編寫的所有 Servlet 都能夠使用 Comet 支持。此接口定義了在我們的 Servlet 中實(shí)現(xiàn)的名為 public void event(CometEvent event) 的單個(gè)方法。清單 1 顯示了此 Servlet 的兩個(gè)主要方法:


清單 1:Comet Servlet
            public void init() throws ServletException {
            super.init();
            Runnable r = new Runnable() {
            public void run() {
            while (!stop) {
            synchronized (openConnections){
            List<Stock> stocks = new StockService().getStocks();
            for (HttpServletResponse response : openConnections) {
            try {
            PrintWriter pw = response.getWriter();
            for (Stock stock : stocks) {
            pw.println(stock.getSymbol() + ":"
            + stock.getPrice());
            }
            pw.flush();
            } catch (IOException e) {
            e.printStackTrace(System.out);
            }
            }
            }
            try {
            Thread.sleep(5000);
            } catch (InterruptedException e) {
            e.printStackTrace(System.out);
            }
            }
            }
            };
            Thread stockThread = new Thread(r);
            stockThread.setDaemon(true);
            stockThread.start();
            }
            public void event(CometEvent event) throws IOException, ServletException {
            HttpServletRequest request = event.getHttpServletRequest();
            HttpServletResponse response = event.getHttpServletResponse();
            if (event.getEventType() == CometEvent.EventType.BEGIN) {
            synchronized (openConnections){
            openConnections.add(response);
            }
            } else if (event.getEventType() == CometEvent.EventType.ERROR) {
            synchronized (openConnections){
            openConnections.remove(response);
            }
            } else if (event.getEventType() == CometEvent.EventType.END) {
            synchronized (openConnections){
            openConnections.remove(response);
            }
            } else if (event.getEventType() == CometEvent.EventType.READ) {
            }
            }
            

init 方法中,我們將實(shí)例化獲取股票報(bào)價(jià)的線程,此線程還要將這些報(bào)價(jià)寫入所有正在偵聽的客戶端,即 openConnections 列表中的所有響應(yīng)對(duì)象。出現(xiàn)四個(gè)事件(BEGIN、ERROR、END、READ)中的任意事件時(shí),都會(huì)觸發(fā) event 方法。我們從作為參數(shù)傳遞的 org.apache.catalina.CometEvent 對(duì)象中獲得響應(yīng)。對(duì)于 BEGIN 事件,要將響應(yīng)添加到集合中。對(duì)于 ERROREND 事件,我們將從列表中刪除響應(yīng)。

BEGIN 事件代表著該連接處理開始,因此我們要將響應(yīng)添加到響應(yīng)列表中。ENDERROR 事件代表著連接結(jié)束或出現(xiàn)了錯(cuò)誤。有關(guān)這些事件的含義的更多信息,請(qǐng)參見 Apache Tomcat 文檔。

配置 DWR

應(yīng)用程序硬編碼了一組要顯示的股票。股票值由 com.dev.trade.service.StockQuoteGenerator 類隨機(jī)更新。清單 2 顯示了這個(gè)類的源代碼的相關(guān)部分。


清單 2:生成股票價(jià)格的類
            package com.dev.trade.service;
            import java.util.HashSet;
            import java.util.List;
            import java.util.Set;
            import java.util.Collections;
            import com.dev.trade.bo.Stock;
            public class StockQuoteGenerator {
            private StockService ss = new StockService();
            private List<Stock>  stocks = null;
            private static StockQuoteGenerator generator = new StockQuoteGenerator();
            private Set<QuoteListener>
            listeners = Collections.synchronizedSet(new HashSet<QuoteListener> ());
            private volatile boolean contextDestroyed = false;
            private StockQuoteGenerator() {
            Runnable r = new Runnable() {
            public void run() {
            try {
            while (!contextDestroyed) {
            update(generateStockQuotes());
            Thread.sleep(5000);
            }
            }catch (Exception e) {
            e.printStackTrace(System.out);
            }
            }
            };
            Thread t = new Thread(r);
            t.setDaemon(true);
            t.start();
            }
            public static StockQuoteGenerator getInstance() {
            return generator;
            }
            public void setContextDestroyed(boolean cd) {
            this.contextDestroyed = cd;
            }
            public void addListener(QuoteListener listener) {
            listeners.add(listener);
            }
            private void update(List<Stock>  stocks) {
            for (QuoteListener listener : listeners) {
            listener.updateStockQuotes(stocks);
            }
            }
            private List<Stock>  generateStockQuotes() {
            stocks = ss.getStocks();
            return stocks;
            }
            }
            

在 StockQuoteGenerator 類(一個(gè)單態(tài)類)的構(gòu)造函數(shù)中,我們啟動(dòng)了一個(gè)新線程,并向該線程分配了一個(gè) Runnable 對(duì)象。因此,這個(gè)對(duì)象的 run 方法將繼續(xù)執(zhí)行,直到將 contextDestroyed 變量設(shè)置為 true 為止。此變量?jī)H在應(yīng)用程序上下文要銷毀時(shí)才會(huì)設(shè)置為 true。為此,我們將在 web.xml 中注冊(cè)一個(gè)上下文偵聽器,即 com.dev.trade.listener.ServletContextListener。

generateStockQuotes 方法調(diào)用 StockServicegetStocks 方法來獲取生成的股票報(bào)價(jià)。使用 addListener 方法可添加偵聽器。這些偵聽器實(shí)現(xiàn) com.dev.trade.service.QuoteListener 接口以及相應(yīng)的 updateStockQuotes 方法。

這些偵聽器都是 com.dev.trade.service.StockQuoteListenerImpl 的實(shí)例。此類在其構(gòu)造函數(shù)中初始化 DWR 提供的 org.directwebremoting.WebContext 類的實(shí)例,然后向 StockQuoteGenerator's 偵聽器列表注冊(cè)自身。清單 3 顯示了此類的 updateStockQuotes 方法。


清單 3:向不同客戶端推送數(shù)據(jù)的代碼
            public void updateStockQuotes(List<Stock> stocks) {
            ScriptBuffer script = new ScriptBuffer();
            script.appendScript("updateStocks(").appendData(stocks).appendScript(
            ");");
            Collection<ScriptSession> sessions = wctx.getAllScriptSessions();
            for (ScriptSession session : sessions) {
            if(!session.isInvalidated()){
            session.addScript(script);
            } else {
            wctx.getAllScriptSessions().remove(session);
            }
            }
            }
            

此方法將 JavaScript 函數(shù)調(diào)用傳播到所有開放客戶端。將會(huì)調(diào)用函數(shù) updateStocks 并傳遞股票值。此 JavaScript 方法實(shí)際更新我們將顯示的 Dojo 網(wǎng)格小部件的模型,然后調(diào)用其 update 方法,以讓網(wǎng)格顯示新數(shù)據(jù)。DWR 為每個(gè)開放股票報(bào)價(jià)器頁創(chuàng)建腳本會(huì)話。

請(qǐng)注意,為了使其工作,應(yīng)該由執(zhí)行 DWR 代碼的同一個(gè)線程調(diào)用 StockQuoteListenerImpl 類的構(gòu)造函數(shù)。為此,我們將需要配置 DWR,以實(shí)例化 StockQuoteListenerImpl 的對(duì)象。對(duì)于此配置,我們將創(chuàng)建 dwr.xml 文件,并將其放置在應(yīng)用程序的 WEB-INF 目錄中。清單 4 顯示了此文件。


清單 4:dwr.xml
            <dwr>
            <allow>
            <create creator="new" javascript="Ticker" scope="application">
            <param name="class" value="com.dev.trade.service.StockQuoteListenerImpl"/>
            </create>
            <create creator="new" javascript="StockService" scope="application">
            <param name="class" value="com.dev.trade.service.StockService"/>
            </create>
            <convert converter="bean" match="com.dev.trade.bo.Stock"/>
            </allow>
            </dwr>
            

請(qǐng)注意,StockQuoteListenerImpl 已經(jīng)通過創(chuàng)建程序在 dwr.xml 中公開。我們將此對(duì)象的范圍設(shè)置為 application,因?yàn)槊總€(gè)應(yīng)用程序只需要一個(gè)此對(duì)象的實(shí)例。我們向 JavaScript 公開的另一個(gè)類是 com.dev.trade.service.StockService,此類為我們提供了用于獲得股票列表的 getStocks 方法。我們還需要將 DWRServlet 添加到應(yīng)用程序的 web.xml,以便初始化 DWR,并由其將所配置的上述對(duì)象的代理向 JavaScript 公開。清單 5 顯示了 web.xml 文件。


清單 5:web.xml
            <?xml version="1.0" encoding="UTF-8"?>
            <web-app xmlns="http://java./xml/ns/j2ee" version="2.4"
            xmlns:xsi="http://www./2001/XMLSchema-instance"
            xsi:schemaLocation="http://java./xml/ns/j2ee
            http://java./xml/ns/j2ee/web-app_2_4.xsd">
            <display-name>brokerage</display-name>
            <listener>
            <listener-class>
            com.dev.trade.listener.DwrContextListener
            </listener-class>
            </listener>
            <servlet>
            <display-name>DWR Servlet</display-name>
            <servlet-name>dwr-invoker</servlet-name>
            <servlet-class>org.directwebremoting.servlet.DwrServlet</servlet-class>
            <init-param>
            <param-name>debug</param-name>
            <param-value>true</param-value>
            </init-param>
            <init-param>
            <param-name>activeReverseAjaxEnabled</param-name>
            <param-value>true</param-value>
            </init-param>
            <init-param>
            <param-name>initApplicationScopeCreatorsAtStartup</param-name>
            <param-value>true</param-value>
            </init-param>
            <load-on-startup>1</load-on-startup>
            </servlet>
            <servlet-mapping>
            <servlet-name>dwr-invoker</servlet-name>
            <url-pattern>/dwr/*</url-pattern>
            </servlet-mapping>
            <welcome-file-list>
            <welcome-file>/stocks.html</welcome-file>
            </welcome-file-list>
            </web-app>
            

activeReverseAjaxEnabled 屬性設(shè)置為 true,以便 DWR 使用 Comet 來啟用 Reverse Ajax。如果設(shè)置為 false,則 DWR 將使用合并選項(xiàng)。

initApplicationScopeCreatorsAtStartup 用于在啟動(dòng) DWR 時(shí)初始化所有應(yīng)用程序范圍內(nèi)的對(duì)象。

現(xiàn)在,我們需要在客戶端導(dǎo)入兩個(gè)腳本文件:DWR 客戶端引擎和 DWR 為公開的對(duì)象 com.dev.trade.service.StockService 創(chuàng)建的 JavaScript 代理。清單 6 顯示了此導(dǎo)入對(duì)應(yīng)的代碼。


清單 6:在客戶端上進(jìn)行訪問
            <script type="text/javascript" src="dwr/engine.js"></script>
            <script type='text/javascript'
            src='/brokerage/dwr/interface/StockService.js'></script>
            

我們還需要配置 DWR 客戶端引擎,以使用活動(dòng) Reverse Ajax,因此我們需要調(diào)用 dwr.engine.setActiveReverseAjax(true)。

我們可以調(diào)用 StockServicegetStocks 方法,以使用 StockService.getStocks({callback:getModel,async:false}) 對(duì)要顯示的 Dojo 網(wǎng)格小部件進(jìn)行初始填充。getModel 參數(shù)引用將調(diào)用的 JavaScript 方法,此調(diào)用的結(jié)果將作為方法參數(shù)傳遞。

清單 7 所示的方法將返回我們要顯示的 Dojo 網(wǎng)格的模型。


清單 7:Web Remoting
            function getModel(stocks) {
            var data = new Array();
            for ( var i = 0; i < stocks.length; i++) {
            var subData = new Array();
            subData[0] = stocks[i].symbol;
            subData[1] = stocks[i].companyName
            subData[2] = stocks[i].price
            subData[3] = stocks[i].eps
            data[i] = subData;
            }
            updatedModel = new dojox.grid.data.Table(null, data);
            return updatedModel;
            }
            

配置 Dojo

Community Edition 隨附了 Dojo JavaScript 庫(kù)。其中對(duì)一些管理控制臺(tái) Portlet 使用了 Dojo。Dojo 打包為在上下文根 /dojo 提供的 Web 應(yīng)用程序。要在我們的 HTML 客戶端頁中使用 Dojo,我們需要使用清單 8 中所示的腳本導(dǎo)入 dojo.js 腳本。


清單 8:導(dǎo)入 dojo.js
            <script type="text/javascript" src="/dojo/dojo/dojo.js"
            djConfig="isDebug:false, parseOnLoad: true"></script>
            

導(dǎo)入 Dojo 腳本時(shí),我們可以通過 dojo.require 調(diào)用導(dǎo)入其余依賴項(xiàng)。我們要?jiǎng)?chuàng)建的 dojox.Grid 小部件需要模型和結(jié)構(gòu)。其模型代表要顯示的數(shù)據(jù),而結(jié)構(gòu)代表我們將要如何進(jìn)行顯示。此模型實(shí)際上是由數(shù)組組成的數(shù)組。清單 9 顯示了結(jié)構(gòu)定義:


清單 9:模型定義
            var view1 = {
            noscroll :false,
            cells : [ [ {
            name :'Symbol',
            width :'auto'
            }, {
            name :'Company Name',
            width :'auto'
            }, {
            name :'Price',
            width :'auto'
            }, {
            name :'Earnings Per Share',
            width :'auto'
            } ] ]
            };
            var gridLayout = [ {
            type :'dojox.GridRowView',
            width :'20px'
            }, view1 ];
            <div class="tundra" id="stock_grid" dojoType="dojox.Grid" model="updatedModel"
            structure="gridLayout" elasticView="1" defaultHeight="37em"></div>
            

在此清單中,我們發(fā)現(xiàn)帶 id="stock_grid"div 封裝了實(shí)際的網(wǎng)格。此結(jié)構(gòu)由 gridLayout 對(duì)象定義,此對(duì)象是包含 view1 的數(shù)組。

view1 變量也是數(shù)組,其中包含提供所有列應(yīng)該在網(wǎng)格中如何顯示的詳細(xì)信息的 cells 屬性。


構(gòu)建并部署 Web 應(yīng)用程序

要構(gòu)建此應(yīng)用程序,您將需要 Apache Maven2。安裝 Maven2 并按照以下步驟構(gòu)建應(yīng)用程序:

  1. 提取 ticker.zip 存檔,這將創(chuàng)建名為 ticker 的目錄。
  2. 打開命令 Shell,并將當(dāng)前目錄更改為 ticker
  3. 運(yùn)行 mvn install。這將構(gòu)建應(yīng)用程序,并將輸出 WAR 文件放入 ticker 下的 target 目錄中。WAR 文件的名稱為 ticker.war
  4. 在瀏覽器中打開 Community Edition 控制臺(tái),并導(dǎo)航到 Deploy New Portlet。
  5. Archive 文本框中,輸入所生成 ticker.war 的路徑,并單擊 Install。

測(cè)試 Web 應(yīng)用程序

  1. 在 Web 瀏覽器中打開 http://localhost:8080/ticker,以打開股票報(bào)價(jià)器,如圖 4 中所示。

    圖 4. 瀏覽器中運(yùn)行的股票報(bào)價(jià)器
    顯示正在運(yùn)行的應(yīng)用程序的屏幕截圖

  2. 在 Web 瀏覽器中打開 http://localhost:8080/ticker/comet,以查看 Comet Servlet 的輸出,如圖5 中所示。

    圖 5. Comet Servlet 輸出
    顯示瀏覽器中 Comet Servlet 的輸出的屏幕截圖


結(jié)束語

在本文中,我們通過管理控制臺(tái)創(chuàng)建并配置了嵌入在 Community Edition 中的 Tomcat 實(shí)例的 NIO 連接器。我們還開發(fā)了一個(gè) Java EE Web 應(yīng)用程序,使用 DWR 的 Reverse Ajax 功能將來自服務(wù)器的數(shù)據(jù)通過 NIO 連接器中內(nèi)置的 Comet 支持推送到瀏覽器。最后,我們了解了如何實(shí)現(xiàn) Tomcat 的 CometProcessor 接口來編寫公開其 Comet 功能的 Servlet。

致謝

感謝 Phani Madgula 和 Ashish Jain 對(duì)本文進(jìn)行了審閱。 

    本站是提供個(gè)人知識(shí)管理的網(wǎng)絡(luò)存儲(chǔ)空間,所有內(nèi)容均由用戶發(fā)布,不代表本站觀點(diǎn)。請(qǐng)注意甄別內(nèi)容中的聯(lián)系方式、誘導(dǎo)購(gòu)買等信息,謹(jǐn)防詐騙。如發(fā)現(xiàn)有害或侵權(quán)內(nèi)容,請(qǐng)點(diǎn)擊一鍵舉報(bào)。
    轉(zhuǎn)藏 分享 獻(xiàn)花(0

    0條評(píng)論

    發(fā)表

    請(qǐng)遵守用戶 評(píng)論公約

    類似文章 更多