我正在使用Felix作为嵌入式应用程序,如中所述, How to start and use Apache Felix from code?。我想要做的是通过OSGi从我的宿主应用程序动态加载jar文件并调用实现类的方法。
所以我有三个maven项目
1)具有界面的maven项目。并导出此接口的包。 ---> ProjA。
2)实施项目 - > ProjB,另一个maven项目,它将ProjA作为maven依赖项导入,并使用具体类在其上实现接口。同样在这个项目中,我为ProjA接口包做了OSGi import-package。在这里,我通过激活器在OSGI上注册我的实现。
3)然后ProjC是托管应用程序。我在那里做的是,
HostActivator activator = new HostActivator();
List<Object> list = new LinkedList<Object>();
list.add(activator);
map.put(FelixConstants.SYSTEMBUNDLE_ACTIVATORS_PROP, list);
Felix f = new Felix(map);
f.start();
Bundle a = f.getBundleContext().installBundle("file:C:/ProjA.jar");
Bundle b = f.getBundleContext().installBundle("file:C:/ProjB.jar"); ); // dirty path ;)
b.start();
ServiceReference sr = activator.getContext().getAllServiceReferences(MyInterface.class.getName(), "(" + "osgi-device-name" + "=*)")[0];
MyInterface dictionary = (MyInterface) activator.getContext().getService(sr);
dictionary.doAction();
一切正常,直到施放。在那里,我可以看到以下错误,
Exception in thread "main" java.lang.ClassCastException: projB.MyImplementation cannot be cast to projA.MyInterface
at MyHostApplication.MyMainClass.main(MyMainClass.java:70)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
任何人都可以帮我这个,对我而言,这似乎是felix的一个错误。
答案 0 :(得分:2)
ProjA位于主项目的类路径中(打开嵌入的OSGi容器),它也作为捆绑包安装到嵌入式OSGi容器中。解析ProjB后,它会连接到ProjA软件包,因此它实现了来自已安装的projA软件包的接口。
当您尝试转换结果对象时,您尝试转换为主项目的类路径上的接口。这是ProjB捆绑实现的另一个接口,因为它实现了projA bundle的接口。
您不应将ProjA作为捆绑包安装到OSGi容器中。您应确保ProjB捆绑包可以解析。为此,您应将 projA 作为系统包添加到嵌入式OSGi容器中。
答案 1 :(得分:0)
another way to solve this problem is using export tag in maven maven-bundle-plugin or manifest file
<build>
<plugins>
<plugin>
<groupId>org.apache.felix</groupId>
<artifactId>maven-bundle-plugin</artifactId>
<extensions>true</extensions>
<configuration>
<instructions>
<Embed-Dependency>*;scope=compile|runtime</Embed-Dependency>
<Export-Package>come.example.myInterface</Export-Package>
<Bundle-Activator>come.example.Activator</Bundle-Activator>
</instructions>
</configuration>
</plugin>
</plugins>
</build>
and did'nt forget
map.put(Constants.FRAMEWORK_SYSTEMPACKAGES_EXTRA, "come.example.myInterface; version=0.0.1");