HADOOP-17287. Support new Instance by non default constructor by ReflectionUtils (#2341)
This commit is contained in:
parent
578370d6c8
commit
4b1c0e4e5b
|
@ -122,15 +122,35 @@ public class ReflectionUtils {
|
||||||
*/
|
*/
|
||||||
@SuppressWarnings("unchecked")
|
@SuppressWarnings("unchecked")
|
||||||
public static <T> T newInstance(Class<T> theClass, Configuration conf) {
|
public static <T> T newInstance(Class<T> theClass, Configuration conf) {
|
||||||
|
return newInstance(theClass, conf, EMPTY_ARRAY);
|
||||||
|
}
|
||||||
|
|
||||||
|
/** Create an object for the given class and initialize it from conf
|
||||||
|
*
|
||||||
|
* @param theClass class of which an object is created
|
||||||
|
* @param conf Configuration
|
||||||
|
* @param argTypes the types of the arguments
|
||||||
|
* @param values the values of the arguments
|
||||||
|
* @return a new object
|
||||||
|
*/
|
||||||
|
@SuppressWarnings("unchecked")
|
||||||
|
public static <T> T newInstance(Class<T> theClass, Configuration conf,
|
||||||
|
Class<?>[] argTypes, Object ... values) {
|
||||||
T result;
|
T result;
|
||||||
|
if (argTypes.length != values.length) {
|
||||||
|
throw new IllegalArgumentException(argTypes.length
|
||||||
|
+ " parameters are required but "
|
||||||
|
+ values.length
|
||||||
|
+ " arguments are provided");
|
||||||
|
}
|
||||||
try {
|
try {
|
||||||
Constructor<T> meth = (Constructor<T>) CONSTRUCTOR_CACHE.get(theClass);
|
Constructor<T> meth = (Constructor<T>) CONSTRUCTOR_CACHE.get(theClass);
|
||||||
if (meth == null) {
|
if (meth == null) {
|
||||||
meth = theClass.getDeclaredConstructor(EMPTY_ARRAY);
|
meth = theClass.getDeclaredConstructor(argTypes);
|
||||||
meth.setAccessible(true);
|
meth.setAccessible(true);
|
||||||
CONSTRUCTOR_CACHE.put(theClass, meth);
|
CONSTRUCTOR_CACHE.put(theClass, meth);
|
||||||
}
|
}
|
||||||
result = meth.newInstance();
|
result = meth.newInstance(values);
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
throw new RuntimeException(e);
|
throw new RuntimeException(e);
|
||||||
}
|
}
|
||||||
|
|
|
@ -28,6 +28,7 @@ import java.util.List;
|
||||||
import static org.hamcrest.CoreMatchers.containsString;
|
import static org.hamcrest.CoreMatchers.containsString;
|
||||||
import static org.junit.Assert.*;
|
import static org.junit.Assert.*;
|
||||||
|
|
||||||
|
import org.apache.hadoop.test.GenericTestUtils;
|
||||||
import org.apache.hadoop.test.GenericTestUtils.LogCapturer;
|
import org.apache.hadoop.test.GenericTestUtils.LogCapturer;
|
||||||
import org.junit.Before;
|
import org.junit.Before;
|
||||||
import org.junit.Test;
|
import org.junit.Test;
|
||||||
|
@ -168,6 +169,34 @@ public class TestReflectionUtils {
|
||||||
containsString("Process Thread Dump: " + title));
|
containsString("Process Thread Dump: " + title));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testNewInstanceForNonDefaultConstructor() {
|
||||||
|
Object x = ReflectionUtils.newInstance(
|
||||||
|
NoDefaultCtor.class, null, new Class[] {int.class}, 1);
|
||||||
|
assertTrue(x instanceof NoDefaultCtor);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testNewInstanceForNonDefaultConstructorWithException() {
|
||||||
|
try {
|
||||||
|
ReflectionUtils.newInstance(
|
||||||
|
NoDefaultCtor.class, null, new Class[]{int.class}, 1, 2);
|
||||||
|
fail("Should have failed before this point");
|
||||||
|
} catch (IllegalArgumentException e) {
|
||||||
|
GenericTestUtils.assertExceptionContains(
|
||||||
|
"1 parameters are required but 2 arguments are provided", e);
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
ReflectionUtils.newInstance(
|
||||||
|
NoDefaultCtor.class, null, new Class[]{int.class});
|
||||||
|
fail("Should have failed before this point");
|
||||||
|
} catch (IllegalArgumentException e) {
|
||||||
|
GenericTestUtils.assertExceptionContains(
|
||||||
|
"1 parameters are required but 0 arguments are provided", e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Used for testGetDeclaredFieldsIncludingInherited
|
// Used for testGetDeclaredFieldsIncludingInherited
|
||||||
private class Parent {
|
private class Parent {
|
||||||
private int parentField;
|
private int parentField;
|
||||||
|
|
Loading…
Reference in New Issue