在 SpringSource dm Server 中部署 GWT 應用程式 - 第 2 部分

工程 | Ben Corrie | 2008 年 11 月 24 日 | ...

介紹

這是描述在 SpringSource dm Server™ 中構建和部署 GWT 應用程式的分步方法的系列部落格中的第二篇。第一篇部落格介紹了從 GWT 示例應用程式建立簡單 WAR 檔案的過程。下一篇部落格將介紹如何將我們在 第 1 部分 中建立的 WAR 檔案轉換為 “共享庫” WAR。這意味著我們將把應用程式的 GWT 依賴項外部化到一個 OSGi 捆綁包中,以便它可以被任意數量的 GWT 應用程式共享。您可以將其視為用 GWT 遠端處理功能擴充套件我們的 dm Server。

第 1 部分 中所述,我在這第二篇部落格文章中沒有使用 Spring 框架,而是專注於 SpringSource dm Server™SpringSource Tool Suite 來部署“純”GWT。

另請參閱 第 1 部分 以瞭解 GWT StockWatcher 示例和我正在使用的軟體的背景資訊。

快速回顧

第 1 部分 中,我們從頭開始將 GWT StockWatcher 示例應用程式構建為一個 Eclipse 專案,然後將程式碼生成到一個動態 Web 專案中,然後將其部署到 dm Server 中。最後,我們將動態 Web 專案匯出到 WAR 檔案中,並在 STS 之外部署它。

這裡描述的分步方法將基於我們在 第 1 部分 中所做的工作,而不是重新開始。我們在 第 1 部分 中所做的唯一要改變的事情是移除對gwt-servlet.jar庫的顯式依賴。

步驟 1:將我們的 GWT 依賴項轉換為 OSGi 捆綁包

首先,再補充一點背景知識。“共享庫”方法的整個概念是使用 OSGi 捆綁包之間的顯式匯入和匯出,在 dm Server 中建立依賴項對映。對於像我們的 StockWatcher 示例這樣的小型 WAR,這大多隻是一個有趣的學術練習。然而,鑑於許多商業 Web 專案以大型 WAR 檔案形式釋出,這些檔案包含數十甚至數百個依賴 jar 檔案,將這些依賴項分解為可共享資源不僅從佔用空間的角度來看有意義,而且還大大減少了應用程式的打包、版本控制和維護的痛苦。

好訊息是,建立這些依賴項的大部分工作已經為您完成。 SpringSource企業捆綁包儲存庫包含大多數常見庫的“捆綁”版本。然而,在撰寫本文時,我們的GWT依賴項是一個您必須自己轉換為捆綁包的庫的示例。幸運的是,Eclipse 3.4使這個過程變得非常簡單。

- 在專案資源管理器中右鍵單擊,選擇“新建”->“其他”->“外掛開發”->“從現有Jar存檔建立外掛”。 - 點選“新增外部”並瀏覽gwt-servlet.jar。 - 點選“下一步”,並將專案命名為“com.google.gwt”。 - 將外掛版本設定為反映GWT版本,在本例中是1.5.3。 - 選擇“分析庫內容並新增依賴項” - 選擇Equinox OSGi框架

點選“完成”,無需切換到外掛開發透檢視。我們只是要直接匯出我們的捆綁包。

現在您應該會看到生成的MANIFEST.MF檔案概覽,其中定義了捆綁包的依賴項。您會在“執行時”選項卡中看到該工具已將所有com.google.gwt..包新增為匯出項。您還會在“依賴項”選項卡中看到它已經發現此捆綁包需要幾個javax.servlet..包和一個junit包。

我們暫時移除JUnit依賴項,因為它在dm Server中預設無法解析。當然,如果需要,我們可以將JUnit捆綁包新增到dm Server以滿足依賴項,或者我們可以透過新增required:=optional來使依賴項可選。選擇junit.framework包,點選“移除”然後儲存。

值得指出的是,這是一種將JAR檔案轉換為捆綁包的粗略方法,不能保證在所有情況下都適用。首先,我們可能不希望所有包都被匯出。更重要的是,有一兩個原始碼級別的陷阱可能在OSGi中表現不佳,例如使用Class.forName()。如有疑問,請始終先訪問SpringSource企業捆綁包儲存庫,而不是嘗試自己建立。

最後,我們需要將我們的外掛專案匯出為OSGi捆綁包。選擇“匯出”->“外掛開發”->“可部署外掛和片段”。選擇一個方便的輸出目錄。

