)利用 Eclipse 開發基於 OSGi 的 Bundle 應用

來源:互聯網
上載者:User
引用:http://www.ibm.com/developerworks/cn/opensource/os-ecl-osgibdev/
開放服務網關協議 (Open Services Gateway Initiative),簡稱 OSGi,為網路服務定義了一個標準的、面向服務的計算環境,為使用者提供了開放的、面向服務元件的、易於部署的編程模型,這個編程模型允許使用者將定義好的 介面規範綁定到 OSGi 運行環境中的特定Service,在構件 SOA 面向服務為中心的公司專屬應用程式的過程中,OSGi 技術正發揮越來越重要的作用。在本文中,將介紹 OSGi 的概念和體繫結構,並且利用 Eclipse 3.2 開發一個基於 OSGi 規範的服務應用 Bundle。通過學習本文,讀者可以瞭解到如何開發和部署基於 OSGi 規範的 Bundle 應用。

OSGi 規範簡介

OSGi 聯盟建立於 1999 年,是一個非贏利機構,旨在建立一個開放的服務規範。OSGi 規範為網路服務定義了一個標準的、面向組件的計算環境,它最初的目的就是為各種嵌入式裝置提供通用的軟體運行平台,屏蔽裝置作業系統與硬體區別的中介軟體平 台,通過這個平台,可以對不同軟體商提供的應用(OSGi 中稱為 Bundle)進行組件的生命週期管理的能力,如應用組件可以從運行中被安裝、升級或者移除而不需要中斷裝置的操作,應用組件可以動態發現和使用其他庫 或者應用程式。由於 OSGi 技術具有服務元件模組化、動態載入應用等優點,正被越來越多的領域關注,如嵌入裝置製造業、汽車製造業、公司專屬應用程式等。目前,OSGi 聯盟發布的最新的 OSGi 服務規範為 4.0,讀者可以查閱參考資料瞭解詳細資料。



回頁首

OSGi 體繫結構

OSGi 的體系架構是基於外掛程式式的軟體結構,包括一個 OSGi 架構和一系列外掛程式,在 OSGi中,外掛程式稱為 Bundle,其中,OSGi 架構規範是 OSGi 規範的核心部分,它提供了一個通用的、安全可管理的 Java 架構,通過這個架構,可以支援 Bundle 服務應用的部署和擴充。Bundle 之間可以通過 Import Package 和 Require-Bundle 來共用 Java 類,在 OSGi 服務平台中,使用者通過開發 Bundle 來提供需要的功能,這些 Bundle 可以動態載入和卸載,或者根據需要遠程下載和升級。OSGi 體繫結構圖 1 所示:

圖示1 OSGi 體繫結構

其中:

Execution Environment:

Bundle 應用所倚賴啟動並執行 Java 執行環境,如 J2SE-1.4、CDC-1.0 等都是可用的執行環境。

Modules:

模組層定義了 Bundle 應用的載入策略。OSGi 架構是一個健壯並且嚴格定義的類載入模型。在大多數 Java 應用中,通常只有一個單獨的 ClassPath,它包含了所有的 Java 類檔案和資源檔,OSGi基於Java技術,對於每個實現了 BundleActivator 介面的 Bundle 應用,為它產生一個單獨的 ClassLoader,使得 Bundle 應用的組織更加模組化。

Life Cycle:

生命週期層可以動態地對 Bundle 進行安裝、啟動、停止、升級和卸載等操作。該層基於模組層,提供了一組 API 來控制 Bundle 應用的運行時操作。

Service Registry 和 Services:

OSGi 服務層定義了一個整合在生命週期層中的動態協作模型,是一個發布、動態尋找、綁定的服務模型。一個服務通常是一個 Java 對象實現了特定的服務介面,並且通過服務註冊,被綁定到 OSGi 的運行環境中。Bundle 應用可以註冊發布服務,動態綁定服務,並且在服務註冊狀態改變時,可以接受到事件訊息等。

Security:

OSGi 的安全管理是基於 Java2 安全體系的,貫穿在 OSGi 平台的所有層中,它能夠對部署在 OSGi 運行環境中的 Bundle 應用進行詳細的管理控制。



回頁首

Bundle 生命週期的狀態

在一個動態擴充的 OSGi 環境中,OSGi 架構管理 Bundle 的安裝和更新,同時也管理 Bundle 和服務之間的依賴關係。一個 Bundle 可能處於以下六個狀態, 2 所示:

圖示 2 Bundle 狀態圖

INSTALLED:安裝完成,本地資源成功載入。

RESOLVED:依賴關係滿足,這個狀態意味該Bundle要麼已經準備好運行,要麼是被停止了。

STARTING:Bundle正在被啟動,BundleActivator的start()方法已經被調用但是還沒有返回。

STOPPING:Bundle正在被停止,BundleActivator的stop()方法已經被調用但是還沒有返回。

ACTIVE:Bundle 被成功啟動並且在運行。

