This is an automated email from the ASF dual-hosted git repository.

jsedding pushed a commit to branch 
fix/SLING-12157-late-bind-unbind-for-DS-components
in repository 
https://gitbox.apache.org/repos/asf/sling-org-apache-sling-testing-osgi-mock.git

commit ab8371a6be3a47d3f15acfe8a2d053cf775623f6
Author: Julian Sedding <[email protected]>
AuthorDate: Wed Nov 15 18:04:59 2023 +0100

    SLING-12157 [osgi-mock] late binding does not work for non-service DS 
components
    
    - OsgiServiceUtilBindUnbindTest seems to have worked around this issue, 
hence the change
    - factored out "registerDSComponent" in order to reduce code duplication
    - with this fix, a non-service DS component is stored in 
MockBundleContext#registeredServices
      but its MockServiceRegistration#clazzes field is an empty set and thus 
cannot be retrieved
      via BundleContext#getServiceReference
---
 .../apache/sling/testing/mock/osgi/MockOsgi.java   | 28 ++++++++++++----------
 .../mock/osgi/OsgiServiceUtilBindUnbindTest.java   |  3 +--
 2 files changed, 17 insertions(+), 14 deletions(-)

diff --git 
a/core/src/main/java/org/apache/sling/testing/mock/osgi/MockOsgi.java 
b/core/src/main/java/org/apache/sling/testing/mock/osgi/MockOsgi.java
index ac51aef..c847c92 100644
--- a/core/src/main/java/org/apache/sling/testing/mock/osgi/MockOsgi.java
+++ b/core/src/main/java/org/apache/sling/testing/mock/osgi/MockOsgi.java
@@ -26,6 +26,7 @@ import java.io.IOException;
 import java.util.Dictionary;
 import java.util.Map;
 import java.util.Map.Entry;
+import java.util.Objects;
 
 import org.apache.sling.testing.mock.osgi.OsgiMetadataUtil.OsgiMetadata;
 import org.jetbrains.annotations.NotNull;
@@ -228,12 +229,7 @@ public final class MockOsgi {
         MockOsgi.injectServices(component, bundleContext, mergedProperties);
         ComponentContext componentContext = newComponentContext(bundleContext, 
mergedProperties);
         OsgiServiceUtil.activateDeactivate(component, 
(MockComponentContext)componentContext, true);
-        OsgiMetadata metadata = 
OsgiMetadataUtil.getMetadata(component.getClass());
-        if (!metadata.getServiceInterfaces().isEmpty()) {
-            // convert component properties to service properties 
(http://docs.osgi.org/specification/osgi.cmpn/7.0.0/service.component.html#service.component-service.properties)
-            Dictionary<String, Object> serviceProperties = 
mergedProperties.entrySet().stream().filter(e -> e.getKey() != null && 
!e.getKey().startsWith(".")).collect(new DictionaryCollector<String, 
Object>(Entry::getKey, Entry::getValue));
-            
bundleContext.registerService(metadata.getServiceInterfaces().toArray(new 
String[0]), component, serviceProperties);
-        }
+        registerDSComponent(component, bundleContext, mergedProperties);
     }
 
     /**
@@ -270,15 +266,23 @@ public final class MockOsgi {
         Map<String, Object> mergedProperties = 
propertiesMergeWithOsgiMetadata(dsComponentClass, 
getConfigAdmin(bundleContext), properties);
         ComponentContext componentContext = newComponentContext(bundleContext, 
mergedProperties);
         T component = OsgiServiceUtil.activateInjectServices(dsComponentClass, 
(MockComponentContext)componentContext);
-        OsgiMetadata metadata = OsgiMetadataUtil.getMetadata(dsComponentClass);
-        if (!metadata.getServiceInterfaces().isEmpty()) {
-            // convert component properties to service properties 
(http://docs.osgi.org/specification/osgi.cmpn/7.0.0/service.component.html#service.component-service.properties)
-            Dictionary<String, Object> serviceProperties = 
mergedProperties.entrySet().stream().filter(e -> e.getKey() != null && 
!e.getKey().startsWith(".")).collect(new DictionaryCollector<String, 
Object>(Entry::getKey, Entry::getValue));
-            
bundleContext.registerService(metadata.getServiceInterfaces().toArray(new 
String[0]), component, serviceProperties);
-        }
+        registerDSComponent(component, bundleContext, mergedProperties);
         return component;
     }
 
+    private static <T> void registerDSComponent(@NotNull T component, @NotNull 
BundleContext bundleContext, Map<String, Object> mergedProperties) {
+        OsgiMetadata metadata = 
Objects.requireNonNull(OsgiMetadataUtil.getMetadata(component.getClass()),
+                "No metadata found for " + component.getClass());
+
+        // convert component properties to service properties 
(http://docs.osgi.org/specification/osgi.cmpn/7.0.0/service.component.html#service.component-service.properties)
+        Dictionary<String, Object> serviceProperties = 
mergedProperties.entrySet().stream()
+                .filter(e -> e.getKey() != null && !e.getKey().startsWith("."))
+                .collect(new DictionaryCollector<>(Entry::getKey, 
Entry::getValue));
+
+        // we also register DS Components that aren't services in order for 
bind/unbind to work - they are registered with no service interfaces
+        
bundleContext.registerService(metadata.getServiceInterfaces().toArray(new 
String[0]), component, serviceProperties);
+    }
+
     /**
      * Injects dependencies, activates and registers a DS component in the 
mocked OSGi environment.
      * @param <T> DS component type
diff --git 
a/core/src/test/java/org/apache/sling/testing/mock/osgi/OsgiServiceUtilBindUnbindTest.java
 
b/core/src/test/java/org/apache/sling/testing/mock/osgi/OsgiServiceUtilBindUnbindTest.java
index 4bce611..9e6f834 100644
--- 
a/core/src/test/java/org/apache/sling/testing/mock/osgi/OsgiServiceUtilBindUnbindTest.java
+++ 
b/core/src/test/java/org/apache/sling/testing/mock/osgi/OsgiServiceUtilBindUnbindTest.java
@@ -141,8 +141,7 @@ public class OsgiServiceUtilBindUnbindTest {
 
     @SuppressWarnings({ "null", "unchecked" })
     private <T> T registerInjectService(T service) {
-        MockOsgi.injectServices(service, bundleContext);
-        bundleContext.registerService((Class<T>)service.getClass(), service, 
(Dictionary)null);
+        MockOsgi.registerInjectActivateService(service, bundleContext);
         return service;
     }
 

Reply via email to