`

OSGI之生命周期层

    博客分类:
  • OSGI
阅读更多

前言

 

Java模块化编程是将来发展的一种趋势,虽然JDK对模块化编程的支持来得有点晚,但jdk1.9中发布的Jigsaw(或者应该称之为JPMS)终归还是对模块化编程提供了支持。但相比于OSGI来说,JDK1.9毕竟还没有大范围商用,其模块模块化还没有被大范围验证。OSGI已经很多成熟的案例,索引要学习java的模块化编程,建议还是从OSGI开始。上一篇文章对模块层的规范进行了总结,这次继续对生命周期层进行总结。

 

OSGI规范在生命周期层定义一些列接口,用来定义和管理Bundle生命周期。这些API又分为两类:

1、在应用程序外部,生命周期层精确的定义了对Bundle生命周期相关的操作接口,实现对OSGI框架中运行的Bundle进行动态的改变。简单的理解就是生命周期层允许你在执行时从外部安装、启动、更新、停止、卸载Bundle,即可以实现所谓的热更新。

2、在应用程序内部,生命周期层定义了一些Bundle访问执行环境上下文的接口,为Bundle提供了一种与OSGI框架交互的途径以及一些执行时的便利条件。

模块层只是依赖于元数据,而生命周期层主要依赖一些API接口,对Bundle进行操作。

 

OSGI框架在生命周期层中的作用:OSGI框架支持了Bundle的生命周期管理:安装、解析、启动、停止、更新、卸载。

 

如何将Bundle挂接到OSGI框架下呢,通过向元数据配置文件(MANIFEST.MF)中添加Bundle激活器Bundle-Activator,配置方式为:Bundle-Activator: com.sky.osgi.api.ApiActivator。其中ApiActivator是自定义的激活器,继承自org.osgi.framework.BundleActivator。这个接口提供了两个方法startstop,注意这两个方法不是启动和停止Bundle的方法,而是在Bundle的启动和停止发生时,需要执行的操作。有点类似于在Spring中配置init-methoddestroy-method

 

换句话说也就是没有在元数据配置文件中配置激活器,Bundle也是可以正常的启动和停止。激活器只是起到让OSGI框架与Bundle连接起来,提供一些钩子API而已。

 

生命周期层API

 

OSGI规范定义的生命周期层API主要分布在三个接口中(具体的实现交给具体的OSGI框架):BundleActivator(激活器)、BundleContexBundle的上下文对象)、BundleBundle对象本身),下面分别来看下这些API

 

BundleActivator激活器

首先就是上面提到的org.osgi.framework.BundleActivator中定义的startstop方法:

public interface BundleActivator {
    void start(BundleContext var1) throws Exception;
    void stop(BundleContext var1) throws Exception;
}

 

当一个BundleOSGI框架中被安装和启动后,会调用start方法,以便做一些初始化处理;当Bundle被停止后,会调用stop方法做一些相应的清理工作。需要注意的是,每次Bundle被启动时会创建一个BundleActivator实例,Bundle被停止后该BundleActivator实例被丢弃,;如果再重启启动该Bundle,又会创建一个新的BundleActivator实例。也就是说在Bundle启动到停止之间,这些操作都是由OSGI框架自己去保证。

 

BundleActivatorstartstop方法只是把Bundle与框架连接起来,真正实现与框架的交互是由BundleContex--Bundle上下文对象提供的相关API实现。可以看到它是startstop方法的参数,并在这两个方法体内部实现与框架的交互。

 

BundleContex上下文对象

BundleContext只是一个接口类,其中定义的API方法 大致分为两类:

1OSGI框架与Bundle部署和生命周期相关的API

2Bundle之间服务式的交互API

换句话说在BundleContext中即定义了与命周期层相关的API,又定义了与“服务层”相关的API。本次总结的主题是生命周期层,所以本次只关注第一类API,大致如如下方法:

public interface BundleContext extends BundleReference {
  String getProperty(String var1);
 
  Bundle getBundle();
  //安装Bundle到OSGI框架,是Bundle生命周期的入口
  Bundle installBundle(String var1, InputStream var2) throws BundleException;
  //安装Bundle到OSGI框架,是Bundle生命周期的入口
  Bundle installBundle(String var1) throws BundleException;
  //根据id获取Bundle
  Bundle getBundle(long var1);
  //获取框架中所有的Bundle列表
  Bundle[] getBundles();
  //添加Bundle状态变更监听器
  void addBundleListener(BundleListener var1);
  //移除Bundle状态变更监听器
  void removeBundleListener(BundleListener var1);
  //添加框架操作监听器
  void addFrameworkListener(FrameworkListener var1);
  //移除框架操作监听器
  void removeFrameworkListener(FrameworkListener var1);
  //根据url获取Bundle
  Bundle getBundle(String var1);
  //省略其它"服务层"方法
}
 

 

Bundle接口

每个已安装到OSGI框架的Bundle,都对应会生成一个Bundle对象。Bundle接口是OSGI规范定义的一系列操作Bundle对象方法,用于管理已经安装的Bundle的生命周期,

public interface Bundle extends Comparable<Bundle> {
    // Bundle生命周期内不同的状态常量
    int UNINSTALLED = 1;//卸载状态
    int INSTALLED = 2;//已安装状态
    int RESOLVED = 4;//已解析状态
    int STARTING = 8;//启动中
    int STOPPING = 16;//停止中
    int ACTIVE = 32;//激活状态
    //省略其它
    //获取当前状态
    int getState();
    //启动Bundle
    void start(int var1) throws BundleException;
    //启动Bundle
    void start() throws BundleException;
    //停止Bundle
    void stop(int var1) throws BundleException;
    //停止Bundle
    void stop() throws BundleException;
    //更新Bundle
    void update(InputStream var1) throws BundleException;
    //更新Bundle
    void update() throws BundleException;
    //卸载Bundle
    void uninstall() throws BundleException;
    //获取Bundle元数据
    Dictionary<String, String> getHeaders();
    //获取BundleId
    long getBundleId();
    //获取Bundle地址
    String getLocation();
    //获取Bundle元数据
    Dictionary<String, String> getHeaders(String var1);
    //获取Bundle_SymbolicName
    String getSymbolicName();
    //获取Bundle私有空间下的文件
    File getDataFile(String var1);
}
 

 

Bundle对象的唯一标识

 

OSGI规范中有三种方式可以唯一确定一个Bundle

1、在“模块层”元数据中定义的Bundle-SymbolicNameBundle-Version。这个属于静态的 Bundle jar文件识别。

2Bundle在被首次加载时,需要调用BundleContextinstallBundle方法,该方法需要一个Bundle jar所在的地址。通过这个地址可以唯一识别一个已经安装的Bundle对象。在BundleContext中定义了一个根据地址获取Bundle对象的方法:Bundle getBundle(String var1);

3、每个已经安装的Bundle会生成一个bundleId,这个id是从0开始安装Bundle的安装顺序自增的。在OSGI框架中可以通过这个bundleId唯一确定一个Bundle对象。在BundleContext定义了一个根据id获取Bundle对象的方法:Bundle getBundle(long var1);

 

bundleId0Bundle对象是OSGI框架运行时加载的第一个Bundle,也称为系统Bundle”,它随框架的启动而自动加载。当系统Bundle对象停止时,它会首先停止其它所有的Bundle,然后在关闭自己。

 

一个Bundle的生命周期

 

上一节列出了OSGI规范中定义的生命周期层常用的API方法,具体这些方法是如何使用,以及如何控制Bundle的生命周期的呢?这里以摘自《OSGI实战》中的生命周期状态图为例把各个API方法串联起来:



 

 

这个图中描述了一些Bundle的状态,在上图中以椭圆形表示,这些状态值都是在Bundle接口中定义的常量(见上一节);另外状态的转换需要有的需要调用一些方法完成,对应图中的箭头线,有些是框架自己隐式的完成,有些需要调用前一节中提到的生命周期方法才能完成。没有箭头线相连的状态 表示两者之间不能直接到达。下面一步步的来看这些生命周期方法:

 

1、安装方法:BundleContext. installBundle()系列方法,参数可以是一个jar包的路径,也可以是一个输入流。调用该方法,可以向框架中安装一个Bundle,此时会生成一个Bundle对象,状态为INSTALLED(已安装)。

 

2、启动方法:Bundle.start()方法,该方法的调用有一个前提,就是Bundle的已解析(RESOLVED),解析的过程是由框架自己隐式的完成。该方法调用成功后Bundle会进入激活状态(ACTIVE),如果失败回退到已解析状态,这也是有框架隐式的完成状态转换。

3、停止方法:Bundle.stop方法,这个方法会触发Bundle经“停止中”状态 回退到已解析状态。

5、更新方法:Bundle.update方法,最终状态会转到已安装,也就是在启动时需要重新解析。

 

6、卸载方法:Bundle.uninstall方法,可以让一个处于“已安装”的状态转换为卸载状态。如果该Bundle正处于激活状态,OSGI框架会自己调用stop方法停止该Bundle转换为已解析状态,再隐式的转换为已安装状态,最后执行卸载操作,状态变为卸载状态

 

 

 

  • 大小: 131.1 KB
0
0
分享到:
评论

相关推荐

    OSGi入门篇:生命周期层

    这是来自cnblogs博主 静默虚空 的文章 ,为方便离线查看,转存为了pdf

    osgi介绍osgi介绍

    osgi介绍osgi介绍osgi介绍osgi介绍osgi介绍osgi介绍osgi介绍osgi介绍osgi介绍osgi介绍

    OSGi.NET框架 Documentation

    3.生命周期管理 4.服务注册 5.扩展点支持 目前OSGi.NET具有如下特色: 1.组件的可插拔性:组件可根据业务需要在运行时进行装载、卸载操作 2.组件的动态更新:组件在运行时可更新替换当前版本 3.组件的版本隔离...

    osgi生命周期

    osgi的初级教程,适合刚学的人入门,强人就绕行吧,有不足的地方还望包涵

    osgi-core技术文档与说明

    OSGI技术 讲述了osgi的三个模块服务层 模块层 生命周期层 主要介绍了如何进行模块化的开发等等,可以灵活的开发网络模块

    OSGI框架实战

    7.3.4. DS中Component的生命周期.......82 7.3.5. DS中Component的通讯机制.......83 八. 应用OSGI.........84 8.1. 模块化设计...84 8.2. 面向服务的组件模型设计....85 8.3. 动态性设计...85 8.4. 面向接口的开发....

    《OSGi实战》完整中文版

    《 OSGi实战》是学习OSGi的全面指导,利用与架构和开发人员相关...《OSGi实战》面向OSGi规范的使用者,系统、全面、深入地阐述OSGi的重要特性及其使用方法,还介绍了某些技术的低层实现细节,引领读者畅游OSGi的世界。

    论文研究-OSGi框架下基于LDAP的异构遥感服务调用机制研究.pdf

    针对异构遥感算法服务集成方法在元数据和生命周期管理方面的不足,提出了在OSGi框架下基于LDAP的异构服务调用机制。该机制设计了一个异构服务代理,将异构服务封装为OSGi bundle服务,实现服务生命周期管理,并结合...

    OSGI原理与最佳实践

    资源名称:OSGI原理与最佳实践内容简介:国内第一本OSGi图书OSGi国内推广者林昊多年经验的结晶涵盖OSGi从入门到深入的知识体系引领OSGi国内研究和普及本书基于作者多年使用OSGi的经验而编写,涵盖了OSGi从入门到深入...

    深入理解osgi

    深入理解osgi,本书由浅入深的讲解了osgi的发展历程,模块层规范,生命周期层规范,以及基本实现原理,对初学者和从业人员都有不错的指导意义

    利用R-OSGi实现分布式OSGi应用

    利用R-OSGi实现分布式OSGi应用 本文通过介绍传统 OSGi 应用程序及 R-OSGi 的实现方式入手,阐述了 R-OSGi 对于 OSGi 规范的实现方式。然后通过一个简单的功能实现由浅入深地讲述传统 OSGi 和 R-OSGi 上的两种不同...

    OSGI进阶.pdf

    讲OSGI应用的讲OSGI应用的讲OSGI应用的讲OSGI应用的讲OSGI应用的

    OSGI合集 OSGi原理与最佳实践

    网上收集的OSGI资料. 包括: OSGi原理与最佳实践(精选版).pdf OSGI实战和源码.rar osgi进阶.pdf Introduce.OSGi.ppt OSGi.in.action.ppt r4.cmpn.pdf r4.core.pdf r4.enterprise.pdf

    OSGI 入门资料PDF

    OSGI 入门资料PDF,包括OSGI实战、OSGI进阶、OSGI 入门和整合Spring、OSGI原理与最佳实践

    基于OSGi框架之开发环境搭建V_2.0

    基于OSGi框架之开发环境搭建基于OSGi框架之开发环境搭建

    OSGI 实例eclipse插件开发

    OSGI 实例 eclipse 插件开发

    OSGi入门教程(OSGi Introduce)

    OSGi的入门教程,帮助初学者快速了解OSGi的定义、用途及组成。

    OSGI进阶实战教程

    OSGi学习不错的材料 OSGi学习不错的材料 OSGi学习不错的材料 OSGi学习不错的材料

    OSGI进阶--OSGi开发指南

    OSGi开发文档和实践指南,描述了OSGI的开发流程

    osgi,林昊写的osgi实战和进阶

    osgi,林昊写的osgi实战和进阶,学习osgi的好东西,入门的首选。

Global site tag (gtag.js) - Google Analytics