如何避免OSGi中的class.forName()?

时间:2011-07-07 14:58:21

标签: java reflection osgi

我对OSGi和我们的部门相对较新。正在转向OSGi框架。我有两个捆绑A和B. B依赖于A所以我将它作为Import-Package包含在B的清单文件中:A。

另外,我在A中有一个类,它使用反射从B访问某个类。 A中的类使用class.forName(B中的类)。我想摆脱这种反思,因为当我转向OSGi框架时,这可能会导致问题。我怎样才能摆脱这个class.forName()?

谢谢!

3 个答案:

答案 0 :(得分:4)

在OSGi中,你会想远离反思,原因很多其他地方都有。

所以,你的情况是bundle A需要一个驻留在bundle B中的类的实例。要让A理解这个实例,我会假设它有一些用于与实例通信的接口。让我们更具体一点。

/Bundle A
  /ThingyInterface.class

/Bundle B
  /ThingyImplementation.class (implements ThingyInterface.class)

这是一种常规模式:一个包提供一个接口,另一个包提供实现。现在有两种可能的情况,

  • A只需要一份实现副本。在这种情况下,请将Thingy注册为服务。
  • A需要多个实施实例。在这种情况下,在ThingyFactory中引入A,并在B中创建该工厂的实现,然后将其注册为服务。

在任何一种情况下,你让B进行实际的实例化,你没有从AB的依赖,而B不需要反射来实例化对象。

简而言之,服务是您的朋友

答案 1 :(得分:0)

在我看来,有两种在Java中创建对象的方法

  1. 通过新
  2. 致电建设者
  3. 使用反射
  4. 因此,如果你想避免反射,你只能导入bundle A中的class,然后导入new()实例(为了做到这一点,你需要在bundle A中引入B)。但是由于bundle B alreadys依赖于A,这将导致OSGi中不允许的交叉依赖。所以我建议你重构你的类来从bundle A中提取这样的代码并移动到bundle B.

答案 2 :(得分:0)

我不知道你确切的用例,但听起来你有一些意大利面。你说Bundle B依赖于A,但A必须通过反射从B加载一个类。这意味着A也依赖于B.既然你不能拥有B - > A - > B,您需要删除其中一个依赖项。

或许您需要另一个包C,其中包含A和B共有的任何类。请记住,OSGi可以帮助您创建具有干净接口的模块。如果你发现自己在使用OSGi时遇到了麻烦,可能是因为某些抽象漏洞或某些依赖关系设计得不好。