Do I need to repeat annotations in a public container?
I noticed a mismatch between the Eclipse compiler and javac when using repeating annotations. The repeating annotation and its container were in the same package, but the former was declared public and the latter remained private. Eclipse had no layout issues, although re-annotation was mentioned in another package. javac, on the other hand, refused to compile by saying
The value () in [container] is defined in an inaccessible class or interface
My question is which one is correct? I couldn't find any rule about this in the JLS. Does this mean that he is open to interpretation? Or is there a bug in one of the compilers?
source to share
There are no claims regarding accessibility, but the spec makes it clear that it is possible that a repeatable annotation may be limited to repeatability only in certain places due to the way the annotation is declared.
...
T applies to at least the same types of program item as TC (ยง9.6.4.1). In particular, if the types of program elements, where T is applicable, are denoted by the set m1, and the types of program elements in which TC is applied are denoted by the set m2, then each type in m2 must occur in m1, ...
This section implements the policy that the type of annotation can be repeated only for certain types of program elements, where it is applicable
This is also with an example :
Example 9.6.3-2. Restriction where annotations can repeat
Annotations whose type declaration indicates that the target
java.lang.annotation.ElementType.TYPE
can be displayed in at least as many places as the annotation whose type declaration indicates the targetjava.lang.annotation.ElementType.ANNOTATION_TYPE
. For example, given the following declarations that are duplicate and contain annotation types:
@Target(ElementType.TYPE) @Repeatable(FooContainer.class) @interface Foo {} @Target(ElementType.ANNOTATION_TYPE) @Interface FooContainer { Foo[] value(); }
@Foo
can appear in any type declaration, and@FooContainer
can only appear in annotation type declarations. Therefore, the following annotation type declaration is legal:@Foo @Foo @interface X {}
while the following interface declaration is illegal:
@Foo @Foo interface X {}
While this discusses constraints imposed @Target
rather than accessibility modifiers, it describes a "spirit" that can be applied to the latter as well. Obviously, the intent is that a repeatable annotation can be repeated only if the properties of the specified annotation of the container allow, otherwise the annotation can still be used, but with only one occurrence.
Not like repeatable annotation properties that can override annotation type properties of a container. This is consistent with the behavior elsewhere; even if there is no reference to an unavailable annotation type in the source code, compiling the repeated annotation will create a reference in the class file, and the class file may not contain symbolic links to unavailable classes and should not be an exception for container annotations only.
source to share