4

我有一个带有捆绑包的 OSGI 应用程序,需要 2 个版本的 IBM MQSeries:6.0.2 和 7.0.1。我们安装了以下 IBM MQ 捆绑包(仅提及主要捆绑包)

  • com.ibm.mq.osgi.client_6.0.2.5.jar
  • com.ibm.msg.client.osgi.wmq_7.0.1.5.jar

我们将 2 个 Bundle 定义为 Require-Bundle 如下(是的,我知道,我们应该使用 import-package ;-)) Bundle ARequire-Bundle: com.ibm.msg.client.osgi.wmq;bundle-version="7.0.1"

捆绑 BRequire-Bundle: com.ibm.mq.osgi.client;bundle-version="[6.0.2,7.0.0)"

我们另外定义org.osgi.framework.bootdelegation=javax.*。没有伙伴类加载,没有动态类加载。

现在,当 Bundle A 加载com.ibm.mq.jms.MQQueueConnectionFactoryusing

final MQQueueConnectionFactory connectionFactory = new MQQueueConnectionFactory();

我希望 Equinox 从 Bundle 加载类com.ibm.msg.client.osgi.wmq_7.0.1.5。不是这种情况 !?!??MQQueueConnectionFactory 是从 Bundle 加载的com.ibm.mq.osgi.client_6.0.2.5

因此,Bundle A 使用的是 MQ 6.0.2.5..

设置一些 Equinox 调试选项,我可以看到以下内容:

Bundle id 56 == com.ibm.mq.osgi.client_6.0.2.5
Bundle id 53 == com.ibm.msg.client.osgi.jms.prereq_7.0.1.5

[...]
BundleLoader[A_1.1.3].loadBundleClass(com.ibm.mq.jms.MQQueueConnectionFactory)
BundleLoader[com.ibm.mq.osgi.client_6.0.2.5].findLocalClass(com.ibm.mq.jms.MQQueueConnectionFactory)
BundleClassLoader[PATH/org.eclipse.osgi/bundles/56/1/.cp/com.ibm.mq.jar].findClassImpl(com.ibm.mq.jms.MQQueueConnectionFactory)
BundleClassLoader[PATH/org.eclipse.osgi/bundles/56/1/.cp/com.ibm.mqjms.jar].findClassImpl(com.ibm.mq.jms.MQQueueConnectionFactory)
  about to read 11659 bytes from com/ibm/mq/jms/MQQueueConnectionFactory.class
  read 11659 bytes from PATH/org.eclipse.osgi/bundles/56/1/.cp/com.ibm.mqjms.jar/com/ibm/mq/jms/MQQueueConnectionFactory.class
  defining class com.ibm.mq.jms.MQQueueConnectionFactory
[...]

“有趣”的部分是 javax.jms.* 类是从中加载的 com.ibm.msg.client.osgi.jms.prereq_7.0.1.5

BundleClassLoader[com.ibm.mq.osgi.client_6.0.2.5].loadClass(javax.jms.QueueConnectionFactory)
BundleLoader[com.ibm.mq.osgi.client_6.0.2.5].loadBundleClass(javax.jms.QueueConnectionFactory)
BundleLoader[com.ibm.msg.client.osgi.jms.prereq_7.0.1.5].findLocalClass(javax.jms.QueueConnectionFactory)
BundleClassLoader[PATH/org.eclipse.osgi/bundles/53/1/.cp/jms.jar].findClassImpl(javax.jms.QueueConnectionFactory)
  about to read 371 bytes from javax/jms/QueueConnectionFactory.class
  read 371 bytes from /opt/fxportal/FXMB/application/configuration/org.eclipse.osgi/bundles/53/1/.cp/jms.jar/javax/jms/QueueConnectionFactory.class
  defining class javax.jms.QueueConnectionFactory
BundleLoader[com.ibm.msg.client.osgi.jms.prereq_7.0.1.5] found local class javax.jms.QueueConnectionFactory

恕我直言,这与org.osgi.framework.bootdelegation设置有关,并且 7.0.1.5 JMS 先决条件发生在 6.0.2.5 之前。

有人可以解释捆绑类加载器的行为吗?为什么 Equinox 以这种方式连接束 A?我怎样才能达到预期的行为?

Bundle B 正在按预期工作......

4

2 回答 2

0

如果这是一个有效的答案,请不要尝试在 BUndle A version="[7.0.1,7.0.1]" 中定义依赖项时使用此格式,这表示严格的版本范围。更糟糕的情况是,如果您仍然遇到问题,您可以通过执行 Platform.getBundle("com.ibm.msg.client.osgi.wmq").loadClass("com.myclass") 直接从 Bundle 加载类?

于 2012-11-15T20:22:26.083 回答
0

当我在 IDE 中使用 OSGi 相关编码时,我遇到了类似的情况。由您的 IDE 完成的这种接线是错误的。当您期望它连接com.ibm.mq.osgi.client_6.0.2.5同一类的com.ibm.msg.client.osgi.wmq_7.0.1.5. 在您谈到的第二个问题中,同样的问题正在发生。您可以通过查找com.ibm.mq.jms.MQQueueConnectionFactoryIDE 使用它的类来检查这一点。(您可以使用 Ctrl + 鼠标单击查看已连接的版本)。

于 2012-11-22T04:23:40.933 回答