Overridden annotations ignored in Java 8 PropertyDescriptor

I'm not quite sure how to briefly describe this problem, so please bear with me.

I am studying the upgrade of our application from Java 7 to Java 8. The application uses the use of reflection to dynamically instantiate various business objects (the so-called "Adaptive Object Model" ). When I try to create an application with the latest version of Java 8 (Oracle 1.8.0_25), some of the tests start to fail. In particular, there is a test that verifies that the getter method in the "test object" is annotated with a specific annotation, and the test fails because the annotation is not found. The super "entity" class has some common fields that apply to all instances of the entity (name, description, display name, etc.), and in the test class, the "test object" extends the "entity"and overrides one of the getter methods (getDisplayName) and adds an additional annotation:

static class EntityWithCompositeDisplayName extends Entity {
    @CompositeProperty("${name} - ${description}")
    @Override
    public String getDisplayName() {
        return super.getDisplayName();
    }
}

@CompositeProperty is our own annotation. This has a METHOD goal and RUNTIME Retention.

The test calls the following code to see if the annotation is present:

    CompositeProperty compositeProperty = propd.getReadMethod().getAnnotation(CompositeProperty.class);

"compositeProperty" returns null in Java 8, but non-null in Java 7. But if I try to getAnnotation () for one of the annotations, declare the super method getDisplayName (), then that's fine. Similarly, if I move the CompositeProperty annotation to a superclass, then the test passes, but in practice this is not an option. Can anyone explain this behavior?

+4
source share
2 answers

After digging a bit in the JDK source code, here's what happens inside the JDK8 implementation Introspector:

  • Introspector . Introspector. getTargetPropertyInfo , PropertyDescriptor s.
  • EntityWithCompositeDisplayName Object::getClass Entity::getName.
  • EntityWithCompositeDisplayName Introspector getPublicDeclaredMethods(Class), com.sun.beans.MethodFinder::findAccessibleMethod(Method).
  • (!) Class , , EntityWithCompositeDisplayName. , , , . , , , private-private - ( ).

Method MethodFinder JDK7 ( ). , , .

(, , ) .

+2

, :

public class MyAnnotatedClass extends MyAnnotatedSuperClass{

    @MyCustomAnnotation(name="annotationName", value="annotationValue")
    @Override
    public String getMyString() {
        return myString;
    }

    public static void main(String args[])
    {
        Class<MyAnnotatedClass> myClass =  MyAnnotatedClass.class;

        MyCustomAnnotation myCustomAnnotation = myClass.getMethods()[0].getAnnotation(MyCustomAnnotation.class);

        if(myCustomAnnotation!=null)
            System.out.println("ok: "+myCustomAnnotation.name());
        else
            System.out.println("not ok");
    }
}

abstract class MyAnnotatedSuperClass {
    public String myString;
    public abstract String getMyString();
}

@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.METHOD)

public @interface MyCustomAnnotation {
     public String name();
     public String value();
}

, , .

0

All Articles