UNINSTALLED:bundle被卸載並且無法進入其他狀態。

Bundle介面定義了getState()方法來返回Bundle的狀態。



回頁首

OSGi 標準服務

在 OSGi 平台之上,OSGi 聯盟定義了很多服務。服務是由一個 Java Interface 來定義的,Bundle 可以實現這個介面並且把服務註冊到服務註冊表中去,使用者可以從註冊表中找到需要的服務來使用,並且可以響應特定服務的狀態改變,如服務註冊和服務取消。下 面簡單介紹一下 OSGi Release 4 的一些主要服務。OSGi 架構提供了許可權管理服務,包管理服務和最初載入系統服務。這些服務是 OSGi 架構的一部分並且管理著 OSGi 架構的運作。

Permission Admin Service:許可權管理是指 Bundle 是否許可其他的 Bundle 的代碼。當前的或者其他的 Bundle 的許可權可以通過這個服務來操作,一旦被設定許可權,馬上就生效。 Package Admin Service:Bundle 之間可以共用包內的 Java 類和資源,bundle 的更新可能需要 OSGi 架構重新解析 Bundle 之間的依賴關係,這個服務提供了 OSGi 服務平台中包的共用狀態資訊。

Start Level Service:Start Level是指一些在特定Bundle起動之前必須運行或者初始化的一系列 bundle。Start Lever Service 可以設定當前OSGi服務架構初始的Start Level,並且可以指定和查詢特定Bundle的Start Level。



回頁首

使用 Eclipse 開發 Bundle 應用

Equinox 架構是 Eclipse 組織基於 OSGi Release 4 的一個實現架構,它實現了 OSGi 規範的核心架構和許多標準架構服務的實現。關於Equinox項目的詳細資料,請查閱參考資料資訊。在本文中,我們使用 Eclipse 3.2 平台開發兩個基於 OSGi 的 Bundle 應用,其中第一個 Bundle 應用聲明、實現並註冊了一個姓名查詢服務,用於判斷所給姓名是否在已定義的查詢列表中;第二個 Bundle 應用查詢並引用第一個 Bundle 應用所註冊的姓名查詢服務,如果使用者所給的姓名包含在查詢列表中,將返回正確的資訊,最後,將開發的 Bundle應用部署的 Equinox OSGi 架構中,使用者可以在 OSGi 控制命令列中輸入命令來查詢關於架構和 Bundle 應用的具體資訊。讀者可以從參考資料中獲得本文 Bundle 應用的原始碼。

(1)建立 Plug-in Project,在 Eclipse 3.2 開發環境中,從功能表列選擇 File > New > Project... ,開啟 New Project 嚮導,可以看到有Plug-in Project建立嚮導,建立一個Plug-in 項目。項目名為 example 的 Bundle 應用,該應用實現並註冊了一個姓名查詢服務,實現了 BundleActivator 介面。選擇 Equinox 架構作為 Bundle 應用啟動並執行 OSGi 服務平台。

圖示 3 Plug-in 項目嚮導

(2)實現OSGi服務通常需要兩個步驟,首先定義所提供服務的介面,然後實現這個服務介面。在本例中,我們建立一個姓名查詢服務用來查詢所給姓名是否有效。首先定義姓名查詢介面NameService.java。下面是該介面的原始碼:

NameService Interface 原始碼

package example.service;
/**
* A simple service interface that defines a name service.
* A name service simply verifies the existence of a Name.
**/
public interface NameService {
/**
* Check for the existence of a Name.
* @param name the Name to be checked.
* @return true if the Name is in the list,
* false otherwise.
**/
public boolean checkName(String name);
}

該服務介面很簡單,只包含一個需要實現的方法。為了將服務介面和服務實現相分離,方便其他 Bundle 引用該服務,我們通常需要將該服務介面單獨放在一個包內,本例中,存放NameService.java 介面的 Java 包為 example.service。接下來,需要實現 NameService 介面,並且註冊該服務。在本例中,我們用內部類實現了該介面,下面是該 Bundle 應用的部分原始碼。

Example Bundle部分原始碼

public void start(BundleContext context) throws Exception {
Properties props = new Properties();
props.put("ClassRoom", "ClassOne");
context.registerService(NameService.class.getName(), new NameImpl(),
props);
}
private static class NameImpl implements NameService {
// The set of names contained in the arrays.
String[] m_name = { "Marry", "John", "David", "Rachel", "Ross" };
/**
* Implements NameService.checkName(). Determines if the passed name is
* contained in the Array.
*
* @param name
* the name to be checked.
* @return true if the name is in the Array, false otherwise.
*/
public boolean checkName(String name) {
// This is very inefficient
for (int i = 0; i < m_name.length; i++) {
if (m_name[i].equals(name)) {
return true;
}
}
return false;
}
}

在start()方法中,利用BundleContext註冊一個姓名查詢服務,並且為該服務設定相關屬性以便服務查詢。在實現姓名查詢服務時,我們簡單定義了一個靜態數組用於存放有效姓名資訊。

