[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [List Home]
Re: [p2-dev] Service ranking and p2's IAgentServiceFactory.

I think you incorrectly configures *service.ranking* property in your service definition. OSGi will sort them by default by sequence of loading their bundles.

P2 is searching services via OSGi API that would sort the service implementations by their ranking.

Our product registers a customized profile registry in similar way, it works well on Eclipse 3.6, 3.7 and 3.8.

I paste the DS definition below,

<scr:component xmlns:scr="http://www.osgi.org/xmlns/scr/v1.1.0"; name="WR Profile Registry">
<implementation class="com.windriver.p2.installer.internal.services.ProfileRegistry"/>
<property name="p2.agent.servicename" type="String" value="org.eclipse.equinox.p2.engine.IProfileRegistry"/>
<provide interface="org.eclipse.equinox.p2.core.spi.IAgentServiceFactory"/>
<property name="service.ranking" type="Integer" value="99"/>

Mengxin Zhu

On 08/01/2012 04:08 AM, Carlos O'Donell wrote:

I've been tracking down a problem that has to do with upgrades of our product
and I've been left scratching my head.

My immediate question is:

Does the default IProvisioningAgent honour service.ranking when looking for UIServices?

Problem Background

In our product we have a custom authentication dialog that we
use for authentication when a customer connects to our private p2 repo.

We use the org.eclipse.equinox.p2.core.UIServices service to register our own
implementation of an org.eclipse.equinox.p2.core.spi.IAgentServiceFactory.
When registering the service we set the service.ranking to 255 to ensure that
our service is selected above the default.

<?xml version="1.0" encoding="UTF-8"?>
<scr:component xmlns:scr="http://www.osgi.org/xmlns/scr/v1.1.0"; name="com.codesourcery.portal.ide.PortalServiceUIComponent">
	<property name="service.ranking" type="Integer">255</property>
	<implementation class="com.codesourcery.portal.ide.PortalServiceUIComponent"/>
		<provide interface="org.eclipse.equinox.p2.core.spi.IAgentServiceFactory"/>
	<property name="p2.agent.servicename" type="String" value="org.eclipse.equinox.p2.core.UIServices"/>

In a normal install of our product the service we install works just fine.

However, after an upgrade the default service and default authentication
dialog start being used.

This is because:

(a) The bundle ID order is different. After the upgrade we are at a lower
     bundle ID e.g.

osgi> ss
127     ACTIVE      org.eclipse.equinox.p2.core_2.1.0.v20110502-1955
316     <<LAZY>>    com.codesourcery.portal.ide_1.0.0.376509

(b) The code in the default ProvisioningAgent uses an OSGi API that doesn't
     take into account the service.ranking.

			//attempt to get factory service from service registry
			Collection<ServiceReference<IAgentServiceFactory>> refs;
			try {
				refs = context.getServiceReferences(IAgentServiceFactory.class, "(" + IAgentServiceFactory.PROP_CREATED_SERVICE_NAME + '=' + serviceName + ')'); //$NON-NLS-1$
			} catch (InvalidSyntaxException e) {
				return null;
			if (refs == null || refs.isEmpty())
				return null;
			ServiceReference<IAgentServiceFactory> firstRef = refs.iterator().next();

The call to getServiceReferences returns 2 services, the default and ours.

However refs.iterator().next() returns the first service, ignoring the service.ranking,
and using the default, which is not correct for our situation.

What's the solution to this problem?

Should p2 be using an iterator that takes into account the service.ranking?

Should I have done something to make my bundle start first?
- I'm pretty sure this is a not kosher since bundle start level should not be used
   to control service start order since services might come and go at any point.

Should I implement my own provisioning agent that does the right thing?
- This seems like a lot of work for an OSGi-based services solution which should
   be using service ranking.

Our product is shipping with 3.7.1 but I've looked at the code in git trunk
and it's the same.

Did I miss anything?

* Of relevance is this discussion in 2010-02-02:
Unfortunately John doesn't directly comment on Meng's point about:
"... But the implementation of IProvisioningAgent simply uses the first
factory instance in its querying result..."