Class KiwiReflection

java.lang.Object
org.kiwiproject.reflect.KiwiReflection

public final class KiwiReflection extends Object
Some utilities related to reflection. Please read the WARNING below.

Many of the methods are simply wrappers around JDK methods in Class, Field, and Method; they catch the various exceptions that can be thrown by the JDK methods and wrap them with a single RuntimeReflectionException.

WARNING: Note that some of the methods bypass the Java accessibility mechanism and/or change the visibility of a method or field. This makes Sonar very unhappy. See Sonar rule java:S3011 for more details, as well as rule SEC05-J from the SEI CERT Oracle Secure Coding Standard.

With the above warning in mind, there are good reasons to bypass Java's protections in some situations. And since this is a class specifically intended to be used in such situations, we intentionally suppress Sonar's warnings and assume you have good reasons to violate those rules.

  • Method Details

    • findField

      public static Field findField(Object target, String fieldName)
      Find a field by name in the specified target object, whether it is public or not.

      Note specifically that if the field is not public, this method uses Field.setAccessible(boolean) to make it accessible and thus is subject to a SecurityException or InaccessibleObjectException.

      Parameters:
      target - the target object
      fieldName - the field name to find
      Returns:
      the Field object
      Throws:
      RuntimeReflectionException - if any error occurs finding the field
      See Also:
    • getTypedFieldValue

      public static <T> T getTypedFieldValue(Object target, String fieldName, Class<T> type)
      Get the value of a specific field in an object, cast to the specified type.
      Type Parameters:
      T - the type parameter
      Parameters:
      target - the target object
      fieldName - the field name
      type - the type of object to return
      Returns:
      the field value
      Throws:
      RuntimeReflectionException - if any error occurs getting the field value (excluding type cast errors)
      ClassCastException - if the given return type is not correct
    • getFieldValue

      public static Object getFieldValue(Object target, String fieldName)
      Get the value of a specific field in an object.

      Note that if the field is not public, this method uses Field.setAccessible(boolean) to make it accessible and thus is subject to a SecurityException or InaccessibleObjectException.

      Parameters:
      target - the target object
      fieldName - the field name
      Returns:
      the field value
      Throws:
      RuntimeReflectionException - if any error occurs finding the field or getting its value
    • getTypedFieldValue

      public static <T> T getTypedFieldValue(Object target, Field field, Class<T> type)
      Get the value of a specific field in an object, cast to the specified type.
      Type Parameters:
      T - the type parameter
      Parameters:
      target - the target object
      field - the field object
      type - the type of object to return
      Returns:
      the field value
      Throws:
      RuntimeReflectionException - if any error occurs getting the field value (excluding type cast errors)
      ClassCastException - if the given return type is not correct
    • getFieldValue

      public static Object getFieldValue(Object target, Field field)
      Get the value of a specific field in an object.
      Parameters:
      target - the target object
      field - the field object
      Returns:
      the field value
      Throws:
      RuntimeReflectionException - if any error occurs getting the field
    • setFieldValue

      public static void setFieldValue(Object target, String fieldName, Object value)
      Sets a value directly into the specified field in the target object.

      Subject to the restrictions of and exceptions thrown by Field.set(Object, Object).

      Note that if the field is not public, this method uses Field.setAccessible(boolean) to make it accessible and thus is subject to a SecurityException or InaccessibleObjectException.

      Parameters:
      target - the target object in which the field resides
      fieldName - the field name
      value - the new value
      Throws:
      RuntimeReflectionException - if any error occurs setting the field value
      See Also:
    • setFieldValue

      public static void setFieldValue(Object target, Field field, Object value)
      Sets a value directly into the specified field in the target object.

      Subject to the restrictions of and exceptions thrown by Field.set(Object, Object).

      Parameters:
      target - the target object in which the field resides
      field - the field to set
      value - the new value
      Throws:
      RuntimeReflectionException - if any error occurs setting the field value
      See Also:
    • nonStaticFieldsInHierarchy

      public static List<Field> nonStaticFieldsInHierarchy(Class<?> type)
      Builds a list of all the declared non-static fields in an object including all parent non-static fields.
      Parameters:
      type - the class to extract fields from
      Returns:
      the list of fields in the given class plus fields from all ancestor (parent) classes
      See Also:
    • findPublicAccessorMethods

      public static List<Method> findPublicAccessorMethods(Object target)
      Finds all public accessor methods (getXxx / isXxx conforming to JavaBeans rules) in the class of the given object (including superclasses).
      Parameters:
      target - the target object
      Returns:
      list of public "getter" methods
      See Also:
    • findPublicAccessorMethods

      public static List<Method> findPublicAccessorMethods(Class<?> clazz)
      Finds all public accessor methods (getXxx / isXxx conforming to JavaBeans rules) in the given class (including superclasses).
      Parameters:
      clazz - the target class
      Returns:
      list of public "getter" methods
      See Also:
    • isPublicAccessorMethod

      public static boolean isPublicAccessorMethod(Method method)
      Checks whether the given method is a public accessor method (getXxx / isXxx conforming to JavaBeans rules).
      Parameters:
      method - the method to check
      Returns:
      true if method is a public accessor, false otherwise
    • isStrictlyGetAccessorMethod

      public static boolean isStrictlyGetAccessorMethod(Method method)
      Checks whether the given method is a public accessor method (only getXxx conforming to JavaBeans rules).

      Note this explicitly excludes the Object.getClass() method.

      Parameters:
      method - the method to check
      Returns:
      true if the method is a public "getXxx" method, false otherwise
    • isStrictlyIsAccessorMethod

      public static boolean isStrictlyIsAccessorMethod(Method method)
      Checks whether the given method is a public accessor method (only isXxx conforming to JavaBeans rules).
      Parameters:
      method - the method to check
      Returns:
      true if the method is a public "isXxx" method, false otherwise
    • findPublicMutatorMethods

      public static List<Method> findPublicMutatorMethods(Object target)
      Finds all public mutator methods (setXxx conforming to JavaBeans rules) in the class of the given object (including superclasses).
      Parameters:
      target - the target object
      Returns:
      list of public "setter" methods
      See Also:
    • findPublicMutatorMethods

      public static List<Method> findPublicMutatorMethods(Class<?> clazz)
      Finds all public mutator methods (setXxx conforming to JavaBeans rules) in the given class (including superclasses).
      Parameters:
      clazz - the target class
      Returns:
      list of public "setter" methods
      See Also:
    • findPublicMethods

      public static List<Method> findPublicMethods(Class<?> clazz, Predicate<Method> predicate)
      Finds all public methods in the given class (including superclasses) that satisfy the given Predicate.
      Parameters:
      clazz - the target class
      predicate - the predicate to satisfy
      Returns:
      a list of methods
      See Also:
    • isPublicMutatorMethod

      public static boolean isPublicMutatorMethod(Method method)
      Checks whether the given method is a public mutator method (setXxx conforming to JavaBeans rules).
      Parameters:
      method - the method to check
      Returns:
      true if the method is a public "setXxx" method, false otherwise
    • invokeMutatorMethodsWithNull

      public static void invokeMutatorMethodsWithNull(Object target)
      Finds public mutator methods for the given object, then for reference types invokes the mutator supplying null as the argument.

      The effect is thus to nullify the values of (mutable) properties in target having a reference (non-primitive) type.

      Parameters:
      target - the object containing mutable properties exposed via public mutator methods
      See Also:
    • invokeMutatorMethodsWithNullIgnoringProperties

      public static void invokeMutatorMethodsWithNullIgnoringProperties(Object target, String... properties)
      Finds public mutator methods for the given object, then for reference types invokes the mutator supplying null as the argument except for property names contained in properties.

      The properties vararg specifies the names of the properties to ignore. These names will be translated into the corresponding "setter" method name. For example, if "dateOfBirth" is the property name to ignore, then the "setDateOfBirth" method is the corresponding setter method, and it will be ignored (not called).

      The effect is thus to nullify the values of (mutable) properties in target having a reference (non-primitive) type, excluding the ones specified in properties.

      Parameters:
      target - the object containing mutable properties exposed via public mutator methods
      properties - the property names to ignore, e.g. "firstName", "age", "zipCode"
      See Also:
    • invokeMutatorMethodsWithNullIncludingOnlyProperties

      public static void invokeMutatorMethodsWithNullIncludingOnlyProperties(Object target, String... properties)
      Finds public mutator methods for the given object, then for reference types invokes the mutator supplying null as the argument including only the property names contained in properties.

      The properties vararg specifies the names of the properties to include. These names will be translated into the corresponding "setter" method name. For example, if "dateOfBirth" is the property name to include, then the "setDateOfBirth" method is the corresponding setter method, and it will be called with a null argument.

      The effect is thus to nullify the values of (mutable) properties in target having a reference (non-primitive) type, including only the ones specified in properties.

      Parameters:
      target - the object containing mutable properties exposed via public mutator methods
      properties - the property names to include, e.g. "firstName", "age", "zipCode"
      See Also:
    • invokeMutatorMethodsWithNullSatisfying

      public static void invokeMutatorMethodsWithNullSatisfying(Object target, Predicate<Method> methodPredicate)
      Finds public mutator methods for the given object, then for reference types invokes the mutator supplying null as the argument including only methods that satisfy the given Predicate.

      When methodPredicate returns true, the mutator method is called with a null argument. When it returns false then the method is not called.

      The effect is thus to nullify the values of (mutable) properties in target having a reference (non-primitive) type, including only the ones for which methodPredicate returns true.

      Parameters:
      target - the object containing mutable properties exposed via public mutator methods
      methodPredicate - a Predicate that tests whether to include a mutator method
    • findMethodOptionally

      public static Optional<Method> findMethodOptionally(Class<?> targetClass, String methodName, Class<?>... params)
      Finds a public method having the given name and parameter types in the given class.
      Parameters:
      targetClass - the class in which to look for the method
      methodName - the name of the method to find
      params - the parameter types of the method's argument list, if any
      Returns:
      an Optional that will contain the Method if found. Otherwise, returns an empty Optional in all other circumstances.
      See Also:
    • findAccessor

      public static Method findAccessor(KiwiReflection.Accessor methodType, String fieldName, Object target, Class<?>... params)
      Finds an accessor method of the given methodType for the specified fieldName in target.
      Parameters:
      methodType - the type of method to find
      fieldName - the field name
      target - the target object
      params - the method parameters
      Returns:
      the found Method
      Throws:
      RuntimeReflectionException - if any error occurs finding the accessor method
    • findAccessor

      public static Method findAccessor(KiwiReflection.Accessor methodType, String fieldName, Class<?> targetClass, Class<?>... params)
      Finds a public accessor method of the given methodType for the specified fieldName in the given targetClass. For example, given "firstName" as the field name and KiwiReflection.Accessor.SET as the method type, will attempt to find a public setFirstName

      Handles primitive boolean vs. reference Boolean distinction transparently even if KiwiReflection.Accessor.GET is passed as the method type for a primitive. In other words, this method will return the boolean isXxx() method if provided KiwiReflection.Accessor.GET but the actual return type is primitive.

      Allows for having a naming convention of instance variables starting with an underscore, e.g. String _firstName, by stripping underscores from the field name. The fieldName argument can be supplied with or without a leading underscore. Note, however, that since this method removes all underscores from the fieldName, oddly named fields may produce exceptions.

      Parameters:
      methodType - the type of method to find
      fieldName - the field name
      targetClass - the class in which the field resides
      params - the method parameters (should be none for getters, and one for setters)
      Returns:
      the found Method
      Throws:
      RuntimeReflectionException - if any error occurs finding the accessor method
    • findMethod

      public static Method findMethod(Class<?> targetClass, String methodName, Class<?>... params)
      Finds a public method having the given name and parameter types in the given class.

      Use this when you expect the method to exist. If you are not sure, then use findMethodOptionally(Class, String, Class[]).

      Parameters:
      targetClass - the class in which to look for the method
      methodName - the name of the method to find
      params - the parameter types of the method's argument list, if any
      Returns:
      the found Method object
      Throws:
      RuntimeReflectionException - if any error occurs finding the method
      See Also:
    • invokeExpectingReturn

      public static <T> T invokeExpectingReturn(Method method, Object target, Class<T> returnType, Object... args)
      Invokes a method on an object expecting a return value of a specific type.
      Type Parameters:
      T - the return type parameter
      Parameters:
      method - the method to invoke
      target - the object on which to invoke the method
      returnType - the expected return type
      args - optionally, the method arguments
      Returns:
      result of calling the method (which could be null), cast to type T
      Throws:
      RuntimeReflectionException - if any error occurs invoking the method (excluding type cast errors)
      ClassCastException - if the given return type is not correct
    • invokeExpectingReturn

      public static Object invokeExpectingReturn(Method method, Object target, Object... args)
      Invokes a method on an object expecting a return value.
      Parameters:
      method - the method to invoke
      target - the object on which to invoke the method
      args - optionally, the method arguments
      Returns:
      result of calling the method (which could be null)
      Throws:
      RuntimeReflectionException - if any error occurs invoking the method
      See Also:
    • invokeVoidReturn

      public static void invokeVoidReturn(Method method, Object target, Object... args)
      Invokes a method on an object expecting no return value.
      Parameters:
      method - the method to invoke
      target - the object on which to invoke the method
      args - optionally, the method arguments
      Throws:
      RuntimeReflectionException - if any error occurs invoking the method
      See Also:
    • newInstanceUsingNoArgsConstructor

      @Beta public static <T> T newInstanceUsingNoArgsConstructor(Class<T> type)
      Convenience method to create a new instance of the given type using its no-args constructor.
      Type Parameters:
      T - the type of object
      Parameters:
      type - the Class representing the object type
      Returns:
      a new instance
      Throws:
      RuntimeReflectionException - if any error occurs invoking the constructor
      IllegalArgumentException - if a no-args constructor does not exist, is private, etc.
      See Also:
    • newInstanceInferringParamTypes

      @Beta public static <T> T newInstanceInferringParamTypes(Class<T> type, Object... arguments)
      Create a new instance of the given type using arguments to determine the constructor argument types, using the first matching constructor based on the argument types and actual constructor parameters. A constructor will match if the constructor parameter type is assignable from the argument type. For example if a one-argument constructor accepts a CharSequence and the actual argument type is String, the constructor matches since String is assignable to CharSequence.

      Note that this method cannot be used if any of the arguments are null. The reason is that the type cannot be inferred. If any argument might be null, or you don't know or aren't sure, use newInstance(Class, List, List) instead.

      Type Parameters:
      T - the type of object
      Parameters:
      type - the Class representing the object type
      arguments - the constructor arguments
      Returns:
      a new instance
      Throws:
      IllegalArgumentException - if no matching constructor was found for the given arguments
      NullPointerException - if any of the arguments is null
      RuntimeReflectionException - if any error occurs invoking the constructor
      See Also:
    • newInstanceExactParamTypes

      @Beta public static <T> T newInstanceExactParamTypes(Class<T> type, List<Class<?>> parameterTypes, Object... arguments)
      This method is an alias for newInstance(Class, List, List), with the arguments as varargs, which may be more convenient in some situations. See that method's javadoc for more details, including the types of exceptions that can be thrown.
      Type Parameters:
      T - the type of object
      Parameters:
      type - the Class representing the object type
      parameterTypes - the constructor parameter types
      arguments - the constructor arguments; individual arguments may be null (but note that a single literal null argument is ambiguous, and must be cast to make the intent clear to the compiler)
      Returns:
      a new instance
      See Also:
      API Note:
      This method is named differently than newInstance(Class, List, List) to avoid amiguity that happens with method overloads when one (or more) uses varargs and the others don't.
    • newInstance

      public static <T> T newInstance(Class<T> type, List<Class<?>> parameterTypes, List<Object> arguments)
      Create a new instance of the given type using a constructor having the given parameter types, and supplying the arguments to that constructor.

      Note that the parameter types must match exactly.

      Type Parameters:
      T - the type of object
      Parameters:
      type - the Class representing the object type
      parameterTypes - the constructor parameter types
      arguments - the constructor arguments; individual arguments may be null
      Returns:
      a new instance
      Throws:
      IllegalArgumentException - if any of the arguments is null, if the length of parameter types and arguments is different, or if no constructor exists with the given parameter types
      RuntimeReflectionException - if any error occurs invoking the constructor
      See Also: