Welcome to follow my public numberEfficient Android Development“Focuses on Android project efficiency and development experience, covering topics such as infrastructure, Kotlin Multiplatform, Gradle construction and optimization, etc. At the same time, we also talk about overseas work and life, and push the latest Podcast of” Two-part radio “.
“Build North” is a series of articles exploring Android building. It covers Gradle, Android Gradle Plugin, Kotlin Script, and other tools, as well as related architecture applications. To find the problem to solve the problem as the starting point, transfer new knowledge to improve production efficiency as the foothold.
I recently changed a previous Annotation Processor and wanted to implement a requirement like this: Determine whether interfaces of a Class implement extends from a unified parent interface. Debug + Evaluate Expression unearth the TypeElement instance to see if it has a valid API.
typeElement.getInterfaces()
You can get the List of the current element, which is pretty straightforward;- The typeMirror in the List, essentially
com.sun.tools.javac.code.Type$ClassType
Type; - Further, Evaluate Expression is used to Evaluate Expression
((Type.ClassType)mirror).interfaces_field
We can get the specific Interface information at the top level, well, that’s pretty much what we want;
With that in mind, write a quick test code. Then compile package – unexpectedly error (please ignore it is a Chinese error =. =) :
Error: package com.sun.tools.javac.code not found Error: symbol not found Symbol: class Type
This class is also a built-in tool class of the JDK. The only conceivable reason is that not all JDK packages are already in the CLASspath at compile time. In the process of Google, also found similar problems, but carefully check the IDE Boot JDK configuration, Gradle JAVA_HOME configuration, nothing wrong. Well, maybe it’s some kind of default operation that nobody knows about…
Google did not have a clear answer, asked a lot of brothers also only said that they had encountered similar problems, and finally rely on their own lead package to solve (if there is an understanding of the students welcome to send me email discussion!) . Here is my solution:
// Manually add tools.jar to compile
// Use the environment variables provided by Gradle to avoid writing lots of compatibility code yourself
compile files(org.gradle.internal.jvm.Jvm.current().toolsJar)
// Similar environment variables are provided by Gradle
// import org.gradle.internal.jvm.Jvm
// println Jvm.current().javaHome
// println Jvm.current().javacExecutable
// println Jvm.current().javadocExecutable.Copy the code
Even if the packet problem is solved, there is still a problem with finding the upper Interface. Interfaces_field: ((type.classtype)mirror).interfaces_field: ((type.classtype)mirror).interfaces_field There are solutions:
TypeElement typeElement = elementUtils.getTypeElement(interfaceCanonicalName); List<? extends TypeMirror> interfaces = typeElement.getInterfaces(); .Copy the code
Loop with elementUtils. GetTypeElement (interfaceCanonicalName) take Interface can all the way up.
Welcome to comment like, and follow my public accountEfficient Android Development.