MethodCoercions { public static Maybe<?> tryFindAndInvokeBestMatchingMethod(Object instance, String methodName, Object argument) { if (argument instanceof List) { List<?> arguments = (List<?>) argument; Maybe<?> maybe = tryFindAndInvokeMultiParameterMethod(instance, methodName, arguments); if (maybe.isAbsent()) maybe = tryFindAndInvokeSingleParameterMethod(instance, methodName, argument); return maybe; } else { return tryFindAndInvokeSingleParameterMethod(instance, methodName, argument); } }  static Predicate<Method> matchSingleParameterMethod(final String methodName, final Object argument); static Maybe<?> tryFindAndInvokeSingleParameterMethod(final Object instance, final String methodName, final Object argument); static Predicate<Method> matchMultiParameterMethod(final String methodName, final List<?> arguments); static Predicate<Method> matchMethodByName(final String methodName); static Predicate<Method> matchMultiParameterMethod(final List<?> arguments); static Maybe<?> tryFindAndInvokeMultiParameterMethod(Object instanceOrClazz, Iterable<Method> methods, List<?> arguments); static Maybe<?> tryFindAndInvokeMultiParameterMethod(Object instance, String methodName, List<?> arguments); static Maybe<?> tryFindAndInvokeBestMatchingMethod(Object instance, String methodName, Object argument);  }
@Test public void testTryFindAndInvokeBestMatchingMethod() throws Exception { TestClass instance = new TestClass(); Maybe<?> maybe = MethodCoercions.tryFindAndInvokeBestMatchingMethod(instance, "singleParameterMethod", "42"); assertTrue(maybe.isPresent()); assertTrue(instance.wasSingleParameterMethodCalled()); instance = new TestClass(); maybe = MethodCoercions.tryFindAndInvokeBestMatchingMethod(instance, "multiParameterMethod", ImmutableList.of("true", "42")); assertTrue(maybe.isPresent()); assertTrue(instance.wasMultiParameterMethodCalled()); instance = new TestClass(); maybe = MethodCoercions.tryFindAndInvokeBestMatchingMethod(instance, "singleCollectionParameterMethod", ImmutableList.of("fred", "joe")); assertTrue(maybe.isPresent()); assertTrue(instance.wasSingleCollectionParameterMethodCalled()); }
@Test public void testTryFindAndInvokeBestMatchingMethodOnPrivateClassWithPublicSuper() throws Exception { PrivateClass instance = new PrivateClass(); Maybe<?> maybe = MethodCoercions.tryFindAndInvokeBestMatchingMethod(instance, "methodOnSuperClass", "42"); assertTrue(maybe.isPresent()); assertTrue(instance.wasMethodOnSuperClassCalled()); Maybe<?> maybe2 = MethodCoercions.tryFindAndInvokeBestMatchingMethod(instance, "methodOnInterface", "42"); assertTrue(maybe2.isPresent()); assertTrue(instance.wasMethodOnInterfaceCalled()); }