(3)定義Bundle描述檔案MANIFEST.MF,Bundle應用example的MANIFEST.MF檔案如下:

MANIFEST.MF檔案資訊

Manifest-Version: 1.0
Bundle-ManifestVersion: 2
Bundle-Name: Example Bundle
Bundle-SymbolicName: example
Bundle-Version: 1.0.0
Bundle-Activator: example.osgi.Activator
Bundle-Localization: plugin
Import-Package: org.osgi.framework;version="1.3.0"
Export-Package: example.service

其中,Bundle-Activator屬性指明了實現BundleActivator介面的類,該類用來啟動和停止Bundle應用。Export-Package屬性指定了該Bundle輸出的共用包,該屬性可以使其他的Bundle應用引用我們所定義的服務介面。

(4)建立項目名為exampleClient的Bundle應用,該應用在OSGi平台上查尋並引用example Bundle應用已經註冊的姓名查詢服務,然後從標準輸入讀入使用者所輸入的姓名資訊,判斷所輸入姓名是否有效。exampleClient應用的部分源代 碼如下,讀者可從參考資料中獲得完整原始碼。

ExampleClient Bundle部分原始碼

public void start(BundleContext context) throws Exception {
ServiceReference[] refs = context.getServiceReferences(
NameService.class.getName(), "(ClassRoom=*)");
if (refs != null) {
try {
System.out.println("Enter a blank line to exit.");
BufferedReader in = new BufferedReader(new InputStreamReader(
System.in));
String name = "";
// Loop endlessly.
while (true) {
// Ask the user to enter a name.
System.out.print("Enter a Name: ");
name = in.readLine();
// If the user entered a blank line, then
// exit the loop.
if (name.length() == 0) {
break;
}
// First, get a name service and then check
// if the name is correct.
NameService nameservice = (NameService) context
.getService(refs[0]);
if (nameservice.checkName(name)) {
System.out.println("The Name is Correct.");
} else {
System.out.println("The Name is Incorrect.");
}
// Unget the name service.
context.ungetService(refs[0]);
}
} catch (IOException ex) {
}
} else {
System.out.println("Couldn't find any name service...");
}
}


回頁首

Bundle的部署及運行

在Eclipse平台中,選擇File-->Export...菜單,將開發的example和exampleClient兩個Bundle 應用匯出成Jar檔案,以便將它們部署到OSGi服務平台中。選擇將要啟動並執行Bundle應用,滑鼠右鍵點擊,在快顯功能表中,選擇Run AS-->Equinox FrameWork來啟動OSGi服務平台。在Equinox啟動配置控制台中,可以為Bundle應用設定預設的Start Level和Bundle應用是否需要自動啟動等選項。在本例中,為了講解如何安裝及啟動Bundle應用,只將example Bundle應用設為自動啟動,而exampleClient Bundle應用需要我們用命令安裝及啟動。

當OSGi Equinox FrameWork啟動後,在OSGi控制命令台中輸入ss命令,可以查看OSGi服務平台中已經安裝的Bundle應用資訊及其狀態。4所示,可以 看到當前OSGi服務平台中有兩個Bundle處於Active狀態,其中,system.bundle_3.2.0.v20060328為OSGi架構 的系統Bundle,而example_1.0.0為註冊姓名查詢服務的Bundle應用,1.0.0為Bundle應用的版本號碼。

圖示4 Bundle資訊查詢

在OSGi控制命令台中利用install命令安裝exampleClient Bundle應用,用ss命令查看安裝後的Bundle應用資訊及其狀態。5所示:

圖示5 安裝Bundle

在OSGi控制命令台中利用start命令安裝exampleClient Bundle應用,使用者可輸入姓名,利用姓名查詢服務來判斷所輸入姓名是否有效,用ss命令查看啟動後的Bundle應用資訊及其狀態。6所示:

圖示6 啟動Bundle

使用者在在OSGi控制命令台中,可利用stop命令來停止指定的Bundle應用,close命令用來停止並退出OSGi控制命令台。關於OSGi Equinox FrameWork控制台命令的詳細資料,可查看參考資料。



回頁首

總結

OSGi服務架構提供了開放的、面向服務的、易於部署的編程模型,在構件面向服務為中心的公司專屬應用程式的過程中,OSGi 技術正發揮越來越重要的作用。目前,Eclipse 3.2 體系架構是參照OSGi實現的,Equinox架構是 Eclipse 組織基於OSGi Release 4 的一個實現架構,它實現了OSGi 規範的核心架構和許多標準架構服務。在本文中,我們利用Eclipse 平台開發了兩個Bundle應用,並且在Bundle應用中,聲明、實現、註冊並引用了一個簡單的服務,最後,將Bundle應用部署到Equinox OSGi服務架構中。通過本文,讀者可以瞭解如何開發和部署基於OSGi規範的Bundle應用。



回頁首

下載

名字 大小 下載方法
example.zip 8KB HTTP

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.