我真的很喜欢这个(OSGI),尝试做一些简单的例子。我不能做懒惰的行动。我知道有一些蓝图可以解决这些问题,但在继续之前,我认为学习一些基础知识会很好。
Bundle DataService: Manifest-Version: 1.0 Bundle-Version: 1.0.0 Bundle-Name: DataService Bundle-ManifestVersion: 2 Bundle-Activator: DataService.Activator Import-Package: org.osgi.framework Bundle-SymbolicName: DataService Export-Package: DataService;version="1.0.0" Bundle-ActivationPolicy: lazy Bundle DataServiceClient: Manifest-Version: 1.0 Bundle-Version: 1.0.0 Bundle-Name: DataServiceClient Bundle-ManifestVersion: 2 Bundle-Activator: DataServiceClient.Activator Import-Package: org.osgi.framework, DataService;version="[1.0.0,1.0.0]" Bundle-SymbolicName: DataServiceClient
好的我已经改变了我的代码,但仍然没有运气。
外部应用程序,安装捆绑包,启动框架,然后只启动DataServiceClient捆绑包。 无法访问任何捆绑类。
File bundleDir = new File("./bundles/"); String[] bundleResources = bundleDir.list(); for(String bundleResourcePath : bundleResources) { File bundleResource = new File(bundleDir, bundleResourcePath); InputStream bs =new FileInputStream(bundleResource); mFramework.getBundleContext().installBundle(bundleResource.getName(), bs); } mFramework.start(); bl = mFramework.getBundleContext().getBundles(); for(Bundle b : bl) { if (b.getBundleId() != 0 && b.getSymbolicName().contains("DataServiceClient")) { b.start(); } }
这是DataServiceClient的开始:
System.out.println("DataServiceClient Start"); IDataService service = new DummyService(); System.out.println(service.getData());
这是“DataService”包中的DummyService类。
public class DummyService implements IDataService { @Override public String getData() { return "DummyService Data"; } }
以下是“DataService”捆绑包的开头:
System.out.println("DataService Start");
我得到的输出:
DataServiceClient Start DummyService Data
但我希望看到:
DataServiceClient Start DataService Start DummyService Data
来自http://www.osgi.org/Design/LazyStart
的一点点辞典延迟激活
延迟激活是一种生命周期策略,要求在第一次成功请求从该捆绑中加载类时必须激活捆绑。
然而,由于它不起作用,我想我完全误解了懒惰激活的概念,或者我做错了什么。
除非我明确地为DataService bundle调用start,否则它似乎不会为DataService bundle调用Activator.start。这就是我没有得到的。
你的时间
答案 0 :(得分:1)
您确定,您的Activator确实没有被调用。我经常遇到这样的情况,即激活器被调用但经验丰富且异常,OSGi吞下了它。你可以在Activator.start的第一行尝试println来检查这个。在这种情况下,尝试使用日志记录也很有用。
顺便说一下。使用大写字母命名包非常不寻常。不确定这是否有问题,但我会避免这种情况。
答案 1 :(得分:0)
当您调用DummyClient.GetData()时,不清楚发生了什么。你说它调用DataService包中的一个类,但是如何? DataService是一个普通的bundle,你的代码是主要的Java启动器应用程序,OSGi中没有办法让“外部”应用程序静态依赖普通的bundle。
无论如何,即使你可以这样做,你也可以在启动包之前执行这行代码。在捆绑启动之前,捆绑激活器肯定会不被调用!!我希望你的激活器可以在第36行被调用,即你在每个捆绑包上调用bundle.start()
。
但是真的......你究竟想做什么? Bundle-ActivationPolicy: lazy
标志几乎完全没用。我有八年的OSGi经验,并且由于遗留原因,我们只在Eclipse RCP应用程序中使用过此设置。除非您正在编写Eclipse插件或Eclipse RCP应用程序,否则不应在OSGi中使用Bundle-ActivationPolicy: lazy
。
在OSGi中实现懒惰(或“及时”)实例化的正确方法是使用声明性服务(DS)。当客户端首次尝试调用它们而不是在注册时,DS会发布的所有服务对象都会按需实例化。您无需执行任何特殊操作即可启用此功能。
答案 2 :(得分:0)
关于更改后的代码......您实际上从未启动捆绑DataServiceClient
,因此无法调用其激活器。您已从启动捆绑包的循环中明确地将其排除在外。 OSGi只会调用已使用BundleActivator
启动的捆绑包上的bundle.start()
。
这是一个非常广泛的误解点...... OSGi 永远不会自动启动捆绑,即使启用了Bundle-ActivationPolicy: lazy
标记也是如此。
你打算做的就是按照以下方式启动软件包:
bundle.start(Bundle.START_ACTIVATION_POLICY).
事实上,您为所有捆绑包执行此操作,而不是随意启动捆绑包的子集。
但是,我必须重申我在另一个答案中提出的观点。使用Bundle-ActivationPolicy: lazy
毫无意义,除非您正在开发Eclipse RCP应用程序,在这种情况下,您有时必须将其用于愚蠢的遗留原因。