a bit of dog food and a lot of javadoc tweakage
git-svn-id: https://svn.apache.org/repos/asf/commons/proper/lang/trunk@1531403 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
parent
eed09d6bd4
commit
b2ad5e80bb
|
@ -16,26 +16,28 @@
|
||||||
*/
|
*/
|
||||||
package org.apache.commons.lang3.reflect;
|
package org.apache.commons.lang3.reflect;
|
||||||
|
|
||||||
|
import java.lang.reflect.AccessibleObject;
|
||||||
import java.lang.reflect.Constructor;
|
import java.lang.reflect.Constructor;
|
||||||
import java.lang.reflect.InvocationTargetException;
|
import java.lang.reflect.InvocationTargetException;
|
||||||
import java.lang.reflect.Modifier;
|
import java.lang.reflect.Modifier;
|
||||||
|
|
||||||
import org.apache.commons.lang3.ArrayUtils;
|
import org.apache.commons.lang3.ArrayUtils;
|
||||||
import org.apache.commons.lang3.ClassUtils;
|
import org.apache.commons.lang3.ClassUtils;
|
||||||
|
import org.apache.commons.lang3.Validate;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* <p> Utility reflection methods focused on constructors, modeled after
|
* <p> Utility reflection methods focused on constructors, modeled after
|
||||||
* {@link MethodUtils}. </p>
|
* {@link MethodUtils}. </p>
|
||||||
*
|
*
|
||||||
* <h3>Known Limitations</h3> <h4>Accessing Public Constructors In A Default
|
* <h3>Known Limitations</h3> <h4>Accessing Public Constructors In A Default
|
||||||
* Access Superclass</h4> <p>There is an issue when invoking public constructors
|
* Access Superclass</h4> <p>There is an issue when invoking {@code public} constructors
|
||||||
* contained in a default access superclass. Reflection locates these
|
* contained in a default access superclass. Reflection correctly locates these
|
||||||
* constructors fine and correctly assigns them as public. However, an
|
* constructors and assigns them as {@code public}. However, an
|
||||||
* <code>IllegalAccessException</code> is thrown if the constructors is
|
* {@link IllegalAccessException} is thrown if the constructor is
|
||||||
* invoked.</p>
|
* invoked.</p>
|
||||||
*
|
*
|
||||||
* <p><code>ConstructorUtils</code> contains a workaround for this situation. It
|
* <p>{@link ConstructorUtils} contains a workaround for this situation: it
|
||||||
* will attempt to call <code>setAccessible</code> on this constructor. If this
|
* will attempt to call {@link AccessibleObject#setAccessible(boolean)} on this constructor. If this
|
||||||
* call succeeds, then the method can be invoked as normal. This call will only
|
* call succeeds, then the method can be invoked as normal. This call will only
|
||||||
* succeed when the application has sufficient security privileges. If this call
|
* succeed when the application has sufficient security privileges. If this call
|
||||||
* fails then a warning will be logged and the method may fail.</p>
|
* fails then a warning will be logged and the method may fail.</p>
|
||||||
|
@ -48,9 +50,9 @@ public class ConstructorUtils {
|
||||||
/**
|
/**
|
||||||
* <p>ConstructorUtils instances should NOT be constructed in standard
|
* <p>ConstructorUtils instances should NOT be constructed in standard
|
||||||
* programming. Instead, the class should be used as
|
* programming. Instead, the class should be used as
|
||||||
* <code>ConstructorUtils.invokeConstructor(cls, args)</code>.</p>
|
* {@code ConstructorUtils.invokeConstructor(cls, args)}.</p>
|
||||||
*
|
*
|
||||||
* <p>This constructor is public to permit tools that require a JavaBean
|
* <p>This constructor is {@code public} to permit tools that require a JavaBean
|
||||||
* instance to operate.</p>
|
* instance to operate.</p>
|
||||||
*/
|
*/
|
||||||
public ConstructorUtils() {
|
public ConstructorUtils() {
|
||||||
|
@ -65,10 +67,11 @@ public class ConstructorUtils {
|
||||||
* The constructor signature must match the argument types by assignment compatibility.</p>
|
* The constructor signature must match the argument types by assignment compatibility.</p>
|
||||||
*
|
*
|
||||||
* @param <T> the type to be constructed
|
* @param <T> the type to be constructed
|
||||||
* @param cls the class to be constructed, not null
|
* @param cls the class to be constructed, not {@code null}
|
||||||
* @param args the array of arguments, null treated as empty
|
* @param args the array of arguments, {@code null treated as empty
|
||||||
* @return new instance of <code>cls</code>, not null
|
* @return new instance of {@code cls}, not {@code null}
|
||||||
*
|
*
|
||||||
|
* @throws NullPointerException if {@code cls} is {@code null}
|
||||||
* @throws NoSuchMethodException if a matching constructor cannot be found
|
* @throws NoSuchMethodException if a matching constructor cannot be found
|
||||||
* @throws IllegalAccessException if invocation is not permitted by security
|
* @throws IllegalAccessException if invocation is not permitted by security
|
||||||
* @throws InvocationTargetException if an error occurs on invocation
|
* @throws InvocationTargetException if an error occurs on invocation
|
||||||
|
@ -78,9 +81,7 @@ public class ConstructorUtils {
|
||||||
public static <T> T invokeConstructor(final Class<T> cls, Object... args)
|
public static <T> T invokeConstructor(final Class<T> cls, Object... args)
|
||||||
throws NoSuchMethodException, IllegalAccessException, InvocationTargetException,
|
throws NoSuchMethodException, IllegalAccessException, InvocationTargetException,
|
||||||
InstantiationException {
|
InstantiationException {
|
||||||
if (args == null) {
|
args = ArrayUtils.nullToEmpty(args);
|
||||||
args = ArrayUtils.EMPTY_OBJECT_ARRAY;
|
|
||||||
}
|
|
||||||
final Class<?> parameterTypes[] = ClassUtils.toClass(args);
|
final Class<?> parameterTypes[] = ClassUtils.toClass(args);
|
||||||
return invokeConstructor(cls, args, parameterTypes);
|
return invokeConstructor(cls, args, parameterTypes);
|
||||||
}
|
}
|
||||||
|
@ -93,11 +94,12 @@ public class ConstructorUtils {
|
||||||
* The constructor signature must match the parameter types by assignment compatibility.</p>
|
* The constructor signature must match the parameter types by assignment compatibility.</p>
|
||||||
*
|
*
|
||||||
* @param <T> the type to be constructed
|
* @param <T> the type to be constructed
|
||||||
* @param cls the class to be constructed, not null
|
* @param cls the class to be constructed, not {@code null}
|
||||||
* @param args the array of arguments, null treated as empty
|
* @param args the array of arguments, {@code null} treated as empty
|
||||||
* @param parameterTypes the array of parameter types, null treated as empty
|
* @param parameterTypes the array of parameter types, {@code null} treated as empty
|
||||||
* @return new instance of <code>cls</code>, not null
|
* @return new instance of {@code cls}, not {@code null}
|
||||||
*
|
*
|
||||||
|
* @throws NullPointerException if {@code cls} is {@code null}
|
||||||
* @throws NoSuchMethodException if a matching constructor cannot be found
|
* @throws NoSuchMethodException if a matching constructor cannot be found
|
||||||
* @throws IllegalAccessException if invocation is not permitted by security
|
* @throws IllegalAccessException if invocation is not permitted by security
|
||||||
* @throws InvocationTargetException if an error occurs on invocation
|
* @throws InvocationTargetException if an error occurs on invocation
|
||||||
|
@ -107,12 +109,8 @@ public class ConstructorUtils {
|
||||||
public static <T> T invokeConstructor(final Class<T> cls, Object[] args, Class<?>[] parameterTypes)
|
public static <T> T invokeConstructor(final Class<T> cls, Object[] args, Class<?>[] parameterTypes)
|
||||||
throws NoSuchMethodException, IllegalAccessException, InvocationTargetException,
|
throws NoSuchMethodException, IllegalAccessException, InvocationTargetException,
|
||||||
InstantiationException {
|
InstantiationException {
|
||||||
if (parameterTypes == null) {
|
args = ArrayUtils.nullToEmpty(args);
|
||||||
parameterTypes = ArrayUtils.EMPTY_CLASS_ARRAY;
|
parameterTypes = ArrayUtils.nullToEmpty(parameterTypes);
|
||||||
}
|
|
||||||
if (args == null) {
|
|
||||||
args = ArrayUtils.EMPTY_OBJECT_ARRAY;
|
|
||||||
}
|
|
||||||
final Constructor<T> ctor = getMatchingAccessibleConstructor(cls, parameterTypes);
|
final Constructor<T> ctor = getMatchingAccessibleConstructor(cls, parameterTypes);
|
||||||
if (ctor == null) {
|
if (ctor == null) {
|
||||||
throw new NoSuchMethodException(
|
throw new NoSuchMethodException(
|
||||||
|
@ -129,10 +127,11 @@ public class ConstructorUtils {
|
||||||
* The constructor signature must match the argument types exactly.</p>
|
* The constructor signature must match the argument types exactly.</p>
|
||||||
*
|
*
|
||||||
* @param <T> the type to be constructed
|
* @param <T> the type to be constructed
|
||||||
* @param cls the class to be constructed, not null
|
* @param cls the class to be constructed, not {@code null}
|
||||||
* @param args the array of arguments, null treated as empty
|
* @param args the array of arguments, {@code null treated as empty
|
||||||
* @return new instance of <code>cls</code>, not null
|
* @return new instance of {@code cls}, not {@code null
|
||||||
*
|
*
|
||||||
|
* @throws NullPointerException if {@code cls} is {@code null}
|
||||||
* @throws NoSuchMethodException if a matching constructor cannot be found
|
* @throws NoSuchMethodException if a matching constructor cannot be found
|
||||||
* @throws IllegalAccessException if invocation is not permitted by security
|
* @throws IllegalAccessException if invocation is not permitted by security
|
||||||
* @throws InvocationTargetException if an error occurs on invocation
|
* @throws InvocationTargetException if an error occurs on invocation
|
||||||
|
@ -142,9 +141,7 @@ public class ConstructorUtils {
|
||||||
public static <T> T invokeExactConstructor(final Class<T> cls, Object... args)
|
public static <T> T invokeExactConstructor(final Class<T> cls, Object... args)
|
||||||
throws NoSuchMethodException, IllegalAccessException, InvocationTargetException,
|
throws NoSuchMethodException, IllegalAccessException, InvocationTargetException,
|
||||||
InstantiationException {
|
InstantiationException {
|
||||||
if (args == null) {
|
args = ArrayUtils.nullToEmpty(args);
|
||||||
args = ArrayUtils.EMPTY_OBJECT_ARRAY;
|
|
||||||
}
|
|
||||||
final Class<?> parameterTypes[] = ClassUtils.toClass(args);
|
final Class<?> parameterTypes[] = ClassUtils.toClass(args);
|
||||||
return invokeExactConstructor(cls, args, parameterTypes);
|
return invokeExactConstructor(cls, args, parameterTypes);
|
||||||
}
|
}
|
||||||
|
@ -157,11 +154,12 @@ public class ConstructorUtils {
|
||||||
* The constructor signature must match the parameter types exactly.</p>
|
* The constructor signature must match the parameter types exactly.</p>
|
||||||
*
|
*
|
||||||
* @param <T> the type to be constructed
|
* @param <T> the type to be constructed
|
||||||
* @param cls the class to be constructed, not null
|
* @param cls the class to be constructed, not {@code null}
|
||||||
* @param args the array of arguments, null treated as empty
|
* @param args the array of arguments, {@code null} treated as empty
|
||||||
* @param parameterTypes the array of parameter types, null treated as empty
|
* @param parameterTypes the array of parameter types, {@code null} treated as empty
|
||||||
* @return new instance of <code>cls</code>, not null
|
* @return new instance of <code>cls</code>, not {@code null}
|
||||||
*
|
*
|
||||||
|
* @throws NullPointerException if {@code cls} is {@code null}
|
||||||
* @throws NoSuchMethodException if a matching constructor cannot be found
|
* @throws NoSuchMethodException if a matching constructor cannot be found
|
||||||
* @throws IllegalAccessException if invocation is not permitted by security
|
* @throws IllegalAccessException if invocation is not permitted by security
|
||||||
* @throws InvocationTargetException if an error occurs on invocation
|
* @throws InvocationTargetException if an error occurs on invocation
|
||||||
|
@ -171,12 +169,8 @@ public class ConstructorUtils {
|
||||||
public static <T> T invokeExactConstructor(final Class<T> cls, Object[] args,
|
public static <T> T invokeExactConstructor(final Class<T> cls, Object[] args,
|
||||||
Class<?>[] parameterTypes) throws NoSuchMethodException, IllegalAccessException,
|
Class<?>[] parameterTypes) throws NoSuchMethodException, IllegalAccessException,
|
||||||
InvocationTargetException, InstantiationException {
|
InvocationTargetException, InstantiationException {
|
||||||
if (args == null) {
|
args = ArrayUtils.nullToEmpty(args);
|
||||||
args = ArrayUtils.EMPTY_OBJECT_ARRAY;
|
parameterTypes = ArrayUtils.nullToEmpty(parameterTypes);
|
||||||
}
|
|
||||||
if (parameterTypes == null) {
|
|
||||||
parameterTypes = ArrayUtils.EMPTY_CLASS_ARRAY;
|
|
||||||
}
|
|
||||||
final Constructor<T> ctor = getAccessibleConstructor(cls, parameterTypes);
|
final Constructor<T> ctor = getAccessibleConstructor(cls, parameterTypes);
|
||||||
if (ctor == null) {
|
if (ctor == null) {
|
||||||
throw new NoSuchMethodException(
|
throw new NoSuchMethodException(
|
||||||
|
@ -193,14 +187,16 @@ public class ConstructorUtils {
|
||||||
* The constructor signature must match the parameter types exactly.</p>
|
* The constructor signature must match the parameter types exactly.</p>
|
||||||
*
|
*
|
||||||
* @param <T> the constructor type
|
* @param <T> the constructor type
|
||||||
* @param cls the class to find a constructor for, not null
|
* @param cls the class to find a constructor for, not {@code null}
|
||||||
* @param parameterTypes the array of parameter types, null treated as empty
|
* @param parameterTypes the array of parameter types, {@code null} treated as empty
|
||||||
* @return the constructor, null if no matching accessible constructor found
|
* @return the constructor, {@code null} if no matching accessible constructor found
|
||||||
* @see Class#getConstructor
|
* @see Class#getConstructor
|
||||||
* @see #getAccessibleConstructor(java.lang.reflect.Constructor)
|
* @see #getAccessibleConstructor(java.lang.reflect.Constructor)
|
||||||
|
* @throws NullPointerException if {@code cls} is {@code null}
|
||||||
*/
|
*/
|
||||||
public static <T> Constructor<T> getAccessibleConstructor(final Class<T> cls,
|
public static <T> Constructor<T> getAccessibleConstructor(final Class<T> cls,
|
||||||
final Class<?>... parameterTypes) {
|
final Class<?>... parameterTypes) {
|
||||||
|
Validate.notNull(cls, "class cannot be null");
|
||||||
try {
|
try {
|
||||||
return getAccessibleConstructor(cls.getConstructor(parameterTypes));
|
return getAccessibleConstructor(cls.getConstructor(parameterTypes));
|
||||||
} catch (final NoSuchMethodException e) {
|
} catch (final NoSuchMethodException e) {
|
||||||
|
@ -214,11 +210,13 @@ public class ConstructorUtils {
|
||||||
* <p>This simply ensures that the constructor is accessible.</p>
|
* <p>This simply ensures that the constructor is accessible.</p>
|
||||||
*
|
*
|
||||||
* @param <T> the constructor type
|
* @param <T> the constructor type
|
||||||
* @param ctor the prototype constructor object, not null
|
* @param ctor the prototype constructor object, not {@code null}
|
||||||
* @return the constructor, null if no matching accessible constructor found
|
* @return the constructor, {@code null} if no matching accessible constructor found
|
||||||
* @see java.lang.SecurityManager
|
* @see java.lang.SecurityManager
|
||||||
|
* @throws NullPointerException if {@code ctor} is {@code null}
|
||||||
*/
|
*/
|
||||||
public static <T> Constructor<T> getAccessibleConstructor(final Constructor<T> ctor) {
|
public static <T> Constructor<T> getAccessibleConstructor(final Constructor<T> ctor) {
|
||||||
|
Validate.notNull(ctor, "constructor cannot be null");
|
||||||
return MemberUtils.isAccessible(ctor)
|
return MemberUtils.isAccessible(ctor)
|
||||||
&& Modifier.isPublic(ctor.getDeclaringClass().getModifiers()) ? ctor : null;
|
&& Modifier.isPublic(ctor.getDeclaringClass().getModifiers()) ? ctor : null;
|
||||||
}
|
}
|
||||||
|
@ -232,16 +230,18 @@ public class ConstructorUtils {
|
||||||
*
|
*
|
||||||
* <p>First it checks if there is a constructor matching the exact signature.
|
* <p>First it checks if there is a constructor matching the exact signature.
|
||||||
* If not then all the constructors of the class are checked to see if their
|
* If not then all the constructors of the class are checked to see if their
|
||||||
* signatures are assignment compatible with the parameter types.
|
* signatures are assignment-compatible with the parameter types.
|
||||||
* The first assignment compatible matching constructor is returned.</p>
|
* The first assignment-compatible matching constructor is returned.</p>
|
||||||
*
|
*
|
||||||
* @param <T> the constructor type
|
* @param <T> the constructor type
|
||||||
* @param cls the class to find a constructor for, not null
|
* @param cls the class to find a constructor for, not {@code null}
|
||||||
* @param parameterTypes find method with compatible parameters
|
* @param parameterTypes find method with compatible parameters
|
||||||
* @return the constructor, null if no matching accessible constructor found
|
* @return the constructor, null if no matching accessible constructor found
|
||||||
|
* @throws NullPointerException if {@code cls} is {@code null}
|
||||||
*/
|
*/
|
||||||
public static <T> Constructor<T> getMatchingAccessibleConstructor(final Class<T> cls,
|
public static <T> Constructor<T> getMatchingAccessibleConstructor(final Class<T> cls,
|
||||||
final Class<?>... parameterTypes) {
|
final Class<?>... parameterTypes) {
|
||||||
|
Validate.notNull(cls, "class cannot be null");
|
||||||
// see if we can find the constructor directly
|
// see if we can find the constructor directly
|
||||||
// most of the time this works and it's much faster
|
// most of the time this works and it's much faster
|
||||||
try {
|
try {
|
||||||
|
|
|
@ -16,15 +16,18 @@
|
||||||
*/
|
*/
|
||||||
package org.apache.commons.lang3.reflect;
|
package org.apache.commons.lang3.reflect;
|
||||||
|
|
||||||
|
import java.lang.reflect.AccessibleObject;
|
||||||
import java.lang.reflect.Field;
|
import java.lang.reflect.Field;
|
||||||
import java.lang.reflect.Modifier;
|
import java.lang.reflect.Modifier;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
import org.apache.commons.lang3.ClassUtils;
|
import org.apache.commons.lang3.ClassUtils;
|
||||||
|
import org.apache.commons.lang3.StringUtils;
|
||||||
|
import org.apache.commons.lang3.Validate;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Utilities for working with fields by reflection. Adapted and refactored from the dormant [reflect] Commons sandbox
|
* Utilities for working with {@link Field}s by reflection. Adapted and refactored from the dormant [reflect] Commons sandbox
|
||||||
* component.
|
* component.
|
||||||
* <p>
|
* <p>
|
||||||
* The ability is provided to break the scoping restrictions coded by the programmer. This can allow fields to be
|
* The ability is provided to break the scoping restrictions coded by the programmer. This can allow fields to be
|
||||||
|
@ -36,24 +39,24 @@ import org.apache.commons.lang3.ClassUtils;
|
||||||
public class FieldUtils {
|
public class FieldUtils {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* FieldUtils instances should NOT be constructed in standard programming.
|
* {@link FieldUtils} instances should NOT be constructed in standard programming.
|
||||||
* <p>
|
* <p>
|
||||||
* This constructor is public to permit tools that require a JavaBean instance to operate.
|
* This constructor is {@code public} to permit tools that require a JavaBean instance to operate.</p>
|
||||||
*/
|
*/
|
||||||
public FieldUtils() {
|
public FieldUtils() {
|
||||||
super();
|
super();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets an accessible <code>Field</code> by name respecting scope. Superclasses/interfaces will be considered.
|
* Gets an accessible {@link Field} by name respecting scope. Superclasses/interfaces will be considered.
|
||||||
*
|
*
|
||||||
* @param cls
|
* @param cls
|
||||||
* the class to reflect, must not be null
|
* the {@link Class} to reflect, must not be {@code null}
|
||||||
* @param fieldName
|
* @param fieldName
|
||||||
* the field name to obtain
|
* the field name to obtain
|
||||||
* @return the Field object
|
* @return the Field object
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if the class or field name is null
|
* if the class is {@code null}, or the field name is blank or empty
|
||||||
*/
|
*/
|
||||||
public static Field getField(final Class<?> cls, final String fieldName) {
|
public static Field getField(final Class<?> cls, final String fieldName) {
|
||||||
final Field field = getField(cls, fieldName, false);
|
final Field field = getField(cls, fieldName, false);
|
||||||
|
@ -62,27 +65,24 @@ public class FieldUtils {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets an accessible <code>Field</code> by name breaking scope if requested. Superclasses/interfaces will be
|
* Gets an accessible {@link Field} by name, breaking scope if requested. Superclasses/interfaces will be
|
||||||
* considered.
|
* considered.
|
||||||
*
|
*
|
||||||
* @param cls
|
* @param cls
|
||||||
* the class to reflect, must not be null
|
* the {@link Class} to reflect, must not be {@code null}
|
||||||
* @param fieldName
|
* @param fieldName
|
||||||
* the field name to obtain
|
* the field name to obtain
|
||||||
* @param forceAccess
|
* @param forceAccess
|
||||||
* whether to break scope restrictions using the <code>setAccessible</code> method. <code>False</code>
|
* whether to break scope restrictions using the {@link AccessibleObject#setAccessible(boolean)} method.
|
||||||
* will only match public fields.
|
* {@code false} will only match {@code public} fields.
|
||||||
* @return the Field object
|
* @return the Field object
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if the class or field name is null
|
* if the class is {@code null}, or the field name is blank or empty or is matched at
|
||||||
|
* multiple places in the inheritance hierarchy
|
||||||
*/
|
*/
|
||||||
public static Field getField(final Class<?> cls, final String fieldName, final boolean forceAccess) {
|
public static Field getField(final Class<?> cls, final String fieldName, final boolean forceAccess) {
|
||||||
if (cls == null) {
|
Validate.isTrue(cls != null, "The class must not be null");
|
||||||
throw new IllegalArgumentException("The class must not be null");
|
Validate.isTrue(StringUtils.isNotBlank(fieldName), "The field name must not be blank/empty");
|
||||||
}
|
|
||||||
if (fieldName == null) {
|
|
||||||
throw new IllegalArgumentException("The field name must not be null");
|
|
||||||
}
|
|
||||||
// Sun Java 1.3 has a bugged implementation of getField hence we write the
|
// Sun Java 1.3 has a bugged implementation of getField hence we write the
|
||||||
// code ourselves
|
// code ourselves
|
||||||
|
|
||||||
|
@ -120,11 +120,9 @@ public class FieldUtils {
|
||||||
Field match = null;
|
Field match = null;
|
||||||
for (final Class<?> class1 : ClassUtils.getAllInterfaces(cls)) {
|
for (final Class<?> class1 : ClassUtils.getAllInterfaces(cls)) {
|
||||||
try {
|
try {
|
||||||
final Field test = ((Class<?>) class1).getField(fieldName);
|
final Field test = class1.getField(fieldName);
|
||||||
if (match != null) {
|
Validate.isTrue(match == null, "Reference to field %s is ambiguous relative to %s"
|
||||||
throw new IllegalArgumentException("Reference to field " + fieldName + " is ambiguous relative to " + cls +
|
+ "; a matching field exists on two or more implemented interfaces.", fieldName, cls);
|
||||||
"; a matching field exists on two or more implemented interfaces.");
|
|
||||||
}
|
|
||||||
match = test;
|
match = test;
|
||||||
} catch (final NoSuchFieldException ex) { // NOPMD
|
} catch (final NoSuchFieldException ex) { // NOPMD
|
||||||
// ignore
|
// ignore
|
||||||
|
@ -134,42 +132,38 @@ public class FieldUtils {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets an accessible <code>Field</code> by name respecting scope. Only the specified class will be considered.
|
* Gets an accessible {@link Field} by name respecting scope. Only the specified class will be considered.
|
||||||
*
|
*
|
||||||
* @param cls
|
* @param cls
|
||||||
* the class to reflect, must not be null
|
* the {@link Class} to reflect, must not be {@code null}
|
||||||
* @param fieldName
|
* @param fieldName
|
||||||
* the field name to obtain
|
* the field name to obtain
|
||||||
* @return the Field object
|
* @return the Field object
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if the class or field name is null
|
* if the class is {@code null}, or the field name is blank or empty
|
||||||
*/
|
*/
|
||||||
public static Field getDeclaredField(final Class<?> cls, final String fieldName) {
|
public static Field getDeclaredField(final Class<?> cls, final String fieldName) {
|
||||||
return getDeclaredField(cls, fieldName, false);
|
return getDeclaredField(cls, fieldName, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets an accessible <code>Field</code> by name breaking scope if requested. Only the specified class will be
|
* Gets an accessible {@link Field} by name, breaking scope if requested. Only the specified class will be
|
||||||
* considered.
|
* considered.
|
||||||
*
|
*
|
||||||
* @param cls
|
* @param cls
|
||||||
* the class to reflect, must not be null
|
* the {@link Class} to reflect, must not be {@code null}
|
||||||
* @param fieldName
|
* @param fieldName
|
||||||
* the field name to obtain
|
* the field name to obtain
|
||||||
* @param forceAccess
|
* @param forceAccess
|
||||||
* whether to break scope restrictions using the <code>setAccessible</code> method. False will only
|
* whether to break scope restrictions using the {@link AccessibleObject#setAccessible(boolean)} method.
|
||||||
* match public fields.
|
* {@code false} will only match {@code public} fields.
|
||||||
* @return the Field object
|
* @return the Field object
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if the class or field name is null
|
* if the class is {@code null}, or the field name is blank or empty
|
||||||
*/
|
*/
|
||||||
public static Field getDeclaredField(final Class<?> cls, final String fieldName, final boolean forceAccess) {
|
public static Field getDeclaredField(final Class<?> cls, final String fieldName, final boolean forceAccess) {
|
||||||
if (cls == null) {
|
Validate.isTrue(cls != null, "The class must not be null");
|
||||||
throw new IllegalArgumentException("The class must not be null");
|
Validate.isTrue(StringUtils.isNotBlank(fieldName), "The field name must not be blank/empty");
|
||||||
}
|
|
||||||
if (fieldName == null) {
|
|
||||||
throw new IllegalArgumentException("The field name must not be null");
|
|
||||||
}
|
|
||||||
try {
|
try {
|
||||||
// only consider the specified class by using getDeclaredField()
|
// only consider the specified class by using getDeclaredField()
|
||||||
final Field field = cls.getDeclaredField(fieldName);
|
final Field field = cls.getDeclaredField(fieldName);
|
||||||
|
@ -191,8 +185,10 @@ public class FieldUtils {
|
||||||
* Gets all fields of the given class and its parents (if any).
|
* Gets all fields of the given class and its parents (if any).
|
||||||
*
|
*
|
||||||
* @param cls
|
* @param cls
|
||||||
* the class to query
|
* the {@link Class} to query
|
||||||
* @return an array of Fields (maybe an empty array).
|
* @return an array of Fields (possibly empty).
|
||||||
|
* @throws IllegalArgumentException
|
||||||
|
* if the class is {@code null}
|
||||||
* @since 3.2
|
* @since 3.2
|
||||||
*/
|
*/
|
||||||
public static Field[] getAllFields(Class<?> cls) {
|
public static Field[] getAllFields(Class<?> cls) {
|
||||||
|
@ -204,15 +200,15 @@ public class FieldUtils {
|
||||||
* Gets all fields of the given class and its parents (if any).
|
* Gets all fields of the given class and its parents (if any).
|
||||||
*
|
*
|
||||||
* @param cls
|
* @param cls
|
||||||
* the class to query
|
* the {@link Class} to query
|
||||||
* @return an array of Fields (maybe an empty array).
|
* @return an array of Fields (possibly empty).
|
||||||
|
* @throws IllegalArgumentException
|
||||||
|
* if the class is {@code null}
|
||||||
* @since 3.2
|
* @since 3.2
|
||||||
*/
|
*/
|
||||||
public static List<Field> getAllFieldsList(Class<?> cls) {
|
public static List<Field> getAllFieldsList(Class<?> cls) {
|
||||||
if (cls == null) {
|
Validate.isTrue(cls != null, "The class must not be null");
|
||||||
throw new IllegalArgumentException("The class must not be null");
|
final List<Field> allFields = new ArrayList<Field>();
|
||||||
}
|
|
||||||
List<Field> allFields = new ArrayList<Field>();
|
|
||||||
Class<?> currentClass = cls;
|
Class<?> currentClass = cls;
|
||||||
while (currentClass != null) {
|
while (currentClass != null) {
|
||||||
final Field[] declaredFields = currentClass.getDeclaredFields();
|
final Field[] declaredFields = currentClass.getDeclaredFields();
|
||||||
|
@ -225,13 +221,13 @@ public class FieldUtils {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Reads an accessible static Field.
|
* Reads an accessible {@code static} {@link Field}.
|
||||||
*
|
*
|
||||||
* @param field
|
* @param field
|
||||||
* to read
|
* to read
|
||||||
* @return the field value
|
* @return the field value
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if the field is null or not static
|
* if the field is {@code null}, or not {@code static}
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the field is not accessible
|
* if the field is not accessible
|
||||||
*/
|
*/
|
||||||
|
@ -240,38 +236,35 @@ public class FieldUtils {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Reads a static Field.
|
* Reads a static {@link Field}.
|
||||||
*
|
*
|
||||||
* @param field
|
* @param field
|
||||||
* to read
|
* to read
|
||||||
* @param forceAccess
|
* @param forceAccess
|
||||||
* whether to break scope restrictions using the <code>setAccessible</code> method.
|
* whether to break scope restrictions using the {@link AccessibleObject#setAccessible(boolean)} method.
|
||||||
* @return the field value
|
* @return the field value
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if the field is null or not static
|
* if the field is {@code null} or not {@code static}
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the field is not made accessible
|
* if the field is not made accessible
|
||||||
*/
|
*/
|
||||||
public static Object readStaticField(final Field field, final boolean forceAccess) throws IllegalAccessException {
|
public static Object readStaticField(final Field field, final boolean forceAccess) throws IllegalAccessException {
|
||||||
if (field == null) {
|
Validate.isTrue(field != null, "The field must not be null");
|
||||||
throw new IllegalArgumentException("The field must not be null");
|
Validate.isTrue(Modifier.isStatic(field.getModifiers()), "The field '%s' is not static", field.getName());
|
||||||
}
|
|
||||||
if (!Modifier.isStatic(field.getModifiers())) {
|
|
||||||
throw new IllegalArgumentException("The field '" + field.getName() + "' is not static");
|
|
||||||
}
|
|
||||||
return readField(field, (Object) null, forceAccess);
|
return readField(field, (Object) null, forceAccess);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Reads the named public static field. Superclasses will be considered.
|
* Reads the named {@code public static} {@link Field}. Superclasses will be considered.
|
||||||
*
|
*
|
||||||
* @param cls
|
* @param cls
|
||||||
* the class to reflect, must not be null
|
* the {@link Class} to reflect, must not be {@code null}
|
||||||
* @param fieldName
|
* @param fieldName
|
||||||
* the field name to obtain
|
* the field name to obtain
|
||||||
* @return the value of the field
|
* @return the value of the field
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if the class is null, the field name is null or if the field could not be found
|
* if the class is {@code null}, or the field name is blank or empty,
|
||||||
|
* is not {@code static}, or could not be found
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the field is not accessible
|
* if the field is not accessible
|
||||||
*/
|
*/
|
||||||
|
@ -280,40 +273,41 @@ public class FieldUtils {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Reads the named static field. Superclasses will be considered.
|
* Reads the named {@code static} {@link Field}. Superclasses will be considered.
|
||||||
*
|
*
|
||||||
* @param cls
|
* @param cls
|
||||||
* the class to reflect, must not be null
|
* the {@link Class} to reflect, must not be {@code null}
|
||||||
* @param fieldName
|
* @param fieldName
|
||||||
* the field name to obtain
|
* the field name to obtain
|
||||||
* @param forceAccess
|
* @param forceAccess
|
||||||
* whether to break scope restrictions using the <code>setAccessible</code> method. <code>False</code>
|
* whether to break scope restrictions using the {@link AccessibleObject#setAccessible(false)} method.
|
||||||
* will only match public fields.
|
* {@code false} will only match {@code public} fields.
|
||||||
* @return the Field object
|
* @return the Field object
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if the class is null, the field name is null or if the field could not be found
|
* if the class is {@code null}, or the field name is blank or empty,
|
||||||
|
* is not {@code static}, or could not be found
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the field is not made accessible
|
* if the field is not made accessible
|
||||||
*/
|
*/
|
||||||
public static Object readStaticField(final Class<?> cls, final String fieldName, final boolean forceAccess) throws IllegalAccessException {
|
public static Object readStaticField(final Class<?> cls, final String fieldName, final boolean forceAccess) throws IllegalAccessException {
|
||||||
final Field field = getField(cls, fieldName, forceAccess);
|
final Field field = getField(cls, fieldName, forceAccess);
|
||||||
if (field == null) {
|
Validate.isTrue(field != null, "Cannot locate field '%s' on %s", fieldName, cls);
|
||||||
throw new IllegalArgumentException("Cannot locate field " + fieldName + " on " + cls);
|
|
||||||
}
|
|
||||||
// already forced access above, don't repeat it here:
|
// already forced access above, don't repeat it here:
|
||||||
return readStaticField(field, false);
|
return readStaticField(field, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets a static Field value by name. The field must be public. Only the specified class will be considered.
|
* Gets the value of a {@code static} {@link Field} by name. The field must be {@code public}.
|
||||||
|
* Only the specified class will be considered.
|
||||||
*
|
*
|
||||||
* @param cls
|
* @param cls
|
||||||
* the class to reflect, must not be null
|
* the {@link Class} to reflect, must not be {@code null}
|
||||||
* @param fieldName
|
* @param fieldName
|
||||||
* the field name to obtain
|
* the field name to obtain
|
||||||
* @return the value of the field
|
* @return the value of the field
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if the class is null, the field name is null or if the field could not be found
|
* if the class is {@code null}, or the field name is blank or empty,
|
||||||
|
* is not {@code static}, or could not be found
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the field is not accessible
|
* if the field is not accessible
|
||||||
*/
|
*/
|
||||||
|
@ -322,40 +316,40 @@ public class FieldUtils {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets a static Field value by name. Only the specified class will be considered.
|
* Gets the value of a {@code static} {@link Field} by name.
|
||||||
|
* Only the specified class will be considered.
|
||||||
*
|
*
|
||||||
* @param cls
|
* @param cls
|
||||||
* the class to reflect, must not be null
|
* the {@link Class} to reflect, must not be {@code null}
|
||||||
* @param fieldName
|
* @param fieldName
|
||||||
* the field name to obtain
|
* the field name to obtain
|
||||||
* @param forceAccess
|
* @param forceAccess
|
||||||
* whether to break scope restrictions using the <code>setAccessible</code> method. <code>False</code>
|
* whether to break scope restrictions using the {@link AccessibleObject#setAccessible(boolean)} method.
|
||||||
* will only match public fields.
|
* {@code false} will only match {@code public} fields.
|
||||||
* @return the Field object
|
* @return the Field object
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if the class is null, the field name is null or if the field could not be found
|
* if the class is {@code null}, or the field name is blank or empty,
|
||||||
|
* is not {@code static}, or could not be found
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the field is not made accessible
|
* if the field is not made accessible
|
||||||
*/
|
*/
|
||||||
public static Object readDeclaredStaticField(final Class<?> cls, final String fieldName, final boolean forceAccess) throws IllegalAccessException {
|
public static Object readDeclaredStaticField(final Class<?> cls, final String fieldName, final boolean forceAccess) throws IllegalAccessException {
|
||||||
final Field field = getDeclaredField(cls, fieldName, forceAccess);
|
final Field field = getDeclaredField(cls, fieldName, forceAccess);
|
||||||
if (field == null) {
|
Validate.isTrue(field != null, "Cannot locate declared field %s.%s", cls.getName(), fieldName);
|
||||||
throw new IllegalArgumentException("Cannot locate declared field " + cls.getName() + "." + fieldName);
|
|
||||||
}
|
|
||||||
// already forced access above, don't repeat it here:
|
// already forced access above, don't repeat it here:
|
||||||
return readStaticField(field, false);
|
return readStaticField(field, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Reads an accessible Field.
|
* Reads an accessible {@link Field}.
|
||||||
*
|
*
|
||||||
* @param field
|
* @param field
|
||||||
* the field to use
|
* the field to use
|
||||||
* @param target
|
* @param target
|
||||||
* the object to call on, may be null for static fields
|
* the object to call on, may be {@code null} for {@code static} fields
|
||||||
* @return the field value
|
* @return the field value
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if the field is null
|
* if the field is {@code null}
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the field is not accessible
|
* if the field is not accessible
|
||||||
*/
|
*/
|
||||||
|
@ -364,24 +358,22 @@ public class FieldUtils {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Reads a Field.
|
* Reads a {@link Field}.
|
||||||
*
|
*
|
||||||
* @param field
|
* @param field
|
||||||
* the field to use
|
* the field to use
|
||||||
* @param target
|
* @param target
|
||||||
* the object to call on, may be null for static fields
|
* the object to call on, may be {@code null} for {@code static} fields
|
||||||
* @param forceAccess
|
* @param forceAccess
|
||||||
* whether to break scope restrictions using the <code>setAccessible</code> method.
|
* whether to break scope restrictions using the {@link AccessibleObject#setAccessible(boolean)} method.
|
||||||
* @return the field value
|
* @return the field value
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if the field is null
|
* if the field is {@code null}
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the field is not made accessible
|
* if the field is not made accessible
|
||||||
*/
|
*/
|
||||||
public static Object readField(final Field field, final Object target, final boolean forceAccess) throws IllegalAccessException {
|
public static Object readField(final Field field, final Object target, final boolean forceAccess) throws IllegalAccessException {
|
||||||
if (field == null) {
|
Validate.isTrue(field != null, "The field must not be null");
|
||||||
throw new IllegalArgumentException("The field must not be null");
|
|
||||||
}
|
|
||||||
if (forceAccess && !field.isAccessible()) {
|
if (forceAccess && !field.isAccessible()) {
|
||||||
field.setAccessible(true);
|
field.setAccessible(true);
|
||||||
} else {
|
} else {
|
||||||
|
@ -391,268 +383,270 @@ public class FieldUtils {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Reads the named public field. Superclasses will be considered.
|
* Reads the named {@code public} {@link Field}. Superclasses will be considered.
|
||||||
*
|
*
|
||||||
* @param target
|
* @param target
|
||||||
* the object to reflect, must not be null
|
* the object to reflect, must not be {@code null}
|
||||||
* @param fieldName
|
* @param fieldName
|
||||||
* the field name to obtain
|
* the field name to obtain
|
||||||
* @return the value of the field
|
* @return the value of the field
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if the class or field name is null
|
* if the class is {@code null}, or
|
||||||
|
* the field name is blank or empty or could not be found
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the named field is not public
|
* if the named field is not {@code public}
|
||||||
*/
|
*/
|
||||||
public static Object readField(final Object target, final String fieldName) throws IllegalAccessException {
|
public static Object readField(final Object target, final String fieldName) throws IllegalAccessException {
|
||||||
return readField(target, fieldName, false);
|
return readField(target, fieldName, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Reads the named field. Superclasses will be considered.
|
* Reads the named {@link Field}. Superclasses will be considered.
|
||||||
*
|
*
|
||||||
* @param target
|
* @param target
|
||||||
* the object to reflect, must not be null
|
* the object to reflect, must not be {@code null}
|
||||||
* @param fieldName
|
* @param fieldName
|
||||||
* the field name to obtain
|
* the field name to obtain
|
||||||
* @param forceAccess
|
* @param forceAccess
|
||||||
* whether to break scope restrictions using the <code>setAccessible</code> method. <code>False</code>
|
* whether to break scope restrictions using the {@link AccessibleObject#setAccessible(boolean)} method.
|
||||||
* will only match public fields.
|
* {@code false} will only match {@code public} fields.
|
||||||
* @return the field value
|
* @return the field value
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if the class or field name is null
|
* if {@code target} is {@code null}, or
|
||||||
|
* the field name is blank or empty or could not be found
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the named field is not made accessible
|
* if the named field is not made accessible
|
||||||
*/
|
*/
|
||||||
public static Object readField(final Object target, final String fieldName, final boolean forceAccess) throws IllegalAccessException {
|
public static Object readField(final Object target, final String fieldName, final boolean forceAccess) throws IllegalAccessException {
|
||||||
if (target == null) {
|
Validate.isTrue(target != null, "target object must not be null");
|
||||||
throw new IllegalArgumentException("target object must not be null");
|
|
||||||
}
|
|
||||||
final Class<?> cls = target.getClass();
|
final Class<?> cls = target.getClass();
|
||||||
final Field field = getField(cls, fieldName, forceAccess);
|
final Field field = getField(cls, fieldName, forceAccess);
|
||||||
if (field == null) {
|
Validate.isTrue(field != null, "Cannot locate field %s on %s" , fieldName, cls);
|
||||||
throw new IllegalArgumentException("Cannot locate field " + fieldName + " on " + cls);
|
|
||||||
}
|
|
||||||
// already forced access above, don't repeat it here:
|
// already forced access above, don't repeat it here:
|
||||||
return readField(field, target);
|
return readField(field, target);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Reads the named public field. Only the class of the specified object will be considered.
|
* Reads the named {@code public} {@link Field}. Only the class of the specified object will be considered.
|
||||||
*
|
*
|
||||||
* @param target
|
* @param target
|
||||||
* the object to reflect, must not be null
|
* the object to reflect, must not be {@code null}
|
||||||
* @param fieldName
|
* @param fieldName
|
||||||
* the field name to obtain
|
* the field name to obtain
|
||||||
* @return the value of the field
|
* @return the value of the field
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if the class or field name is null
|
* if {@code target} is {@code null}, or
|
||||||
|
* the field name is blank or empty or could not be found
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the named field is not public
|
* if the named field is not {@code public}
|
||||||
*/
|
*/
|
||||||
public static Object readDeclaredField(final Object target, final String fieldName) throws IllegalAccessException {
|
public static Object readDeclaredField(final Object target, final String fieldName) throws IllegalAccessException {
|
||||||
return readDeclaredField(target, fieldName, false);
|
return readDeclaredField(target, fieldName, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* <p<>Gets a Field value by name. Only the class of the specified object will be considered.
|
* <p<>Gets a {@link Field} value by name. Only the class of the specified object will be considered.
|
||||||
*
|
*
|
||||||
* @param target
|
* @param target
|
||||||
* the object to reflect, must not be null
|
* the object to reflect, must not be {@code null}
|
||||||
* @param fieldName
|
* @param fieldName
|
||||||
* the field name to obtain
|
* the field name to obtain
|
||||||
* @param forceAccess
|
* @param forceAccess
|
||||||
* whether to break scope restrictions using the <code>setAccessible</code> method. <code>False</code>
|
* whether to break scope restrictions using the {@link AccessibleObject#setAccessible(boolean)} method.
|
||||||
* will only match public fields.
|
* {@code false} will only match public fields.
|
||||||
* @return the Field object
|
* @return the Field object
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if <code>target</code> or <code>fieldName</code> is null
|
* if {@code target} is {@code null}, or
|
||||||
|
* the field name is blank or empty or could not be found
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the field is not made accessible
|
* if the field is not made accessible
|
||||||
*/
|
*/
|
||||||
public static Object readDeclaredField(final Object target, final String fieldName, final boolean forceAccess) throws IllegalAccessException {
|
public static Object readDeclaredField(final Object target, final String fieldName, final boolean forceAccess) throws IllegalAccessException {
|
||||||
if (target == null) {
|
Validate.isTrue(target != null, "target object must not be null");
|
||||||
throw new IllegalArgumentException("target object must not be null");
|
|
||||||
}
|
|
||||||
final Class<?> cls = target.getClass();
|
final Class<?> cls = target.getClass();
|
||||||
final Field field = getDeclaredField(cls, fieldName, forceAccess);
|
final Field field = getDeclaredField(cls, fieldName, forceAccess);
|
||||||
if (field == null) {
|
Validate.isTrue(field != null, "Cannot locate declared field %s.%s" , cls, fieldName);
|
||||||
throw new IllegalArgumentException("Cannot locate declared field " + cls.getName() + "." + fieldName);
|
|
||||||
}
|
|
||||||
// already forced access above, don't repeat it here:
|
// already forced access above, don't repeat it here:
|
||||||
return readField(field, target);
|
return readField(field, target);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Writes a public static Field.
|
* Writes a {@code public static} {@link Field}.
|
||||||
*
|
*
|
||||||
* @param field
|
* @param field
|
||||||
* to write
|
* to write
|
||||||
* @param value
|
* @param value
|
||||||
* to set
|
* to set
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if the field is null or not static
|
* if the field is {@code null} or not {@code static},
|
||||||
|
* or {@code value} is not assignable
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the field is not public or is final
|
* if the field is not {@code public} or is {@code final}
|
||||||
*/
|
*/
|
||||||
public static void writeStaticField(final Field field, final Object value) throws IllegalAccessException {
|
public static void writeStaticField(final Field field, final Object value) throws IllegalAccessException {
|
||||||
writeStaticField(field, value, false);
|
writeStaticField(field, value, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Writes a static Field.
|
* Writes a static {@link Field}.
|
||||||
*
|
*
|
||||||
* @param field
|
* @param field
|
||||||
* to write
|
* to write
|
||||||
* @param value
|
* @param value
|
||||||
* to set
|
* to set
|
||||||
* @param forceAccess
|
* @param forceAccess
|
||||||
* whether to break scope restrictions using the <code>setAccessible</code> method. <code>False</code>
|
* whether to break scope restrictions using the {@link AccessibleObject#setAccessible(boolean)} method. {@code false}
|
||||||
* will only match public fields.
|
* will only match {@code public} fields.
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if the field is null or not static
|
* if the field is {@code null} or not {@code static},
|
||||||
|
* or {@code value} is not assignable
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the field is not made accessible or is final
|
* if the field is not made accessible or is {@code final}
|
||||||
*/
|
*/
|
||||||
public static void writeStaticField(final Field field, final Object value, final boolean forceAccess) throws IllegalAccessException {
|
public static void writeStaticField(final Field field, final Object value, final boolean forceAccess) throws IllegalAccessException {
|
||||||
if (field == null) {
|
Validate.isTrue(field != null, "The field must not be null");
|
||||||
throw new IllegalArgumentException("The field must not be null");
|
Validate.isTrue(Modifier.isStatic(field.getModifiers()), "The field %s.%s is not static",
|
||||||
}
|
field.getDeclaringClass().getName(), field.getName());
|
||||||
if (!Modifier.isStatic(field.getModifiers())) {
|
|
||||||
throw new IllegalArgumentException("The field '" + field.getName() + "' is not static");
|
|
||||||
}
|
|
||||||
writeField(field, (Object) null, value, forceAccess);
|
writeField(field, (Object) null, value, forceAccess);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Writes a named public static Field. Superclasses will be considered.
|
* Writes a named {@code public static} {@link Field}. Superclasses will be considered.
|
||||||
*
|
*
|
||||||
* @param cls
|
* @param cls
|
||||||
* Class on which the Field is to be found
|
* {@link Class} on which the field is to be found
|
||||||
* @param fieldName
|
* @param fieldName
|
||||||
* to write
|
* to write
|
||||||
* @param value
|
* @param value
|
||||||
* to set
|
* to set
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if the field cannot be located or is not static
|
* if {@code cls} is {@code null},
|
||||||
|
* the field name is blank or empty,
|
||||||
|
* the field cannot be located or is not {@code static}, or
|
||||||
|
* {@code value} is not assignable
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the field is not public or is final
|
* if the field is not {@code public} or is {@code final}
|
||||||
*/
|
*/
|
||||||
public static void writeStaticField(final Class<?> cls, final String fieldName, final Object value) throws IllegalAccessException {
|
public static void writeStaticField(final Class<?> cls, final String fieldName, final Object value) throws IllegalAccessException {
|
||||||
writeStaticField(cls, fieldName, value, false);
|
writeStaticField(cls, fieldName, value, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Writes a named static Field. Superclasses will be considered.
|
* Writes a named {@code static} {@link Field}. Superclasses will be considered.
|
||||||
*
|
*
|
||||||
* @param cls
|
* @param cls
|
||||||
* Class on which the Field is to be found
|
* {@link Class} on which the field is to be found
|
||||||
* @param fieldName
|
* @param fieldName
|
||||||
* to write
|
* to write
|
||||||
* @param value
|
* @param value
|
||||||
* to set
|
* to set
|
||||||
* @param forceAccess
|
* @param forceAccess
|
||||||
* whether to break scope restrictions using the <code>setAccessible</code> method. <code>False</code>
|
* whether to break scope restrictions using the {@link AccessibleObject#setAccessible(boolean)} method.
|
||||||
* will only match public fields.
|
* {@code false} will only match {@code public} fields.
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if the field cannot be located or is not static
|
* if {@code cls} is {@code null},
|
||||||
|
* the field name is blank or empty,
|
||||||
|
* the field cannot be located or is not {@code static}, or
|
||||||
|
* {@code value} is not assignable
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the field is not made accessible or is final
|
* if the field is not made accessible or is {@code final}
|
||||||
*/
|
*/
|
||||||
public static void writeStaticField(final Class<?> cls, final String fieldName, final Object value, final boolean forceAccess)
|
public static void writeStaticField(final Class<?> cls, final String fieldName, final Object value, final boolean forceAccess)
|
||||||
throws IllegalAccessException {
|
throws IllegalAccessException {
|
||||||
final Field field = getField(cls, fieldName, forceAccess);
|
final Field field = getField(cls, fieldName, forceAccess);
|
||||||
if (field == null) {
|
Validate.isTrue(field != null, "Cannot locate field %s on %s", fieldName, cls);
|
||||||
throw new IllegalArgumentException("Cannot locate field " + fieldName + " on " + cls);
|
|
||||||
}
|
|
||||||
// already forced access above, don't repeat it here:
|
// already forced access above, don't repeat it here:
|
||||||
writeStaticField(field, value);
|
writeStaticField(field, value);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Writes a named public static Field. Only the specified class will be considered.
|
* Writes a named {@code public static} {@link Field}. Only the specified class will be considered.
|
||||||
*
|
*
|
||||||
* @param cls
|
* @param cls
|
||||||
* Class on which the Field is to be found
|
* {@link Class} on which the field is to be found
|
||||||
* @param fieldName
|
* @param fieldName
|
||||||
* to write
|
* to write
|
||||||
* @param value
|
* @param value
|
||||||
* to set
|
* to set
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if the field cannot be located or is not static
|
* if {@code cls} is {@code null},
|
||||||
|
* the field name is blank or empty,
|
||||||
|
* the field cannot be located or is not {@code static}, or
|
||||||
|
* {@code value} is not assignable
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the field is not public or is final
|
* if the field is not {@code public} or is {@code final}
|
||||||
*/
|
*/
|
||||||
public static void writeDeclaredStaticField(final Class<?> cls, final String fieldName, final Object value) throws IllegalAccessException {
|
public static void writeDeclaredStaticField(final Class<?> cls, final String fieldName, final Object value) throws IllegalAccessException {
|
||||||
writeDeclaredStaticField(cls, fieldName, value, false);
|
writeDeclaredStaticField(cls, fieldName, value, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Writes a named static Field. Only the specified class will be considered.
|
* Writes a named {@code static} {@link Field}. Only the specified class will be considered.
|
||||||
*
|
*
|
||||||
* @param cls
|
* @param cls
|
||||||
* Class on which the Field is to be found
|
* {@link Class} on which the field is to be found
|
||||||
* @param fieldName
|
* @param fieldName
|
||||||
* to write
|
* to write
|
||||||
* @param value
|
* @param value
|
||||||
* to set
|
* to set
|
||||||
* @param forceAccess
|
* @param forceAccess
|
||||||
* whether to break scope restrictions using the <code>setAccessible</code> method. <code>False</code>
|
* whether to break scope restrictions using the {@code AccessibleObject#setAccessible(boolean)} method.
|
||||||
* will only match public fields.
|
* {@code false} will only match {@code public} fields.
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if the field cannot be located or is not static
|
* if {@code cls} is {@code null},
|
||||||
|
* the field name is blank or empty,
|
||||||
|
* the field cannot be located or is not {@code static}, or
|
||||||
|
* {@code value} is not assignable
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the field is not made accessible or is final
|
* if the field is not made accessible or is {@code final}
|
||||||
*/
|
*/
|
||||||
public static void writeDeclaredStaticField(final Class<?> cls, final String fieldName, final Object value, final boolean forceAccess)
|
public static void writeDeclaredStaticField(final Class<?> cls, final String fieldName, final Object value, final boolean forceAccess)
|
||||||
throws IllegalAccessException {
|
throws IllegalAccessException {
|
||||||
final Field field = getDeclaredField(cls, fieldName, forceAccess);
|
final Field field = getDeclaredField(cls, fieldName, forceAccess);
|
||||||
if (field == null) {
|
Validate.isTrue(field != null, "Cannot locate declared field %s.%s", cls.getName(), fieldName);
|
||||||
throw new IllegalArgumentException("Cannot locate declared field " + cls.getName() + "." + fieldName);
|
|
||||||
}
|
|
||||||
// already forced access above, don't repeat it here:
|
// already forced access above, don't repeat it here:
|
||||||
writeField(field, (Object) null, value);
|
writeField(field, (Object) null, value);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Writes an accessible field.
|
* Writes an accessible {@link Field}.
|
||||||
*
|
*
|
||||||
* @param field
|
* @param field
|
||||||
* to write
|
* to write
|
||||||
* @param target
|
* @param target
|
||||||
* the object to call on, may be null for static fields
|
* the object to call on, may be {@code null} for {@code static} fields
|
||||||
* @param value
|
* @param value
|
||||||
* to set
|
* to set
|
||||||
* @throws IllegalArgumentException
|
|
||||||
* if the field is null
|
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the field is not accessible or is final
|
* if the field or target is {@code null},
|
||||||
|
* the field is not accessible or is {@code final}, or
|
||||||
|
* {@code value} is not assignable
|
||||||
*/
|
*/
|
||||||
public static void writeField(final Field field, final Object target, final Object value) throws IllegalAccessException {
|
public static void writeField(final Field field, final Object target, final Object value) throws IllegalAccessException {
|
||||||
writeField(field, target, value, false);
|
writeField(field, target, value, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Writes a field.
|
* Writes a {@link Field}.
|
||||||
*
|
*
|
||||||
* @param field
|
* @param field
|
||||||
* to write
|
* to write
|
||||||
* @param target
|
* @param target
|
||||||
* the object to call on, may be null for static fields
|
* the object to call on, may be {@code null} for {@code static} fields
|
||||||
* @param value
|
* @param value
|
||||||
* to set
|
* to set
|
||||||
* @param forceAccess
|
* @param forceAccess
|
||||||
* whether to break scope restrictions using the <code>setAccessible</code> method. <code>False</code>
|
* whether to break scope restrictions using the {@link AccessibleObject#setAccessible(boolean)} method.
|
||||||
* will only match public fields.
|
* {@code false} will only match {@code public} fields.
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if the field is null
|
* if the field is {@code null} or
|
||||||
|
* {@code value} is not assignable
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the field is not made accessible or is final
|
* if the field is not made accessible or is {@code final}
|
||||||
*/
|
*/
|
||||||
public static void writeField(final Field field, final Object target, final Object value, final boolean forceAccess)
|
public static void writeField(final Field field, final Object target, final Object value, final boolean forceAccess)
|
||||||
throws IllegalAccessException {
|
throws IllegalAccessException {
|
||||||
if (field == null) {
|
Validate.isTrue(field != null, "The field must not be null");
|
||||||
throw new IllegalArgumentException("The field must not be null");
|
|
||||||
}
|
|
||||||
if (forceAccess && !field.isAccessible()) {
|
if (forceAccess && !field.isAccessible()) {
|
||||||
field.setAccessible(true);
|
field.setAccessible(true);
|
||||||
} else {
|
} else {
|
||||||
|
@ -662,16 +656,18 @@ public class FieldUtils {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Writes a public field. Superclasses will be considered.
|
* Writes a {@code public} {@link Field}. Superclasses will be considered.
|
||||||
*
|
*
|
||||||
* @param target
|
* @param target
|
||||||
* the object to reflect, must not be null
|
* the object to reflect, must not be {@code null}
|
||||||
* @param fieldName
|
* @param fieldName
|
||||||
* the field name to obtain
|
* the field name to obtain
|
||||||
* @param value
|
* @param value
|
||||||
* to set
|
* to set
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if <code>target</code> or <code>fieldName</code> is null
|
* if {@code target} is {@code null},
|
||||||
|
* {@code fieldName} is blank or empty or could not be found,
|
||||||
|
* or {@code value} is not assignable
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the field is not accessible
|
* if the field is not accessible
|
||||||
*/
|
*/
|
||||||
|
@ -680,47 +676,47 @@ public class FieldUtils {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Writes a field. Superclasses will be considered.
|
* Writes a {@link Field}. Superclasses will be considered.
|
||||||
*
|
*
|
||||||
* @param target
|
* @param target
|
||||||
* the object to reflect, must not be null
|
* the object to reflect, must not be {@code null}
|
||||||
* @param fieldName
|
* @param fieldName
|
||||||
* the field name to obtain
|
* the field name to obtain
|
||||||
* @param value
|
* @param value
|
||||||
* to set
|
* to set
|
||||||
* @param forceAccess
|
* @param forceAccess
|
||||||
* whether to break scope restrictions using the <code>setAccessible</code> method. <code>False</code>
|
* whether to break scope restrictions using the {@link AccessibleObject#setAccessible(boolean)} method. {@code false}
|
||||||
* will only match public fields.
|
* will only match {@code public} fields.
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if <code>target</code> or <code>fieldName</code> is null
|
* if {@code target} is {@code null},
|
||||||
|
* {@code fieldName} is blank or empty or could not be found,
|
||||||
|
* or {@code value} is not assignable
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the field is not made accessible
|
* if the field is not made accessible
|
||||||
*/
|
*/
|
||||||
public static void writeField(final Object target, final String fieldName, final Object value, final boolean forceAccess)
|
public static void writeField(final Object target, final String fieldName, final Object value, final boolean forceAccess)
|
||||||
throws IllegalAccessException {
|
throws IllegalAccessException {
|
||||||
if (target == null) {
|
Validate.isTrue(target != null, "target object must not be null");
|
||||||
throw new IllegalArgumentException("target object must not be null");
|
|
||||||
}
|
|
||||||
final Class<?> cls = target.getClass();
|
final Class<?> cls = target.getClass();
|
||||||
final Field field = getField(cls, fieldName, forceAccess);
|
final Field field = getField(cls, fieldName, forceAccess);
|
||||||
if (field == null) {
|
Validate.isTrue(field != null, "Cannot locate declared field %s.%s", cls.getName(), fieldName);
|
||||||
throw new IllegalArgumentException("Cannot locate declared field " + cls.getName() + "." + fieldName);
|
|
||||||
}
|
|
||||||
// already forced access above, don't repeat it here:
|
// already forced access above, don't repeat it here:
|
||||||
writeField(field, target, value);
|
writeField(field, target, value);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Writes a public field. Only the specified class will be considered.
|
* Writes a {@code public} {@link Field}. Only the specified class will be considered.
|
||||||
*
|
*
|
||||||
* @param target
|
* @param target
|
||||||
* the object to reflect, must not be null
|
* the object to reflect, must not be {@code null}
|
||||||
* @param fieldName
|
* @param fieldName
|
||||||
* the field name to obtain
|
* the field name to obtain
|
||||||
* @param value
|
* @param value
|
||||||
* to set
|
* to set
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if <code>target</code> or <code>fieldName</code> is null
|
* if {@code target} is {@code null},
|
||||||
|
* {@code fieldName} is blank or empty or could not be found,
|
||||||
|
* or {@code value} is not assignable
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the field is not made accessible
|
* if the field is not made accessible
|
||||||
*/
|
*/
|
||||||
|
@ -729,32 +725,30 @@ public class FieldUtils {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Writes a public field. Only the specified class will be considered.
|
* Writes a {@code public} {@link Field}. Only the specified class will be considered.
|
||||||
*
|
*
|
||||||
* @param target
|
* @param target
|
||||||
* the object to reflect, must not be null
|
* the object to reflect, must not be {@code null}
|
||||||
* @param fieldName
|
* @param fieldName
|
||||||
* the field name to obtain
|
* the field name to obtain
|
||||||
* @param value
|
* @param value
|
||||||
* to set
|
* to set
|
||||||
* @param forceAccess
|
* @param forceAccess
|
||||||
* whether to break scope restrictions using the <code>setAccessible</code> method. <code>False</code>
|
* whether to break scope restrictions using the {@link AccessibleObject#setAccessible(boolean)} method.
|
||||||
* will only match public fields.
|
* {@code false} will only match {@code public} fields.
|
||||||
* @throws IllegalArgumentException
|
* @throws IllegalArgumentException
|
||||||
* if <code>target</code> or <code>fieldName</code> is null
|
* if {@code target} is {@code null},
|
||||||
|
* {@code fieldName} is blank or empty or could not be found,
|
||||||
|
* or {@code value} is not assignable
|
||||||
* @throws IllegalAccessException
|
* @throws IllegalAccessException
|
||||||
* if the field is not made accessible
|
* if the field is not made accessible
|
||||||
*/
|
*/
|
||||||
public static void writeDeclaredField(final Object target, final String fieldName, final Object value, final boolean forceAccess)
|
public static void writeDeclaredField(final Object target, final String fieldName, final Object value, final boolean forceAccess)
|
||||||
throws IllegalAccessException {
|
throws IllegalAccessException {
|
||||||
if (target == null) {
|
Validate.isTrue(target != null, "target object must not be null");
|
||||||
throw new IllegalArgumentException("target object must not be null");
|
|
||||||
}
|
|
||||||
final Class<?> cls = target.getClass();
|
final Class<?> cls = target.getClass();
|
||||||
final Field field = getDeclaredField(cls, fieldName, forceAccess);
|
final Field field = getDeclaredField(cls, fieldName, forceAccess);
|
||||||
if (field == null) {
|
Validate.isTrue(field != null, "Cannot locate declared field %s.%s", cls.getName(), fieldName);
|
||||||
throw new IllegalArgumentException("Cannot locate declared field " + cls.getName() + "." + fieldName);
|
|
||||||
}
|
|
||||||
// already forced access above, don't repeat it here:
|
// already forced access above, don't repeat it here:
|
||||||
writeField(field, target, value);
|
writeField(field, target, value);
|
||||||
}
|
}
|
||||||
|
|
|
@ -23,8 +23,8 @@ import java.lang.reflect.Modifier;
|
||||||
import org.apache.commons.lang3.ClassUtils;
|
import org.apache.commons.lang3.ClassUtils;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Contains common code for working with Methods/Constructors, extracted and
|
* Contains common code for working with {@link Method}s/{@link Constructor}s, extracted and
|
||||||
* refactored from <code>MethodUtils</code> when it was imported from Commons
|
* refactored from {@link MethodUtils} when it was imported from Commons
|
||||||
* BeanUtils.
|
* BeanUtils.
|
||||||
*
|
*
|
||||||
* @since 2.5
|
* @since 2.5
|
||||||
|
@ -42,11 +42,11 @@ abstract class MemberUtils {
|
||||||
/**
|
/**
|
||||||
* XXX Default access superclass workaround
|
* XXX Default access superclass workaround
|
||||||
*
|
*
|
||||||
* When a public class has a default access superclass with public members,
|
* When a {@code public} class has a default access superclass with {@code public} members,
|
||||||
* these members are accessible. Calling them from compiled code works fine.
|
* these members are accessible. Calling them from compiled code works fine.
|
||||||
* Unfortunately, on some JVMs, using reflection to invoke these members
|
* Unfortunately, on some JVMs, using reflection to invoke these members
|
||||||
* seems to (wrongly) prevent access even when the modifier is public.
|
* seems to (wrongly) prevent access even when the modifier is {@code public}.
|
||||||
* Calling setAccessible(true) solves the problem but will only work from
|
* Calling {@code setAccessible(true)} solves the problem but will only work from
|
||||||
* sufficiently privileged code. Better workarounds would be gratefully
|
* sufficiently privileged code. Better workarounds would be gratefully
|
||||||
* accepted.
|
* accepted.
|
||||||
* @param o the AccessibleObject to set as accessible
|
* @param o the AccessibleObject to set as accessible
|
||||||
|
@ -69,16 +69,16 @@ abstract class MemberUtils {
|
||||||
/**
|
/**
|
||||||
* Returns whether a given set of modifiers implies package access.
|
* Returns whether a given set of modifiers implies package access.
|
||||||
* @param modifiers to test
|
* @param modifiers to test
|
||||||
* @return true unless package/protected/private modifier detected
|
* @return {@code true} unless {@code package}/{@code protected}/{@code private} modifier detected
|
||||||
*/
|
*/
|
||||||
static boolean isPackageAccess(final int modifiers) {
|
static boolean isPackageAccess(final int modifiers) {
|
||||||
return (modifiers & ACCESS_TEST) == 0;
|
return (modifiers & ACCESS_TEST) == 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns whether a Member is accessible.
|
* Returns whether a {@link Member} is accessible.
|
||||||
* @param m Member to check
|
* @param m Member to check
|
||||||
* @return true if <code>m</code> is accessible
|
* @return {@code true} if <code>m</code> is accessible
|
||||||
*/
|
*/
|
||||||
static boolean isAccessible(final Member m) {
|
static boolean isAccessible(final Member m) {
|
||||||
return m != null && Modifier.isPublic(m.getModifiers()) && !m.isSynthetic();
|
return m != null && Modifier.isPublic(m.getModifiers()) && !m.isSynthetic();
|
||||||
|
@ -93,8 +93,8 @@ abstract class MemberUtils {
|
||||||
* @param left the "left" parameter set
|
* @param left the "left" parameter set
|
||||||
* @param right the "right" parameter set
|
* @param right the "right" parameter set
|
||||||
* @param actual the runtime parameter types to match against
|
* @param actual the runtime parameter types to match against
|
||||||
* <code>left</code>/<code>right</code>
|
* {@code left}/{@code right}
|
||||||
* @return int consistent with <code>compare</code> semantics
|
* @return int consistent with {@code compare} semantics
|
||||||
*/
|
*/
|
||||||
static int compareParameterTypes(final Class<?>[] left, final Class<?>[] right, final Class<?>[] actual) {
|
static int compareParameterTypes(final Class<?>[] left, final Class<?>[] right, final Class<?>[] actual) {
|
||||||
final float leftCost = getTotalTransformationCost(actual, left);
|
final float leftCost = getTotalTransformationCost(actual, left);
|
||||||
|
|
|
@ -16,6 +16,7 @@
|
||||||
*/
|
*/
|
||||||
package org.apache.commons.lang3.reflect;
|
package org.apache.commons.lang3.reflect;
|
||||||
|
|
||||||
|
import java.lang.reflect.AccessibleObject;
|
||||||
import java.lang.reflect.InvocationTargetException;
|
import java.lang.reflect.InvocationTargetException;
|
||||||
import java.lang.reflect.Method;
|
import java.lang.reflect.Method;
|
||||||
import java.lang.reflect.Modifier;
|
import java.lang.reflect.Modifier;
|
||||||
|
@ -33,19 +34,19 @@ import org.apache.commons.lang3.Validate;
|
||||||
import org.apache.commons.lang3.ClassUtils.Interfaces;
|
import org.apache.commons.lang3.ClassUtils.Interfaces;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* <p>Utility reflection methods focused on methods, originally from Commons BeanUtils.
|
* <p>Utility reflection methods focused on {@link Method}s, originally from Commons BeanUtils.
|
||||||
* Differences from the BeanUtils version may be noted, especially where similar functionality
|
* Differences from the BeanUtils version may be noted, especially where similar functionality
|
||||||
* already existed within Lang.
|
* already existed within Lang.
|
||||||
* </p>
|
* </p>
|
||||||
*
|
*
|
||||||
* <h3>Known Limitations</h3>
|
* <h3>Known Limitations</h3>
|
||||||
* <h4>Accessing Public Methods In A Default Access Superclass</h4>
|
* <h4>Accessing Public Methods In A Default Access Superclass</h4>
|
||||||
* <p>There is an issue when invoking public methods contained in a default access superclass on JREs prior to 1.4.
|
* <p>There is an issue when invoking {@code public} methods contained in a default access superclass on JREs prior to 1.4.
|
||||||
* Reflection locates these methods fine and correctly assigns them as public.
|
* Reflection locates these methods fine and correctly assigns them as {@code public}.
|
||||||
* However, an <code>IllegalAccessException</code> is thrown if the method is invoked.</p>
|
* However, an {@link IllegalAccessException} is thrown if the method is invoked.</p>
|
||||||
*
|
*
|
||||||
* <p><code>MethodUtils</code> contains a workaround for this situation.
|
* <p>{@link MethodUtils} contains a workaround for this situation.
|
||||||
* It will attempt to call <code>setAccessible</code> on this method.
|
* It will attempt to call {@link AccessibleObject#setAccessible(boolean)} on this method.
|
||||||
* If this call succeeds, then the method can be invoked as normal.
|
* If this call succeeds, then the method can be invoked as normal.
|
||||||
* This call will only succeed when the application has sufficient security privileges.
|
* This call will only succeed when the application has sufficient security privileges.
|
||||||
* If this call fails then the method may fail.</p>
|
* If this call fails then the method may fail.</p>
|
||||||
|
@ -56,11 +57,11 @@ import org.apache.commons.lang3.ClassUtils.Interfaces;
|
||||||
public class MethodUtils {
|
public class MethodUtils {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* <p>MethodUtils instances should NOT be constructed in standard programming.
|
* <p>{@link MethodUtils} instances should NOT be constructed in standard programming.
|
||||||
* Instead, the class should be used as
|
* Instead, the class should be used as
|
||||||
* <code>MethodUtils.getAccessibleMethod(method)</code>.</p>
|
* {@code MethodUtils.getAccessibleMethod(method)}.</p>
|
||||||
*
|
*
|
||||||
* <p>This constructor is public to permit tools that require a JavaBean
|
* <p>This constructor is {@code public} to permit tools that require a JavaBean
|
||||||
* instance to operate.</p>
|
* instance to operate.</p>
|
||||||
*/
|
*/
|
||||||
public MethodUtils() {
|
public MethodUtils() {
|
||||||
|
@ -73,8 +74,8 @@ public class MethodUtils {
|
||||||
* <p>This method delegates the method search to {@link #getMatchingAccessibleMethod(Class, String, Class[])}.</p>
|
* <p>This method delegates the method search to {@link #getMatchingAccessibleMethod(Class, String, Class[])}.</p>
|
||||||
*
|
*
|
||||||
* <p>This method supports calls to methods taking primitive parameters
|
* <p>This method supports calls to methods taking primitive parameters
|
||||||
* via passing in wrapping classes. So, for example, a <code>Boolean</code> object
|
* via passing in wrapping classes. So, for example, a {@code Boolean} object
|
||||||
* would match a <code>boolean</code> primitive.</p>
|
* would match a {@code boolean} primitive.</p>
|
||||||
*
|
*
|
||||||
* <p>This is a convenient wrapper for
|
* <p>This is a convenient wrapper for
|
||||||
* {@link #invokeMethod(Object object,String methodName, Object[] args, Class[] parameterTypes)}.
|
* {@link #invokeMethod(Object object,String methodName, Object[] args, Class[] parameterTypes)}.
|
||||||
|
@ -92,9 +93,7 @@ public class MethodUtils {
|
||||||
public static Object invokeMethod(final Object object, final String methodName,
|
public static Object invokeMethod(final Object object, final String methodName,
|
||||||
Object... args) throws NoSuchMethodException,
|
Object... args) throws NoSuchMethodException,
|
||||||
IllegalAccessException, InvocationTargetException {
|
IllegalAccessException, InvocationTargetException {
|
||||||
if (args == null) {
|
args = ArrayUtils.nullToEmpty(args);
|
||||||
args = ArrayUtils.EMPTY_OBJECT_ARRAY;
|
|
||||||
}
|
|
||||||
final Class<?>[] parameterTypes = ClassUtils.toClass(args);
|
final Class<?>[] parameterTypes = ClassUtils.toClass(args);
|
||||||
return invokeMethod(object, methodName, args, parameterTypes);
|
return invokeMethod(object, methodName, args, parameterTypes);
|
||||||
}
|
}
|
||||||
|
@ -105,8 +104,8 @@ public class MethodUtils {
|
||||||
* <p>This method delegates the method search to {@link #getMatchingAccessibleMethod(Class, String, Class[])}.</p>
|
* <p>This method delegates the method search to {@link #getMatchingAccessibleMethod(Class, String, Class[])}.</p>
|
||||||
*
|
*
|
||||||
* <p>This method supports calls to methods taking primitive parameters
|
* <p>This method supports calls to methods taking primitive parameters
|
||||||
* via passing in wrapping classes. So, for example, a <code>Boolean</code> object
|
* via passing in wrapping classes. So, for example, a {@code Boolean} object
|
||||||
* would match a <code>boolean</code> primitive.</p>
|
* would match a {@code boolean} primitive.</p>
|
||||||
*
|
*
|
||||||
* @param object invoke method on this object
|
* @param object invoke method on this object
|
||||||
* @param methodName get method with this name
|
* @param methodName get method with this name
|
||||||
|
@ -122,12 +121,8 @@ public class MethodUtils {
|
||||||
Object[] args, Class<?>[] parameterTypes)
|
Object[] args, Class<?>[] parameterTypes)
|
||||||
throws NoSuchMethodException, IllegalAccessException,
|
throws NoSuchMethodException, IllegalAccessException,
|
||||||
InvocationTargetException {
|
InvocationTargetException {
|
||||||
if (parameterTypes == null) {
|
parameterTypes = ArrayUtils.nullToEmpty(parameterTypes);
|
||||||
parameterTypes = ArrayUtils.EMPTY_CLASS_ARRAY;
|
args = ArrayUtils.nullToEmpty(args);
|
||||||
}
|
|
||||||
if (args == null) {
|
|
||||||
args = ArrayUtils.EMPTY_OBJECT_ARRAY;
|
|
||||||
}
|
|
||||||
final Method method = getMatchingAccessibleMethod(object.getClass(),
|
final Method method = getMatchingAccessibleMethod(object.getClass(),
|
||||||
methodName, parameterTypes);
|
methodName, parameterTypes);
|
||||||
if (method == null) {
|
if (method == null) {
|
||||||
|
@ -143,11 +138,11 @@ public class MethodUtils {
|
||||||
* types.</p>
|
* types.</p>
|
||||||
*
|
*
|
||||||
* <p>This uses reflection to invoke the method obtained from a call to
|
* <p>This uses reflection to invoke the method obtained from a call to
|
||||||
* <code>getAccessibleMethod()</code>.</p>
|
* {@link #getAccessibleMethod}(Class,String,Class[])}.</p>
|
||||||
*
|
*
|
||||||
* @param object invoke method on this object
|
* @param object invoke method on this object
|
||||||
* @param methodName get method with this name
|
* @param methodName get method with this name
|
||||||
* @param args use these arguments - treat null as empty array
|
* @param args use these arguments - treat {@code null} as empty array
|
||||||
* @return The value returned by the invoked method
|
* @return The value returned by the invoked method
|
||||||
*
|
*
|
||||||
* @throws NoSuchMethodException if there is no such accessible method
|
* @throws NoSuchMethodException if there is no such accessible method
|
||||||
|
@ -159,9 +154,7 @@ public class MethodUtils {
|
||||||
public static Object invokeExactMethod(final Object object, final String methodName,
|
public static Object invokeExactMethod(final Object object, final String methodName,
|
||||||
Object... args) throws NoSuchMethodException,
|
Object... args) throws NoSuchMethodException,
|
||||||
IllegalAccessException, InvocationTargetException {
|
IllegalAccessException, InvocationTargetException {
|
||||||
if (args == null) {
|
args = ArrayUtils.nullToEmpty(args);
|
||||||
args = ArrayUtils.EMPTY_OBJECT_ARRAY;
|
|
||||||
}
|
|
||||||
final Class<?>[] parameterTypes = ClassUtils.toClass(args);
|
final Class<?>[] parameterTypes = ClassUtils.toClass(args);
|
||||||
return invokeExactMethod(object, methodName, args, parameterTypes);
|
return invokeExactMethod(object, methodName, args, parameterTypes);
|
||||||
}
|
}
|
||||||
|
@ -171,12 +164,12 @@ public class MethodUtils {
|
||||||
* types given.</p>
|
* types given.</p>
|
||||||
*
|
*
|
||||||
* <p>This uses reflection to invoke the method obtained from a call to
|
* <p>This uses reflection to invoke the method obtained from a call to
|
||||||
* <code>getAccessibleMethod()</code>.</p>
|
* {@link #getAccessibleMethod(Class,String,Class[])}.</p>
|
||||||
*
|
*
|
||||||
* @param object invoke method on this object
|
* @param object invoke method on this object
|
||||||
* @param methodName get method with this name
|
* @param methodName get method with this name
|
||||||
* @param args use these arguments - treat null as empty array
|
* @param args use these arguments - treat null as empty array
|
||||||
* @param parameterTypes match these parameters - treat null as empty array
|
* @param parameterTypes match these parameters - treat {@code null} as empty array
|
||||||
* @return The value returned by the invoked method
|
* @return The value returned by the invoked method
|
||||||
*
|
*
|
||||||
* @throws NoSuchMethodException if there is no such accessible method
|
* @throws NoSuchMethodException if there is no such accessible method
|
||||||
|
@ -189,12 +182,8 @@ public class MethodUtils {
|
||||||
Object[] args, Class<?>[] parameterTypes)
|
Object[] args, Class<?>[] parameterTypes)
|
||||||
throws NoSuchMethodException, IllegalAccessException,
|
throws NoSuchMethodException, IllegalAccessException,
|
||||||
InvocationTargetException {
|
InvocationTargetException {
|
||||||
if (args == null) {
|
args = ArrayUtils.nullToEmpty(args);
|
||||||
args = ArrayUtils.EMPTY_OBJECT_ARRAY;
|
parameterTypes = ArrayUtils.nullToEmpty(parameterTypes);
|
||||||
}
|
|
||||||
if (parameterTypes == null) {
|
|
||||||
parameterTypes = ArrayUtils.EMPTY_CLASS_ARRAY;
|
|
||||||
}
|
|
||||||
final Method method = getAccessibleMethod(object.getClass(), methodName,
|
final Method method = getAccessibleMethod(object.getClass(), methodName,
|
||||||
parameterTypes);
|
parameterTypes);
|
||||||
if (method == null) {
|
if (method == null) {
|
||||||
|
@ -206,7 +195,7 @@ public class MethodUtils {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* <p>Invokes a static method whose parameter types match exactly the parameter
|
* <p>Invokes a {@code static} method whose parameter types match exactly the parameter
|
||||||
* types given.</p>
|
* types given.</p>
|
||||||
*
|
*
|
||||||
* <p>This uses reflection to invoke the method obtained from a call to
|
* <p>This uses reflection to invoke the method obtained from a call to
|
||||||
|
@ -214,8 +203,8 @@ public class MethodUtils {
|
||||||
*
|
*
|
||||||
* @param cls invoke static method on this class
|
* @param cls invoke static method on this class
|
||||||
* @param methodName get method with this name
|
* @param methodName get method with this name
|
||||||
* @param args use these arguments - treat null as empty array
|
* @param args use these arguments - treat {@code null} as empty array
|
||||||
* @param parameterTypes match these parameters - treat null as empty array
|
* @param parameterTypes match these parameters - treat {@code null as empty array
|
||||||
* @return The value returned by the invoked method
|
* @return The value returned by the invoked method
|
||||||
*
|
*
|
||||||
* @throws NoSuchMethodException if there is no such accessible method
|
* @throws NoSuchMethodException if there is no such accessible method
|
||||||
|
@ -228,12 +217,8 @@ public class MethodUtils {
|
||||||
Object[] args, Class<?>[] parameterTypes)
|
Object[] args, Class<?>[] parameterTypes)
|
||||||
throws NoSuchMethodException, IllegalAccessException,
|
throws NoSuchMethodException, IllegalAccessException,
|
||||||
InvocationTargetException {
|
InvocationTargetException {
|
||||||
if (args == null) {
|
args = ArrayUtils.nullToEmpty(args);
|
||||||
args = ArrayUtils.EMPTY_OBJECT_ARRAY;
|
parameterTypes = ArrayUtils.nullToEmpty(parameterTypes);
|
||||||
}
|
|
||||||
if (parameterTypes == null) {
|
|
||||||
parameterTypes = ArrayUtils.EMPTY_CLASS_ARRAY;
|
|
||||||
}
|
|
||||||
final Method method = getAccessibleMethod(cls, methodName, parameterTypes);
|
final Method method = getAccessibleMethod(cls, methodName, parameterTypes);
|
||||||
if (method == null) {
|
if (method == null) {
|
||||||
throw new NoSuchMethodException("No such accessible method: "
|
throw new NoSuchMethodException("No such accessible method: "
|
||||||
|
@ -243,13 +228,13 @@ public class MethodUtils {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* <p>Invokes a named static method whose parameter type matches the object type.</p>
|
* <p>Invokes a named {@code static} method whose parameter type matches the object type.</p>
|
||||||
*
|
*
|
||||||
* <p>This method delegates the method search to {@link #getMatchingAccessibleMethod(Class, String, Class[])}.</p>
|
* <p>This method delegates the method search to {@link #getMatchingAccessibleMethod(Class, String, Class[])}.</p>
|
||||||
*
|
*
|
||||||
* <p>This method supports calls to methods taking primitive parameters
|
* <p>This method supports calls to methods taking primitive parameters
|
||||||
* via passing in wrapping classes. So, for example, a <code>Boolean</code> class
|
* via passing in wrapping classes. So, for example, a {@code Boolean} class
|
||||||
* would match a <code>boolean</code> primitive.</p>
|
* would match a {@code boolean} primitive.</p>
|
||||||
*
|
*
|
||||||
* <p>This is a convenient wrapper for
|
* <p>This is a convenient wrapper for
|
||||||
* {@link #invokeStaticMethod(Class objectClass,String methodName,Object [] args,Class[] parameterTypes)}.
|
* {@link #invokeStaticMethod(Class objectClass,String methodName,Object [] args,Class[] parameterTypes)}.
|
||||||
|
@ -257,7 +242,7 @@ public class MethodUtils {
|
||||||
*
|
*
|
||||||
* @param cls invoke static method on this class
|
* @param cls invoke static method on this class
|
||||||
* @param methodName get method with this name
|
* @param methodName get method with this name
|
||||||
* @param args use these arguments - treat null as empty array
|
* @param args use these arguments - treat {@code null} as empty array
|
||||||
* @return The value returned by the invoked method
|
* @return The value returned by the invoked method
|
||||||
*
|
*
|
||||||
* @throws NoSuchMethodException if there is no such accessible method
|
* @throws NoSuchMethodException if there is no such accessible method
|
||||||
|
@ -269,27 +254,25 @@ public class MethodUtils {
|
||||||
public static Object invokeStaticMethod(final Class<?> cls, final String methodName,
|
public static Object invokeStaticMethod(final Class<?> cls, final String methodName,
|
||||||
Object... args) throws NoSuchMethodException,
|
Object... args) throws NoSuchMethodException,
|
||||||
IllegalAccessException, InvocationTargetException {
|
IllegalAccessException, InvocationTargetException {
|
||||||
if (args == null) {
|
args = ArrayUtils.nullToEmpty(args);
|
||||||
args = ArrayUtils.EMPTY_OBJECT_ARRAY;
|
|
||||||
}
|
|
||||||
final Class<?>[] parameterTypes = ClassUtils.toClass(args);
|
final Class<?>[] parameterTypes = ClassUtils.toClass(args);
|
||||||
return invokeStaticMethod(cls, methodName, args, parameterTypes);
|
return invokeStaticMethod(cls, methodName, args, parameterTypes);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* <p>Invokes a named static method whose parameter type matches the object type.</p>
|
* <p>Invokes a named {@code static} method whose parameter type matches the object type.</p>
|
||||||
*
|
*
|
||||||
* <p>This method delegates the method search to {@link #getMatchingAccessibleMethod(Class, String, Class[])}.</p>
|
* <p>This method delegates the method search to {@link #getMatchingAccessibleMethod(Class, String, Class[])}.</p>
|
||||||
*
|
*
|
||||||
* <p>This method supports calls to methods taking primitive parameters
|
* <p>This method supports calls to methods taking primitive parameters
|
||||||
* via passing in wrapping classes. So, for example, a <code>Boolean</code> class
|
* via passing in wrapping classes. So, for example, a {@code Boolean} class
|
||||||
* would match a <code>boolean</code> primitive.</p>
|
* would match a {@code boolean} primitive.</p>
|
||||||
*
|
*
|
||||||
*
|
*
|
||||||
* @param cls invoke static method on this class
|
* @param cls invoke static method on this class
|
||||||
* @param methodName get method with this name
|
* @param methodName get method with this name
|
||||||
* @param args use these arguments - treat null as empty array
|
* @param args use these arguments - treat {@code null} as empty array
|
||||||
* @param parameterTypes match these parameters - treat null as empty array
|
* @param parameterTypes match these parameters - treat {@code null} as empty array
|
||||||
* @return The value returned by the invoked method
|
* @return The value returned by the invoked method
|
||||||
*
|
*
|
||||||
* @throws NoSuchMethodException if there is no such accessible method
|
* @throws NoSuchMethodException if there is no such accessible method
|
||||||
|
@ -302,12 +285,8 @@ public class MethodUtils {
|
||||||
Object[] args, Class<?>[] parameterTypes)
|
Object[] args, Class<?>[] parameterTypes)
|
||||||
throws NoSuchMethodException, IllegalAccessException,
|
throws NoSuchMethodException, IllegalAccessException,
|
||||||
InvocationTargetException {
|
InvocationTargetException {
|
||||||
if (parameterTypes == null) {
|
args = ArrayUtils.nullToEmpty(args);
|
||||||
parameterTypes = ArrayUtils.EMPTY_CLASS_ARRAY;
|
parameterTypes = ArrayUtils.nullToEmpty(parameterTypes);
|
||||||
}
|
|
||||||
if (args == null) {
|
|
||||||
args = ArrayUtils.EMPTY_OBJECT_ARRAY;
|
|
||||||
}
|
|
||||||
final Method method = getMatchingAccessibleMethod(cls, methodName,
|
final Method method = getMatchingAccessibleMethod(cls, methodName,
|
||||||
parameterTypes);
|
parameterTypes);
|
||||||
if (method == null) {
|
if (method == null) {
|
||||||
|
@ -318,7 +297,7 @@ public class MethodUtils {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* <p>Invokes a static method whose parameter types match exactly the object
|
* <p>Invokes a {@code static} method whose parameter types match exactly the object
|
||||||
* types.</p>
|
* types.</p>
|
||||||
*
|
*
|
||||||
* <p>This uses reflection to invoke the method obtained from a call to
|
* <p>This uses reflection to invoke the method obtained from a call to
|
||||||
|
@ -326,7 +305,7 @@ public class MethodUtils {
|
||||||
*
|
*
|
||||||
* @param cls invoke static method on this class
|
* @param cls invoke static method on this class
|
||||||
* @param methodName get method with this name
|
* @param methodName get method with this name
|
||||||
* @param args use these arguments - treat null as empty array
|
* @param args use these arguments - treat {@code null} as empty array
|
||||||
* @return The value returned by the invoked method
|
* @return The value returned by the invoked method
|
||||||
*
|
*
|
||||||
* @throws NoSuchMethodException if there is no such accessible method
|
* @throws NoSuchMethodException if there is no such accessible method
|
||||||
|
@ -338,9 +317,7 @@ public class MethodUtils {
|
||||||
public static Object invokeExactStaticMethod(final Class<?> cls, final String methodName,
|
public static Object invokeExactStaticMethod(final Class<?> cls, final String methodName,
|
||||||
Object... args) throws NoSuchMethodException,
|
Object... args) throws NoSuchMethodException,
|
||||||
IllegalAccessException, InvocationTargetException {
|
IllegalAccessException, InvocationTargetException {
|
||||||
if (args == null) {
|
args = ArrayUtils.nullToEmpty(args);
|
||||||
args = ArrayUtils.EMPTY_OBJECT_ARRAY;
|
|
||||||
}
|
|
||||||
final Class<?>[] parameterTypes = ClassUtils.toClass(args);
|
final Class<?>[] parameterTypes = ClassUtils.toClass(args);
|
||||||
return invokeExactStaticMethod(cls, methodName, args, parameterTypes);
|
return invokeExactStaticMethod(cls, methodName, args, parameterTypes);
|
||||||
}
|
}
|
||||||
|
@ -348,9 +325,9 @@ public class MethodUtils {
|
||||||
/**
|
/**
|
||||||
* <p>Returns an accessible method (that is, one that can be invoked via
|
* <p>Returns an accessible method (that is, one that can be invoked via
|
||||||
* reflection) with given name and parameters. If no such method
|
* reflection) with given name and parameters. If no such method
|
||||||
* can be found, return <code>null</code>.
|
* can be found, return {@code null}.
|
||||||
* This is just a convenient wrapper for
|
* This is just a convenience wrapper for
|
||||||
* {@link #getAccessibleMethod(Method method)}.</p>
|
* {@link #getAccessibleMethod(Method)}.</p>
|
||||||
*
|
*
|
||||||
* @param cls get method from this class
|
* @param cls get method from this class
|
||||||
* @param methodName get method with this name
|
* @param methodName get method with this name
|
||||||
|
@ -370,7 +347,7 @@ public class MethodUtils {
|
||||||
/**
|
/**
|
||||||
* <p>Returns an accessible method (that is, one that can be invoked via
|
* <p>Returns an accessible method (that is, one that can be invoked via
|
||||||
* reflection) that implements the specified Method. If no such method
|
* reflection) that implements the specified Method. If no such method
|
||||||
* can be found, return <code>null</code>.</p>
|
* can be found, return {@code null}.</p>
|
||||||
*
|
*
|
||||||
* @param method The method that we wish to call
|
* @param method The method that we wish to call
|
||||||
* @return The accessible method
|
* @return The accessible method
|
||||||
|
@ -402,12 +379,12 @@ public class MethodUtils {
|
||||||
/**
|
/**
|
||||||
* <p>Returns an accessible method (that is, one that can be invoked via
|
* <p>Returns an accessible method (that is, one that can be invoked via
|
||||||
* reflection) by scanning through the superclasses. If no such method
|
* reflection) by scanning through the superclasses. If no such method
|
||||||
* can be found, return <code>null</code>.</p>
|
* can be found, return {@code null}.</p>
|
||||||
*
|
*
|
||||||
* @param cls Class to be checked
|
* @param cls Class to be checked
|
||||||
* @param methodName Method name of the method we wish to call
|
* @param methodName Method name of the method we wish to call
|
||||||
* @param parameterTypes The parameter type signatures
|
* @param parameterTypes The parameter type signatures
|
||||||
* @return the accessible method or <code>null</code> if not found
|
* @return the accessible method or {@code null} if not found
|
||||||
*/
|
*/
|
||||||
private static Method getAccessibleMethodFromSuperclass(final Class<?> cls,
|
private static Method getAccessibleMethodFromSuperclass(final Class<?> cls,
|
||||||
final String methodName, final Class<?>... parameterTypes) {
|
final String methodName, final Class<?>... parameterTypes) {
|
||||||
|
@ -429,21 +406,19 @@ public class MethodUtils {
|
||||||
* <p>Returns an accessible method (that is, one that can be invoked via
|
* <p>Returns an accessible method (that is, one that can be invoked via
|
||||||
* reflection) that implements the specified method, by scanning through
|
* reflection) that implements the specified method, by scanning through
|
||||||
* all implemented interfaces and subinterfaces. If no such method
|
* all implemented interfaces and subinterfaces. If no such method
|
||||||
* can be found, return <code>null</code>.</p>
|
* can be found, return {@code null}.</p>
|
||||||
*
|
*
|
||||||
* <p>There isn't any good reason why this method must be private.
|
* <p>There isn't any good reason why this method must be {@code private}.
|
||||||
* It is because there doesn't seem any reason why other classes should
|
* It is because there doesn't seem any reason why other classes should
|
||||||
* call this rather than the higher level methods.</p>
|
* call this rather than the higher level methods.</p>
|
||||||
*
|
*
|
||||||
* @param cls Parent class for the interfaces to be checked
|
* @param cls Parent class for the interfaces to be checked
|
||||||
* @param methodName Method name of the method we wish to call
|
* @param methodName Method name of the method we wish to call
|
||||||
* @param parameterTypes The parameter type signatures
|
* @param parameterTypes The parameter type signatures
|
||||||
* @return the accessible method or <code>null</code> if not found
|
* @return the accessible method or {@code null} if not found
|
||||||
*/
|
*/
|
||||||
private static Method getAccessibleMethodFromInterfaceNest(Class<?> cls,
|
private static Method getAccessibleMethodFromInterfaceNest(Class<?> cls,
|
||||||
final String methodName, final Class<?>... parameterTypes) {
|
final String methodName, final Class<?>... parameterTypes) {
|
||||||
Method method = null;
|
|
||||||
|
|
||||||
// Search up the superclass chain
|
// Search up the superclass chain
|
||||||
for (; cls != null; cls = cls.getSuperclass()) {
|
for (; cls != null; cls = cls.getSuperclass()) {
|
||||||
|
|
||||||
|
@ -456,7 +431,7 @@ public class MethodUtils {
|
||||||
}
|
}
|
||||||
// Does the method exist on this interface?
|
// Does the method exist on this interface?
|
||||||
try {
|
try {
|
||||||
method = interfaces[i].getDeclaredMethod(methodName,
|
return interfaces[i].getDeclaredMethod(methodName,
|
||||||
parameterTypes);
|
parameterTypes);
|
||||||
} catch (final NoSuchMethodException e) { // NOPMD
|
} catch (final NoSuchMethodException e) { // NOPMD
|
||||||
/*
|
/*
|
||||||
|
@ -464,19 +439,16 @@ public class MethodUtils {
|
||||||
* method returns null.
|
* method returns null.
|
||||||
*/
|
*/
|
||||||
}
|
}
|
||||||
if (method != null) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
// Recursively check our parent interfaces
|
// Recursively check our parent interfaces
|
||||||
method = getAccessibleMethodFromInterfaceNest(interfaces[i],
|
Method method = getAccessibleMethodFromInterfaceNest(interfaces[i],
|
||||||
methodName, parameterTypes);
|
methodName, parameterTypes);
|
||||||
if (method != null) {
|
if (method != null) {
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return method;
|
return method;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* <p>Finds an accessible method that matches the given name and has compatible parameters.
|
* <p>Finds an accessible method that matches the given name and has compatible parameters.
|
||||||
|
@ -490,7 +462,7 @@ public class MethodUtils {
|
||||||
* #invokeMethod(Object object, String methodName, Object[] args, Class[] parameterTypes)}.
|
* #invokeMethod(Object object, String methodName, Object[] args, Class[] parameterTypes)}.
|
||||||
*
|
*
|
||||||
* <p>This method can match primitive parameter by passing in wrapper classes.
|
* <p>This method can match primitive parameter by passing in wrapper classes.
|
||||||
* For example, a <code>Boolean</code> will match a primitive <code>boolean</code>
|
* For example, a {@code Boolean} will match a primitive {@code boolean}
|
||||||
* parameter.
|
* parameter.
|
||||||
*
|
*
|
||||||
* @param cls find method in this class
|
* @param cls find method in this class
|
||||||
|
@ -531,8 +503,10 @@ public class MethodUtils {
|
||||||
/**
|
/**
|
||||||
* Get the hierarchy of overridden methods down to {@code result} respecting generics.
|
* Get the hierarchy of overridden methods down to {@code result} respecting generics.
|
||||||
* @param method lowest to consider
|
* @param method lowest to consider
|
||||||
* @param interfacesBehavior whether to search interfaces
|
* @param interfacesBehavior whether to search interfaces, {@code null} {@code implies} false
|
||||||
* @return Collection<Method> in ascending order from sub- to superclass
|
* @return Set<Method> in ascending order from sub- to superclass
|
||||||
|
* @throws NullPointerException if the specified method is {@code null}
|
||||||
|
* @since 3.2
|
||||||
*/
|
*/
|
||||||
public static Set<Method> getOverrideHierarchy(final Method method, Interfaces interfacesBehavior) {
|
public static Set<Method> getOverrideHierarchy(final Method method, Interfaces interfacesBehavior) {
|
||||||
Validate.notNull(method);
|
Validate.notNull(method);
|
||||||
|
@ -568,7 +542,6 @@ public class MethodUtils {
|
||||||
}
|
}
|
||||||
result.add(m);
|
result.add(m);
|
||||||
}
|
}
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue