I have a very simple service provider and consumer. For some reason I cannot solve the problem that my consumer would use provider's service. Here is the bundle source code for provider:
package test;
import org.osgi.framework.BundleContext;
import org.osgi.service.component.ComponentContext;
import org.osgi.service.component.annotations.Activate;
import org.osgi.service.component.annotations.Component;
import org.osgi.service.component.annotations.Deactivate;
@Component (name = "MyProvider", immediate = true)
public class TestClass implements SimpleMathI {
public TestClass() {
System.out.println("contructing TestClass");
}
@Activate
protected void activate(ComponentContext c, BundleContext b) {
System.out.println("activate testClass ");
}
@Deactivate
protected void deactivate() {
System.out.println("de-activate testClass");
}
@Override
public void doSimpleAdd(int x, int y) {
System.out.println("Result(TestClass): " + (x + y));
}
@Override
public void doSimpleSubstract(int x, int y) {
System.out.println("Result(TestClass): " + (x - y));
}
}
It registers component MyProvider and the service test.SimpleMathI (listed in karaf)
Here is the consumer:
If I do not reference service SimpleMathI, but only ConfigurationAdmin it works fine!
package test;
import org.osgi.framework.BundleContext;
import org.osgi.service.cm.ConfigurationAdmin;
import org.osgi.service.component.ComponentContext;
import org.osgi.service.component.annotations.Activate;
import org.osgi.service.component.annotations.Component;
import org.osgi.service.component.annotations.ConfigurationPolicy;
import org.osgi.service.component.annotations.Deactivate;
import org.osgi.service.component.annotations.Reference;
@Component (name = "MyConsumer", immediate = true, configurationPolicy = ConfigurationPolicy.OPTIONAL)
public class TestClass2 {
public TestClass2() {
System.out.println("contructing TestClass2");
}
@Reference (bind = "bind", unbind = "unbind")
ConfigurationAdmin cm; // works
@Reference (bind = "bindSimpleMathI", unbind = "unbindSimpleMathI")
SimpleMathI simpleMath; // does not work, see screenshot
@Activate
protected void activate(ComponentContext c, BundleContext b) {
System.out.println("activate testClass2");
// simpleMath.doSimpleAdd(20, 25);
}
@Deactivate
protected void deactivate() {
System.out.println("de-activate testClass2");
}
protected void bind(ConfigurationAdmin a) {
System.out.println("binding");
}
protected void unbind(ConfigurationAdmin a) {
System.out.println("un-binding");
}
protected void bindSimpleMathI(SimpleMathI a) {
System.out.println("binding!!");
}
protected void unbindSimpleMathI(SimpleMathI a) {
System.out.println("un-binding!!");
}
}
and here is the output in Karaf webconsole.
I googled enough, but still can't figure out what I missed. Strange, since the code is very simple and transparent. So, what I implemented wrong provider or consumer?
Karaf 4.0.7, no Apache felix used, pure OSGi R6 declarative services
I think you did a simple error. In OSGi you should not have two bundles with the same package.
A typical setup in OSGi is to have three packages:
You can either put both test.api and test.impl in the same bundle or have a separate api bundle.
In any case the consumer should not embed the interface package into its own bundle. Instead it should have an Import-Package in its Manifest for the api package.