現在我們應該在<export path>/plugins/com.google.gwt_1.5.3.jar中看到一個檔案。下一步是重新命名該檔案,使其與dm Server中其他命名捆綁包的格式一致:只需將下劃線改為破折號com.google.gwt-1.5.3.jar。如果沒有此更改,當前版本的STS將無法識別捆綁包版本。如果您想跳過此步驟,可以在此處下載。

最後,將捆綁包複製到dm Server捆綁包儲存庫<dm Server installation root>/repository/bundles/usr中。此處的所有捆綁包都可以是dm Server中其他捆綁包的依賴項,但重要的是它也將在STS中作為依賴項可見,正如我們將在下一步中看到的那樣。

此時,您可以從工作區中刪除com.google.gwt專案,因為它已經完成了它的目的。

步驟2:將我們的WAR專案遷移到新的OSGi捆綁包

希望您現在已經安裝了dm Server,並在其儲存庫中有一個com.google.gwt-1.5.3.jar

下一步是“破壞”我們的應用程式!

右鍵單擊StockWatcherWar,選擇“屬性”->“Java EE模組依賴項”,取消選擇gwt-server.jar檔案,然後單擊“確定”。我們現在已刪除WAR對GWT的顯式依賴,並給自己造成了一些新問題,其中大部分是編譯錯誤。

因此,我們需要將我們的動態Web專案轉換為dm Server捆綁包,以便它可以顯式匯入新建立的GWT捆綁包所需的依賴項。為此,右鍵單擊StockWatcherWar並選擇“Spring Tools”->“新增OSGi捆綁包專案特性”。您應該注意到該專案現在帶有一個重要的“S”符號,並且MANIFEST.MF也改變了特徵

它已損壞,因為它不像捆綁包清單。讓我們新增一些合理的預設值(您可以剪下並貼上以下內容,或使用選項卡中的欄位)。請注意,您也可以在編輯器中使用ctrl-space來提示您有效的選項。

Manifest-Version: 1.0 Bundle-ManifestVersion: 2 Bundle-Name: com.google.sample.stockwatcher Bundle-SymbolicName: com.google.sample.stockwatcher Bundle-Version: 1.0.0 Bundle-Description: Shared Libraries StockWatcher demo

這解決了一個問題,即我們的捆綁包清單現在看起來是正常的。但是,我們尚未定義對GWT捆綁包的依賴項,因此我們仍然有許多編譯錯誤。

選擇“依賴項”選項卡,然後單擊“新增”。在最上面,您應該看到一個com.google.gwt捆綁包神奇地出現了。現在,重要的是要明白此列表中出現的GWT捆綁包與我們在步驟1中建立的外掛專案無關。如果您從工作區中刪除該專案,該捆綁包仍將出現。它之所以有效,是因為dm Server安裝被設定為專案的執行時,並且工具正在dm Server的儲存庫中查詢您可能希望匯入的任何捆綁包。如果此操作未成功,則表示GWT捆綁包未複製到正確位置,或者WAR專案的執行時未設定為dm Server。在“屬性”->“目標執行時”中檢查後者。

接下來,選擇GWT捆綁包,單擊“確定”,然後儲存清單。現在您應該看到GWT捆綁包已新增到名為“捆綁包依賴項”的新類路徑元素中

您現在應該注意到大多數錯誤已得到解決,但仍有一些懸而未決。這是因為我們的GWT捆綁包依賴於javax.servletAPI,在這些類可用之前,型別層次結構是不完整的。

那麼為什麼我們之前在構建路徑中只有gwt-servlet.jar時沒有遇到這個問題呢?在我們進行更改之前,我們的WAR將拾取其構建路徑上的所有內容,其中包括dm Server目標執行時提供的所有JAR。但是,您可能已經注意到,當我們新增OSGi捆綁包專案性質時,構建路徑上的dm Server JAR消失了。這是因為,透過成為OSGi捆綁包,我們進入了一個不同的依賴關係世界,其中必須明確宣告匯入和匯出。

宣告我們對javax.servletAPI的依賴項只是匯入另一個捆綁包的簡單事情。您會在列表中看到它作為com.springsource.javax.servlet。新增這兩個捆綁包後,儲存清單,現在您應該看到所有錯誤都已解決。太棒了!

如果現在導航到MANIFEST.MF選項卡,我們可以看到所有按鈕操作的效果:清單中有一個綠色的“Import-Bundle”條目。請注意,我們也可以在“Import-Bundle”後輕鬆使用ctrl-space,它會建議所有可能的匯入。

