You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@sling.apache.org by ro...@apache.org on 2017/11/07 10:18:36 UTC
[sling-org-apache-sling-testing-osgi-mock] 14/23: SLING-4163 OSGi
Mock: Reference bind/unbind method picking order
This is an automated email from the ASF dual-hosted git repository.
rombert pushed a commit to annotated tag org.apache.sling.testing.osgi-mock-1.1.0
in repository https://gitbox.apache.org/repos/asf/sling-org-apache-sling-testing-osgi-mock.git
commit c40b2dd59892d5723bed1caa280f9e9488ffb60a
Author: Stefan Seifert <ss...@apache.org>
AuthorDate: Fri Nov 14 16:16:48 2014 +0000
SLING-4163 OSGi Mock: Reference bind/unbind method picking order
git-svn-id: https://svn.apache.org/repos/asf/sling/trunk/testing/mocks/osgi-mock@1639692 13f79535-47bb-0310-9956-ffa450edef68
---
.../testing/mock/osgi/ReflectionServiceUtil.java | 155 ++++++++++-----------
.../mock/osgi/ReflectionServiceUtilTest.java | 16 ++-
2 files changed, 81 insertions(+), 90 deletions(-)
diff --git a/src/main/java/org/apache/sling/testing/mock/osgi/ReflectionServiceUtil.java b/src/main/java/org/apache/sling/testing/mock/osgi/ReflectionServiceUtil.java
index 1ee8370..fa75ebf 100644
--- a/src/main/java/org/apache/sling/testing/mock/osgi/ReflectionServiceUtil.java
+++ b/src/main/java/org/apache/sling/testing/mock/osgi/ReflectionServiceUtil.java
@@ -74,21 +74,21 @@ final class ReflectionServiceUtil {
// try to find matchin activate/deactivate method and execute it
// 1. componentContext
- Method method = getMethod(targetClass, methodName, new Class<?>[] { ComponentContext.class }, activate);
+ Method method = getMethod(targetClass, methodName, new Class<?>[] { ComponentContext.class });
if (method != null) {
invokeMethod(target, method, new Object[] { componentContext });
return true;
}
// 2. bundleContext
- method = getMethod(targetClass, methodName, new Class<?>[] { BundleContext.class }, activate);
+ method = getMethod(targetClass, methodName, new Class<?>[] { BundleContext.class });
if (method != null) {
invokeMethod(target, method, new Object[] { componentContext.getBundleContext() });
return true;
}
// 3. map
- method = getMethod(targetClass, methodName, new Class<?>[] { Map.class }, activate);
+ method = getMethod(targetClass, methodName, new Class<?>[] { Map.class });
if (method != null) {
invokeMethod(target, method, new Object[] { componentContext.getProperties() });
return true;
@@ -96,7 +96,7 @@ final class ReflectionServiceUtil {
// 4. int (deactivation only)
if (!activate) {
- method = getMethod(targetClass, methodName, new Class<?>[] { int.class }, activate);
+ method = getMethod(targetClass, methodName, new Class<?>[] { int.class });
if (method != null) {
invokeMethod(target, method, new Object[] { 0 });
return true;
@@ -105,7 +105,7 @@ final class ReflectionServiceUtil {
// 5. Integer (deactivation only)
if (!activate) {
- method = getMethod(targetClass, methodName, new Class<?>[] { Integer.class }, activate);
+ method = getMethod(targetClass, methodName, new Class<?>[] { Integer.class });
if (method != null) {
invokeMethod(target, method, new Object[] { 0 });
return true;
@@ -115,7 +115,7 @@ final class ReflectionServiceUtil {
// 6. mixed arguments of componentContext, bundleContext and map
Class<?>[] mixedArgsAllowed = activate ? new Class<?>[] { ComponentContext.class, BundleContext.class, Map.class }
: new Class<?>[] { ComponentContext.class, BundleContext.class, Map.class, int.class, Integer.class };
- method = getMethodWithAnyCombinationArgs(targetClass, methodName, mixedArgsAllowed, activate);
+ method = getMethodWithAnyCombinationArgs(targetClass, methodName, mixedArgsAllowed);
if (method != null) {
Object[] args = new Object[method.getParameterTypes().length];
for (int i=0; i<args.length; i++) {
@@ -137,7 +137,7 @@ final class ReflectionServiceUtil {
}
// 7. noargs
- method = getMethod(targetClass, methodName, new Class<?>[0], activate);
+ method = getMethod(targetClass, methodName, new Class<?>[0]);
if (method != null) {
invokeMethod(target, method, new Object[0]);
return true;
@@ -147,18 +147,47 @@ final class ReflectionServiceUtil {
return false;
}
- private static Method getMethod(Class clazz, String methodName, Class<?>[] signature, boolean activate) {
+ private static Method getMethod(Class clazz, String methodName, Class<?>[] types) {
Method[] methods = clazz.getDeclaredMethods();
for (Method method : methods) {
if (StringUtils.equals(method.getName(), methodName)
- && Arrays.equals(method.getParameterTypes(), signature)) {
+ && Arrays.equals(method.getParameterTypes(), types)) {
return method;
}
}
+ // not found? check super classes
+ Class<?> superClass = clazz.getSuperclass();
+ if (superClass != null && superClass != Object.class) {
+ return getMethod(superClass, methodName, types);
+ }
+ return null;
+ }
+
+ private static Method getMethodWithAssignableTypes(Class clazz, String methodName, Class<?>[] types) {
+ Method[] methods = clazz.getDeclaredMethods();
+ for (Method method : methods) {
+ if (StringUtils.equals(method.getName(), methodName) && method.getParameterTypes().length==types.length) {
+ boolean foundMismatch = false;
+ for (int i=0; i<types.length; i++) {
+ if (!method.getParameterTypes()[i].isAssignableFrom(types[i])) {
+ foundMismatch = false;
+ break;
+ }
+ }
+ if (!foundMismatch) {
+ return method;
+ }
+ }
+ }
+ // not found? check super classes
+ Class<?> superClass = clazz.getSuperclass();
+ if (superClass != null && superClass != Object.class) {
+ return getMethodWithAssignableTypes(superClass, methodName, types);
+ }
return null;
}
- private static Method getMethodWithAnyCombinationArgs(Class clazz, String methodName, Class<?>[] types, boolean activate) {
+ private static Method getMethodWithAnyCombinationArgs(Class clazz, String methodName, Class<?>[] types) {
Method[] methods = clazz.getDeclaredMethods();
for (Method method : methods) {
if (StringUtils.equals(method.getName(), methodName) && method.getParameterTypes().length > 1) {
@@ -170,6 +199,11 @@ final class ReflectionServiceUtil {
return method;
}
}
+ // not found? check super classes
+ Class<?> superClass = clazz.getSuperclass();
+ if (superClass != null && superClass != Object.class) {
+ return getMethodWithAnyCombinationArgs(superClass, methodName, types);
+ }
return null;
}
@@ -252,69 +286,38 @@ final class ReflectionServiceUtil {
// try to invoke bind method
String bindMethodName = reference.getBind();
if (StringUtils.isNotEmpty(bindMethodName)) {
- Method bindMethod = getFirstMethodWithNameAndSignature(targetClass, bindMethodName, new Class<?>[] { type });
+
+ // 1. ServiceReference
+ Method bindMethod = getMethod(targetClass, bindMethodName, new Class<?>[] { ServiceReference.class });
if (bindMethod != null) {
- bindMethod.setAccessible(true);
for (ServiceInfo matchingService : matchingServices) {
- try {
- bindMethod.invoke(target, matchingService.getServiceInstance());
- } catch (IllegalAccessException ex) {
- throw new RuntimeException("Unable to invoke method " + bindMethodName + " for class "
- + targetClass.getName(), ex);
- } catch (IllegalArgumentException ex) {
- throw new RuntimeException("Unable to invoke method " + bindMethodName + " for class "
- + targetClass.getName(), ex);
- } catch (InvocationTargetException ex) {
- throw new RuntimeException("Unable to invoke method " + bindMethodName + " for class "
- + targetClass.getName(), ex.getCause());
- }
+ invokeMethod(target, bindMethod, new Object[] { matchingService.getServiceReference() });
}
return true;
- } else {
- Method bindMethodWithConfig = getFirstMethodWithNameAndSignature(targetClass, bindMethodName,
- new Class<?>[] { type, Map.class });
- if (bindMethodWithConfig != null) {
- bindMethodWithConfig.setAccessible(true);
- for (ServiceInfo matchingService : matchingServices) {
- try {
- bindMethodWithConfig.invoke(target, matchingService.getServiceInstance(),
- matchingService.getServiceConfig());
- } catch (IllegalAccessException ex) {
- throw new RuntimeException("Unable to invoke method " + bindMethodName + " for class "
- + targetClass.getName(), ex);
- } catch (IllegalArgumentException ex) {
- throw new RuntimeException("Unable to invoke method " + bindMethodName + " for class "
- + targetClass.getName(), ex);
- } catch (InvocationTargetException ex) {
- throw new RuntimeException("Unable to invoke method " + bindMethodName + " for class "
- + targetClass.getName(), ex.getCause());
- }
- }
- return true;
- } else {
- Method bindMethodServiceReference = getFirstMethodWithNameAndSignature(targetClass, bindMethodName,
- new Class<?>[] { ServiceReference.class });
- if (bindMethodServiceReference != null) {
- bindMethodServiceReference.setAccessible(true);
- for (ServiceInfo matchingService : matchingServices) {
- if (matchingService.getServiceReference() != null) {
- try {
- bindMethodServiceReference.invoke(target, matchingService.getServiceReference());
- } catch (IllegalAccessException ex) {
- throw new RuntimeException("Unable to invoke method " + bindMethodName
- + " for class " + targetClass.getName(), ex);
- } catch (IllegalArgumentException ex) {
- throw new RuntimeException("Unable to invoke method " + bindMethodName
- + " for class " + targetClass.getName(), ex);
- } catch (InvocationTargetException ex) {
- throw new RuntimeException("Unable to invoke method " + bindMethodName
- + " for class " + targetClass.getName(), ex.getCause());
- }
- }
- }
- return true;
- }
+ }
+
+ // 2. assignable from service instance
+ Class<?> interfaceType;
+ try {
+ interfaceType = Class.forName(reference.getInterfaceType());
+ } catch (ClassNotFoundException e) {
+ throw new RuntimeException("Service reference type not found: " + reference.getInterfaceType());
+ }
+ bindMethod = getMethodWithAssignableTypes(targetClass, bindMethodName, new Class<?>[] { interfaceType });
+ if (bindMethod != null) {
+ for (ServiceInfo matchingService : matchingServices) {
+ invokeMethod(target, bindMethod, new Object[] { matchingService.getServiceInstance() });
+ }
+ return true;
+ }
+
+ // 3. assignable from service instance plus map
+ bindMethod = getMethodWithAssignableTypes(targetClass, bindMethodName, new Class<?>[] { interfaceType, Map.class });
+ if (bindMethod != null) {
+ for (ServiceInfo matchingService : matchingServices) {
+ invokeMethod(target, bindMethod, new Object[] { matchingService.getServiceInstance(), matchingService.getServiceConfig() });
}
+ return true;
}
}
@@ -322,22 +325,6 @@ final class ReflectionServiceUtil {
return false;
}
- private static Method getFirstMethodWithNameAndSignature(Class<?> clazz, String methodName, Class<?>[] signature) {
- Method[] methods = clazz.getDeclaredMethods();
- for (Method method : methods) {
- if (StringUtils.equals(method.getName(), methodName)
- && Arrays.equals(method.getParameterTypes(), signature)) {
- return method;
- }
- }
- // not found? check super classes
- Class<?> superClass = clazz.getSuperclass();
- if (superClass != null && superClass != Object.class) {
- return getFirstMethodWithNameAndSignature(superClass, methodName, signature);
- }
- return null;
- }
-
private static List<ServiceInfo> getMatchingServices(Class<?> type, BundleContext bundleContext) {
List<ServiceInfo> matchingServices = new ArrayList<ServiceInfo>();
try {
diff --git a/src/test/java/org/apache/sling/testing/mock/osgi/ReflectionServiceUtilTest.java b/src/test/java/org/apache/sling/testing/mock/osgi/ReflectionServiceUtilTest.java
index ff29037..6fd4ec2 100644
--- a/src/test/java/org/apache/sling/testing/mock/osgi/ReflectionServiceUtilTest.java
+++ b/src/test/java/org/apache/sling/testing/mock/osgi/ReflectionServiceUtilTest.java
@@ -78,7 +78,7 @@ public class ReflectionServiceUtilTest {
assertEquals(1, references2.size());
assertSame(service2, references2.get(0));
- List<ServiceInterface3> references3 = service3.getReferences3();
+ List<ServiceSuperInterface3> references3 = service3.getReferences3();
assertEquals(1, references3.size());
assertSame(service2, references3.get(0));
@@ -108,7 +108,11 @@ public class ReflectionServiceUtilTest {
// no methods
}
- public interface ServiceInterface3 {
+ public interface ServiceInterface3 extends ServiceSuperInterface3 {
+ // no methods
+ }
+
+ public interface ServiceSuperInterface3 {
// no methods
}
@@ -136,7 +140,7 @@ public class ReflectionServiceUtilTest {
private List<ServiceReference> references2 = new ArrayList<ServiceReference>();
@Reference(name = "reference3", referenceInterface = ServiceInterface3.class, cardinality = ReferenceCardinality.OPTIONAL_MULTIPLE)
- private List<ServiceInterface3> references3 = new ArrayList<ServiceInterface3>();
+ private List<ServiceSuperInterface3> references3 = new ArrayList<ServiceSuperInterface3>();
private List<Map<String, Object>> reference3Configs = new ArrayList<Map<String, Object>>();
private ComponentContext componentContext;
@@ -163,7 +167,7 @@ public class ReflectionServiceUtilTest {
return services;
}
- public List<ServiceInterface3> getReferences3() {
+ public List<ServiceSuperInterface3> getReferences3() {
return this.references3;
}
@@ -191,12 +195,12 @@ public class ReflectionServiceUtilTest {
references2.remove(serviceReference);
}
- protected void bindReference3(ServiceInterface3 service, Map<String, Object> serviceConfig) {
+ protected void bindReference3(ServiceSuperInterface3 service, Map<String, Object> serviceConfig) {
references3.add(service);
reference3Configs.add(serviceConfig);
}
- protected void unbindReference3(ServiceInterface3 service, Map<String, Object> serviceConfig) {
+ protected void unbindReference3(ServiceSuperInterface3 service, Map<String, Object> serviceConfig) {
references3.remove(service);
reference3Configs.remove(serviceConfig);
}
--
To stop receiving notification emails like this one, please contact
"commits@sling.apache.org" <co...@sling.apache.org>.