Java Reflection Method Invoke invokeMethod(Object target, String signature, Object... args)

Here you can find the source of invokeMethod(Object target, String signature, Object... args)

Description

Invokes method declared in target, may be private.

License

Open Source License

Declaration

@SuppressWarnings("unchecked")
public static <T> T invokeMethod(Object target, String signature, Object... args) 

Method Source Code

//package com.java2s;
/*/*w  ww. j  av a 2s  . c  o m*/
 * Copyright (c) 2012, the Dart project authors.
 * 
 * Licensed under the Eclipse Public License v1.0 (the "License"); you may not use this file except
 * in compliance with the License. You may obtain a copy of the License at
 * 
 * http://www.eclipse.org/legal/epl-v10.html
 * 
 * Unless required by applicable law or agreed to in writing, software distributed under the License
 * is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
 * or implied. See the License for the specific language governing permissions and limitations under
 * the License.
 */

import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import org.eclipse.core.runtime.Assert;

public class Main {
    /**
     * Invokes method declared in <code>target</code>, may be private. Re-throws any {@link Exception}
     * as is, without declaring or wrapping them.
     */
    @SuppressWarnings("unchecked")
    public static <T> T invokeMethod(Object target, String signature, Object... args) {
        Assert.isNotNull(target);
        Assert.isNotNull(signature);
        Method method = getMethod(target, signature);
        if (method == null) {
            Class<?> targetClass = getTargetClass(target);
            throw new IllegalArgumentException(signature + " in " + targetClass);
        }
        try {
            return (T) method.invoke(target, args);
        } catch (Throwable e) {
            if (e instanceof InvocationTargetException) {
                e = e.getCause();
            }
            throw new RuntimeException(e);
            // &&& throw ExecutionUtils.propagate(e);
        }
    }

    /**
     * @return the declared {@link Method} with given signature, may be private.
     */
    public static Method getMethod(Object target, String signature) {
        Assert.isNotNull(target);
        Assert.isNotNull(signature);
        Class<?> targetClass = getTargetClass(target);
        while (targetClass != null) {
            for (Method method : targetClass.getDeclaredMethods()) {
                if (getMethodSignature(method).equals(signature)) {
                    method.setAccessible(true);
                    return method;
                }
            }
            targetClass = targetClass.getSuperclass();
        }
        return null;
    }

    /**
     * @return the {@link Class} or the given "target" - "target" itself if it is {@link Class} or its
     *         {@link Class} if just some object.
     */
    private static Class<?> getTargetClass(Object target) {
        if (target instanceof Class) {
            return (Class<?>) target;
        }
        return target.getClass();
    }

    /**
     * @return the signature of the given {@link Method}, not JVM signature however, just some
     *         reasonable signature to write manually.
     */
    private static String getMethodSignature(Method method) {
        StringBuilder sb = new StringBuilder();
        sb.append(method.getName());
        sb.append('(');
        boolean firstParameter = true;
        for (Class<?> parameterType : method.getParameterTypes()) {
            if (!firstParameter) {
                sb.append(',');
            }
            firstParameter = false;
            sb.append(getClassName(parameterType));
        }
        sb.append(')');
        return sb.toString();
    }

    /**
     * @return the name of the {@link Class} for signature.
     */
    public static String getClassName(Class<?> clazz) {
        if (clazz.isArray()) {
            return getClassName(clazz.getComponentType()) + "[]";
        }
        return clazz.getName();
    }
}

Related

  1. invokeMethod(Object target, String method)
  2. invokeMethod(Object target, String methodName, Object... parameters)
  3. invokeMethod(Object target, String methodName, Object[] arguments)
  4. invokeMethod(Object target, String name, Class... parameterTypes)
  5. invokeMethod(Object target, String name, Object[] args, Class[] argTypes)
  6. invokeMethod(Object target, String thisMethod, Object value)
  7. invokeMethod(Object theObject, String methodName, Object... parametersObject)
  8. invokeMethod(String className, String method, Class[] paramTypes, Object obj, Object[] args)
  9. invokeMethod(String methodName, Object gameCommand)