public static Method getMethod ( Class < ? > type , String name , Class < ? > returnType , Class < ? > paramType , boolean caseSensitive ) throws IllegalAccessException , NoSuchMethodException { // flag to help modify the exception to make it a little easier for debugging boolean methodNameFound = false ; // start our search Class < ? > classType = type ; while ( classType != null && ! classType . equals ( Object . class ) ) { for ( Method m : classType . getDeclaredMethods ( ) ) { if ( ( ! caseSensitive && m . getName ( ) . equalsIgnoreCase ( name ) ) || ( caseSensitive && m . getName ( ) . equals ( name ) ) ) { // we found the method name, but its possible the signature won't // match below, we'll set this flag to help construct a better exception // below methodNameFound = true ; // should we validate the return type? if ( returnType != null ) { // if the return types don't match, then this must be invalid // since the JVM doesn't allow the same return type if ( ! m . getReturnType ( ) . equals ( returnType ) ) { throw new NoSuchMethodException ( "Method '" + name + "' was found in " + type . getSimpleName ( ) + ".class" + ", but the returnType " + m . getReturnType ( ) . getSimpleName ( ) + ".class did not match expected " + returnType . getSimpleName ( ) + ".class" ) ; } // make sure the return type is VOID } else { if ( ! m . getReturnType ( ) . equals ( void . class ) ) { throw new NoSuchMethodException ( "Method '" + name + "' was found in " + type . getSimpleName ( ) + ".class" + ", but the returnType " + m . getReturnType ( ) . getSimpleName ( ) + ".class was expected to be void" ) ; } } // return type was okay, check the parameters Class < ? > [ ] paramTypes = m . getParameterTypes ( ) ; // should we check the parameter type? if ( paramType != null ) { // must have exactly 1 parameter if ( paramTypes . length != 1 ) { // this might not be the method we want, keep searching continue ; } else { // if the parameters don't match, keep searching if ( ! paramTypes [ 0 ] . equals ( paramType ) ) { continue ; } } // if paramType was null, then make sure no parameters are expected } else { if ( paramTypes . length != 0 ) { continue ; } } // if we got here, then everything matches so far // now its time to check if the method is accessible if ( ! Modifier . isPublic ( m . getModifiers ( ) ) ) { throw new IllegalAccessException ( "Method '" + name + "' was found in " + type . getSimpleName ( ) + ".class " + ", but its not accessible since its " + Modifier . toString ( m . getModifiers ( ) ) ) ; } // everything was okay return m ; } } // move onto the superclass classType = classType . getSuperclass ( ) ; } String signature = "public " + ( returnType == null ? "void" : returnType . getName ( ) ) + " " + name + "(" + ( paramType == null ? "" : paramType . getName ( ) ) + ")" ; if ( methodNameFound ) { throw new NoSuchMethodException ( "Method '" + signature + "' was found in " + type . getSimpleName ( ) + ".class, but signature match failed" ) ; } else { throw new NoSuchMethodException ( "Method '" + signature + "' was not found in " + type . getSimpleName ( ) + ".class" ) ; } }
Gets the public method within the type that matches the method name return type and single parameter type . Optionally is a case sensitive search . Useful for searching for bean methods on classes .