Supposedly this is not a new problem however I am having trouble finding the solution, because most answers to this refer to the method in question not being public.
There is a package named reflection
, where annotations as well as a UITester
class are defined, the latter uses a class-annotation and a method-annotation. A different package named gui
contains a class MinimalUI
which then tests access to UITester
, its methods and the respective annotation values. However I am running into a NoSuchMethodException
.
FunctionAnnotation
The annotation is used to lock/unlock methods.
package reflection;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
import java.lang.annotation.ElementType;
@Retention( RetentionPolicy.RUNTIME )
@Target( {ElementType.METHOD} )
public @interface FunctionAnnotation
{
boolean locked();
}
SampleAnnotation
Simple annotation to set some basic class properties.
package reflection;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
@Retention( RetentionPolicy.RUNTIME )
public
@interface SampleAnnotation
{
String name();
String value();
boolean output();
}
UITester
This is the annotated class. The class declaration itself is annotated and so is one method of the class, so both annotations previously shown are used.
package reflection;
@SampleAnnotation( name = "default", value = "[MINIMAL UI ANNOTATION] Testing.", output = true )
public class UITester
{
public UITester()
{
System.out.println( "[UI TESTER] Created." );
}
public void print( String value )
{
System.out.println( "[UI TESTER] Printing: " + value );
}
@FunctionAnnotation( locked = false )
public void printIfAvailable( String value )
{
System.out.println( "[UI TESTER] Printing (available): " + value );
}
}
MinimalUI
Finally there is a minimal UI class that implements the Gui
interface, declared in the same package. I am posting just the relevant test method, because otherwise this sample will become a bit large. The following code is method MinimalUI#testUI
. It needs to read the annotations set for UITester
and behave in accordance with the results. The implementation is minimalistic and lacks safeguards, which is fine, because this is a sandbox project where I am testing patterns to be transferred to production. The code:
@Override
public void testUI()
{
UITester tester = new UITester();
Annotation annotation = UITester.class.getAnnotation( SampleAnnotation.class );
if ( annotation instanceof SampleAnnotation )
{
String value = ( (SampleAnnotation) annotation ).value();
tester.print( value );
try
{
Method possiblyLockedMethod = UITester.class.getMethod( "printIfAvailable" );
Annotation methodLockCheck = possiblyLockedMethod.getAnnotation( FunctionAnnotation.class );
if ( !( ( FunctionAnnotation) methodLockCheck ).locked() ) tester.printIfAvailable( value );
}
catch( NoSuchMethodException e )
{
System.out.println( "[MINIMAL UI][ERROR] Cannot find method to be retrieved. Reflection failed. " + e.getMessage() );
}
catch( Exception e )
{
System.out.println( "[MINIMAL UI][ERROR] Exception during UI testing via reflection: " + e.getMessage() + " Exception: " + e.toString() );
}
}
else
{
System.out.println( "[MINIMAL UI][ERROR] Reflection error. Unable to read annotation!" );
}
}
Running MinimalUI#testUI
results in a NoSuchMethodException
being thrown, so far I do not understand why. The exact line throwing the exception is Method possiblyLockedMethod = UITester.class.getMethod( "printIfAvailable" );
.
getMethod
? Possibly class declaration is changed somehow? printIfAvailable
is declared public
, so then why is it not found? Do annotations somehow influence the public
status? @Retention( RetentionPolicy.RUNTIME )
, is it possible that this prevents the function from being defined as the class is loaded or anything of the sort? I assume it is something simple I am missing. Currently there were no typos I was able to find, so what is going on there?
The call UITester.class.getMethod( "printIfAvailable" )
means that you're trying to get a method called printIfAvailable
that takes no parameters (the parameterTypes
parameter of getMethod
is a var-arg).
However, your method is declared with a String
parameter. You should get it with
UITester.class.getMethod( "printIfAvailable", String.class );
Your problem right now is that you're using the getMethod
-method wrong. You just search for a method without any parameter. If you change it to this UITester.class.getMethod( "printIfAvailable", String.class );
it will work fine.
JavaDoc:
/**
* Returns a {@code Method} object that reflects the specified public
* member method of the class or interface represented by this
* {@code Class} object. The {@code name} parameter is a
* {@code String} specifying the simple name of the desired method. The
* {@code parameterTypes} parameter is an array of {@code Class}
* objects that identify the method's formal parameter types, in declared
* order. If {@code parameterTypes} is {@code null}, it is
* treated as if it were an empty array.
* ...
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.