Why java classes do not inherit annotations from implemented interfaces?

JavaInheritanceInterfaceAnnotations

Java Problem Overview


I'm using a Dependency Injection framework (Guice's AOP to intercept some method calls specifically). My class implements an interface and I would like to annotate the interface methods so the framework could select the right methods. Even if the annotation type is annotated with Inherited annotation implementing class doesn't inherit the annotation as stated in Inherited's java doc:

> Note also that this meta-annotation > only causes annotations to be > inherited from superclasses; > annotations on implemented interfaces > have no effect.

What could be the reason for this? Getting to know all interfaces that an object's class does implement in runtime is not that hard thing to do so there must be a good reason behind this decision.

Java Solutions


Solution 1 - Java

I'd say the reason is that otherwise a multiple-inheritance problem would occur.

Example:

@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.METHOD) @Inherited
public @interface Baz { String value(); }

public interface Foo{
    @Baz("baz") void doStuff();
}

public interface Bar{
    @Baz("phleem") void doStuff();
}

public class Flipp{
    @Baz("flopp") public void doStuff(){}
}

public class MyClass extends Flipp implements Foo, Bar{}

If I do this:

MyClass.class.getMethod("doStuff").getAnnotation(Baz.class).value()

what's the result going to be? 'baz', 'phleem' or 'flopp'?


For this reason, annotations on interfaces are rarely useful.

Solution 2 - Java

From the [Javadoc][1] for @Inherited:

> Indicates that an annotation type is automatically inherited. If an > Inherited meta-annotation is present on an annotation type > declaration, and the user queries the annotation type on a class > declaration, and the class declaration has no annotation for this > type, then the class's superclass will automatically be queried for > the annotation type. This process will be repeated until an annotation > for this type is found, or the top of the class hierarchy (Object) is > reached. If no superclass has an annotation for this type, then the > query will indicate that the class in question has no such annotation. > Note that this meta-annotation type has no effect if the annotated > type is used to annotate anything other than a class. Note also that > this meta-annotation only causes annotations to be inherited from > superclasses; annotations on implemented interfaces have no effect.

On the other hand, JSR 305 validators do some sort of inheritance lookup. If you have a hierarchy of classes:

//Person.java
@Nonnull
 public Integer getAge() {...}

//Student.java (inherits from Person)
@Min(5)
public Integer getAge() {...}

Then the effective validations on Student.getAge() are @Nonnull @Min(5). @Nonnull has no @Inherited meta-annotation.

[1]: http://docs.oracle.com/javase/7/docs/api/java/lang/annotation/Inherited.html "@Inherited Javadoc"

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionBoris PavlovićView Question on Stackoverflow
Solution 1 - JavaSean Patrick FloydView Answer on Stackoverflow
Solution 2 - JavaEric JablowView Answer on Stackoverflow