OSGI捆绑包和组件之间有什么区别?

sta*_*ker 13 java eclipse osgi

开始使用osgi,我想知道bundle和组件之间的概念差异是什么.何时使用其中的哪一个.任何指针都是受欢迎的.

编辑:

组件和捆绑包提供不同的接口,因此它们可能不可互换

Von*_*onC 11

一个组件是:

  • 系统的积极参与者
  • 意识到并适应​​其环境
    • environment =其他组件提供的服务
    • 环境=资源,设备,......
  • 可以为其他组件提供服务并使用其他组件提供的服务
  • 有一个生命周期

简而言之:

  • 组件提供服务
  • Bundle管理生命周期

一个bundle只能有一个激活器(需要一个BundleContext),并且可以拥有任意数量的活动组件.
这意味着你可能最终试图将一个与松散相关的问题放入一个激活器中.
这就是为什么通过声明式服务管理这些组件可能更容易,通过SCR("服务组件运行时",这是一个"扩展器包"实现新的和改进的OSGi R4.2 DS - 声明性服务 - 规范).
自OSGi 4.2以来尤其如此,因为现在将DS组件编写为POJO要容易得多:不再需要使用activatedeactivate方法来获取ComponentContext参数.另请参见惰性声明式服务.


注意:

它可以帮助在OSGi的上下文中替换这些术语,并看看"我们如何到达那里"(Neil Bartlett的优秀博客文章)

以下是一些相关的摘录,其中"模块"最终成为OSGi Bundles(管理声明服务的组件):

模块分离

我们的第一个要求是干净地分离模块,以便来自一个模块的类不具有从其他模块中查看和模糊类的不受控制的能力.
在传统的Java中,所谓的"类路径"是一个庞大的类列表,如果多个类碰巧具有相同的完全限定名,那么第一个将始终被找到,第二个和所有其他类将被忽略.

防止不受控制的可见性和模糊类的方法是为每个模块创建一个类加载器.类加载器只能加载它直接知道的类,在我们的系统中它将是单个模块的内容.

模块访问级别

如果我们在这里停止,那么模块将完全隔离并且无法彼此通信.为了使系统实用,我们需要重新添加查看其他模块中的类的能力,但我们是以谨慎和有限的方式进行的.
此时我们输入了另一个要求:模块希望能够隐藏它们的一些实现细节.

我们希望有一个"模块"访问级别,但今天的问题是javac编译器不知道模块边界在哪里.

我们在模块系统中选择的解决方案是允许模块仅"导出"其内容的一部分.如果模块的某些部分未导出,则其他模块无法看到它.

在导入时,我们应该导入我们实际需要使用的内容,无论它来自何处,并忽略碰巧与其一起打包的所有内容.

出口和进口的粒度

OSGi选择包.
Java包的内容有点连贯,但是将包列为导入和导出并不是太繁重,并且它不会破坏任何东西以将一些包放在一个模块中而将其他包放在另一个模块中.
应该是我们模块内部的代码可以放在一个或多个非导出的包中.

包装线

既然我们已经有了模块如何隔离自己然后重新连接的模型,我们可以设想构建一个构建这些模块的具体运行时实例的框架.它将负责安装模块并构建知道其各自模块内容的类加载器.

然后它将查看新安装的模块的导入并尝试查找匹配的导出.

这意味着我们可以动态安装,更新和卸载模块.安装新模块对已解决的模块没有影响,但可能会解决一些以前无法解析的模块.卸载或更新时,框架确切地知道受影响的模块,并在必要时更改其状态.

版本

我们的模块系统看起来很好,但我们还不能处理模块中不可避免的变化.我们需要支持版本.

我们如何做到这一点?首先,导出器可以简单地声明一些有关它正在导出的包的有用信息:"这是API的1.0.0版".导入器现在只能导入与其预期兼容且已编译/测试的版本,并拒绝接受

包装模块和元数据

我们的模块系统需要一种方法来将模块的内容与描述导入和导出的元数据打包到可部署单元中.

所以唯一的问题是,我们应该在哪里放置元数据,即导入和导出列表,版本等等?

实际上,OSGi是在2000年之前设计的,所以它确实选择了这些解决方案中的任何一个.相反,它回顾了JAR文件规范,其中拼写出答案:
META-INF/MANIFEST.MF是任意特定于应用程序的元数据的标准位置.

后期绑定

模块化难题的最后一部分是实现与接口的后期绑定.我认为它是模块化的一个重要特征,即使某些模块系统完全忽略它,或者至少认为它超出了范围.

我们应该寻找一种分散的方法.
我们假设每个模块可以简单地创建对象并将其发布到其他模块可以找到它们的某个地方,而不是被告知上帝类要做什么.我们将这些发布的对象称为"服务",并将它们发布到"服务注册表"的位置.
有关服务的最重要信息是它实现的接口(或接口),因此我们可以将其用作主要注册密钥.
现在,需要查找特定接口实例的模块可以简单地查询注册表并找出当时可用的服务.注册表本身仍然是任何模块之外存在的核心组件,但它不是"上帝"......相反,它就像一个共享的白板.


ome*_*dat 6

在OSGi术语中,"组件"就像运行时服务.每个组件都有一个实现类,并且可以选择实现公共接口,从而有效地提供这种"服务".OSGi的这个方面有时被比作服务注册表模式.

根据定义,OSGi中的组件由bundle提供.捆绑包可以包含/提供多个组件.虽然捆绑包本身可能不提供服务,但组件/声明性服务用于使OSGi更加面向服务.您没有义务使用组件/服务.