Reference target filters not handled correctly
----------------------------------------------

                 Key: FELIX-993
                 URL: https://issues.apache.org/jira/browse/FELIX-993
             Project: Felix
          Issue Type: Bug
          Components: Declarative Services (SCR)
    Affects Versions: scr-1.0.6
            Reporter: Soren Petersen


The SCR implementation does not handle references with target filter correctly. 
When the properties of a bound service is modified so that the service no 
longer matches the reference filter it isn't unbound as it should.

Suppose we have an event broadcaster component defined by:

        <component name="EventBroadcaster">
                <implementation class="example.EventBroadcaster" />
                <reference 
                        name="eventListeners" 
                        interface="example.EventListener"
                        cardinality="0..n"
                        policy="dynamic"
                        bind="addListener"
                        unbind="removeListener" 
                        target="(listener.state=Active)" 
                />
        </component>

If an event listener is registered by the code

        Dictionary<String, Object> props = new Hashtable<String, Object>();
        props.put("listener.state", "Active");
        ServiceRegistration reg = 
context.registerService(EventListener.class.getName(), new EventListener(), 
props);

the new service will be bound to our event broadcaster and the addListener 
method will be called. This is as it should be. Now, suppose we changed the 
properties of the service by executing

        Dictionary<String, Object> props2 = new Hashtable<String, Object>();
        props2.put("listener.state", "Inactive");
        reg.setProperties(props2);

At this point, the event listener service should be unbound from the event 
broadcaster component since it does no longer match the target filter. However, 
due to a bug in org.apache.felix.scr.impl.DependencyManager, this the service 
stays bound and isn't even unbound if

        reg.unregister();

is executed.

The problem is, basically, caused by the following two segments of code:

        public void serviceChanged( ServiceEvent event )
        {
                switch ( event.getType() )
                {
                        case ServiceEvent.REGISTERED:
                                serviceAdded( event.getServiceReference() );
                                break;

                        case ServiceEvent.MODIFIED:
                                serviceRemoved( event.getServiceReference() );
                                serviceAdded( event.getServiceReference() );
                                break;

                        case ServiceEvent.UNREGISTERING:
                                serviceRemoved( event.getServiceReference() );
                                break;
                }
        }

and

        private void serviceRemoved( ServiceReference reference )
        {
                // ignore the service, if it does not match the target filter
                if ( !targetFilterMatch( reference ) )
                {
                        [...]
                        return;
                }

                [...]
        }

Since the properties of the service has already been modified when 
serviceChanged is called, the filter will no longer match the service and 
serviceRemoved will ignore it.

-- 
This message is automatically generated by JIRA.
-
You can reply to this email to add a comment to the issue online.

Reply via email to