TypeMirror is missing annotation
Marcel Kliemannel
dev at marcelkliemannel.com
Sat Apr 1 06:22:24 UTC 2017
Hello,
I am writing a compiler plugin for code analyzation. The bug JDK-8031744 (https://bugs.openjdk.java.net/browse/JDK-8031744) seems to fix some problems in jdk 9 with missing annotations in the types of some kinds of elements. I found a case where the annotation is still missing. Maybe someone can say whether this is a compiler bug related to JDK-8031744, or I am doing something totally wrong?
The annotation:
-----------------------------------------
import java.lang.annotation.*;
import static java.lang.annotation.RetentionPolicy.CLASS;
@Retention(CLASS)
@Target({ElementType.TYPE_USE})
public @interface R {}
-----------------------------------------
and the class to analyse:
-----------------------------------------
import java.util.function.Consumer;
public class Test {
public void test() {
Consumer<@R String> consumer = input -> {};
}
}
-----------------------------------------
I am expecting that the parameter ‘input’ of the lambda expression is of type ‘@R() java.lang.String’, but the TypeMirror of the Element ‘input’ just gives me ‘java.lang.String’ without the annotation.
Below is a compiler plugin to reproduce this behaviour with jdk 9 build 163 and the annotation and class above. I invoke the plugin with the command:
javac -processorpath CompilerPlugin.jar -Xplugin:CompilerPlugin Test.java R.java
-----------------------------------------
import com.sun.source.tree.*;
import com.sun.source.util.*;
import javax.lang.model.element.Element;
public class CompilerPlugin implements Plugin {
@Override
public String getName() {
return "CompilerPlugin";
}
@Override
public void init(JavacTask javacTask, String[] args) {
javacTask.addTaskListener(new TaskListener() {
@Override
public void started(TaskEvent e) {}
@Override
public void finished(TaskEvent taskEvent) {
if (TaskEvent.Kind.ANALYZE.equals(taskEvent.getKind())) {
taskEvent.getCompilationUnit().getTypeDecls().forEach(typeDecl -> {
ClassTree classTree = (ClassTree) typeDecl;
classTree.getMembers().forEach(member -> {
MethodTree methodTree = (MethodTree) member;
methodTree.getBody().getStatements().forEach(statement -> {
if (Tree.Kind.VARIABLE.equals(statement.getKind())) {
// Consumer<@R String> consumer = input -> {};
VariableTree variableTree = (VariableTree) statement;
LambdaExpressionTree lambdaExpressionTree =
(LambdaExpressionTree) variableTree.getInitializer(); // input -> {}
Tree firstParameter = lambdaExpressionTree.getParameters().get(0); // input
TreePath path = TreePath.getPath(taskEvent.getCompilationUnit(), firstParameter);
Element element = Trees.instance(javacTask).getElement(path);
System.out.println(element.asType()); // java.lang.String
System.out.println(element.asType().getAnnotationMirrors()); // nothing :(
}
});
});
});
}
}
});
}
}
-----------------------------------------
Thank you for your time and best regards,
Marcel
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.openjdk.java.net/pipermail/compiler-dev/attachments/20170401/e28a8b2f/attachment.html>
More information about the compiler-dev
mailing list