如果您想檢視我的專案,可以在此處下載一個壓縮副本。它包含執行時配置,用於在嵌入式Tomcat的託管模式、dm Server的託管模式下啟動,以及啟動GWT編譯器。請注意,嵌入式Tomcat的託管模式無需修改捆綁包WAR專案即可正常工作。這是因為javax.servletdm Server的包不再在構建路徑上。要使用我的專案,您需要GWT_ROOT_INSTALL變數,並且您可能需要選擇您的dm Server目標執行時例項,如第1部分所述。

步驟3:部署到dm Server

部署我們的“共享庫”應用程式的步驟與第1部分中的步驟7和8完全相同,因此沒有必要再次詳細介紹。當然,關鍵區別在於我們已成功將依賴項分解為可供多個GWT應用程式共享的庫。如果您下載我的StockWatcher共享庫WAR,您會發現它現在是290k,而不是890k。

為了好玩,讓我們深入瞭解一下,看看我們的捆綁包如何互動。

當dm Server啟動時,它會通知您可以使用telnet客戶端訪問其OSGi控制檯

[2008-10-27 16:48:04.266] main                     <SPOF0001I> OSGi telnet 控制檯在埠 2401 上可用。

讓我們開啟一個終端視窗,看看我們能發現什麼

> telnet localhost 2401 嘗試 ::1... 連線到 localhost。跳脫字元是 '^]'。

osgi>

您可以透過輸入help獲取Equinox控制檯可用的命令列表。還有一個有用的DeveloperWorks文章,您可以在此處閱讀。

輸入ss會給我們一個所有正在執行的外掛的列表

osgi> ss

框架已啟動。

id    狀態       捆綁包 . . . . 73    ACTIVE      com.google.sample.stockwatcher_1.0.0 74    ACTIVE      com.google.gwt_1.5.3

輸入包74提供了GWT捆綁包的所有匯出包。它顯示所有匯出包都由StockWatcherWar捆綁包匯入。這是我們使用“Import-Bundle”的結果。實際上,我們的StockWatcherWar實際需要的包只有com.google.gwt.user.client.rpc還是com.google.gwt.user.server.rpc。如果需要,我們可以透過使用“Import-Package”更具選擇性地顯式匯入這些包。這在dm Server程式設計師指南中有所描述。

file:////Users/bcorrie/dmServer-1.0.0/springsource-dm-server-1.0.0.RELEASE/work/com.springsource.server.deployer/Module/StockWatcherWar.war-0/StockWatcherWar.war [73] 匯入 com.google.gwt.i18n.client.constants; version="0.0.0"<file:////Users/bcorrie/dmServer-1.0.0/springsource-dm-server-1.0.0.RELEASE/repository/bundles/usr/com.google.gwt-1.5.3.jar [74]>

步驟4:在共享庫上部署其他GWT應用程式

值得注意的是,並非所有GWT應用程式都需要使用gwt-servlet.jar。只有使用某種形式的遠端處理的GWT應用程式才依賴此庫。Google在其發行版中提供了許多示例應用程式,其中大部分只生成javascript和html,因此無需Java程式碼即可部署。將這些示例轉換為WAR檔案很簡單,只需按照第1部分步驟5所述,將編譯指令碼執行到一個動態Web專案中,然後建立一個合適的web.xml。

然而,GWT發行版中包含的一個使用簡單遠端處理的示例名為DynaTable。我使用這些部落格中描述的相同步驟和原理,將此示例轉換為共享庫WAR檔案。要檢視我所做的工作,您可以下載壓縮的專案WAR檔案並檢視。這非常簡單地演示了在dm Server中執行多個應用程式的原理,這兩個應用程式都共享我們建立的GWT捆綁包。

展望第三部分

在本系列的最後一篇部落格中,我們將進一步模組化我們的StockWatcher示例,將其服務抽象為可以熱插拔進出執行伺服器的捆綁包。

獲取 Spring 新聞通訊

透過 Spring 新聞通訊保持聯絡

訂閱

領先一步

VMware 提供培訓和認證,助您加速進步。

瞭解更多

獲得支援

Tanzu Spring 提供 OpenJDK™、Spring 和 Apache Tomcat® 的支援和二進位制檔案,只需一份簡單的訂閱。

瞭解更多

即將舉行的活動

檢視 Spring 社群所有即將舉行的活動。

檢視所有