Support package level annotations in Java
#KT-10942 In Progress
This commit is contained in:
@@ -43,10 +43,8 @@ import com.sun.tools.javac.util.Options
|
||||
import org.jetbrains.kotlin.javac.wrappers.symbols.SymbolBasedClass
|
||||
import org.jetbrains.kotlin.javac.wrappers.symbols.SymbolBasedClassifierType
|
||||
import org.jetbrains.kotlin.javac.wrappers.symbols.SymbolBasedPackage
|
||||
import org.jetbrains.kotlin.javac.wrappers.trees.TreeBasedClass
|
||||
import org.jetbrains.kotlin.javac.wrappers.trees.TreeBasedPackage
|
||||
import org.jetbrains.kotlin.javac.wrappers.trees.TreePathResolverCache
|
||||
import org.jetbrains.kotlin.javac.wrappers.trees.computeClassId
|
||||
import org.jetbrains.kotlin.javac.wrappers.trees.*
|
||||
import org.jetbrains.kotlin.load.java.structure.JavaAnnotation
|
||||
import org.jetbrains.kotlin.load.java.structure.JavaClass
|
||||
import org.jetbrains.kotlin.load.java.structure.JavaClassifier
|
||||
import org.jetbrains.kotlin.load.java.structure.JavaPackage
|
||||
@@ -142,6 +140,14 @@ class JavacWrapper(
|
||||
}
|
||||
.associateBy(TreeBasedPackage::fqName)
|
||||
|
||||
private val packageSourceAnnotations = compilationUnits
|
||||
.filter {
|
||||
it.sourceFile.isNameCompatible("package-info", JavaFileObject.Kind.SOURCE) &&
|
||||
it.packageName != null
|
||||
}.associateBy({ FqName(it.packageName!!.toString()) }) { compilationUnit ->
|
||||
compilationUnit.packageAnnotations.map { TreeBasedAnnotation(it, compilationUnit, this) }
|
||||
}
|
||||
|
||||
private val kotlinClassifiersCache = KotlinClassifiersCache(if (javaFiles.isNotEmpty()) kotlinFiles else emptyList(), this)
|
||||
private val treePathResolverCache = TreePathResolverCache(this)
|
||||
private val symbolBasedClassesCache = hashMapOf<String, SymbolBasedClass?>()
|
||||
@@ -212,6 +218,9 @@ class JavacWrapper(
|
||||
.filterKeys { it.isSubpackageOf(fqName) && it != fqName }
|
||||
.map { it.value }
|
||||
|
||||
fun getPackageAnnotationsFromSources(fqName: FqName): List<JavaAnnotation> =
|
||||
packageSourceAnnotations[fqName] ?: emptyList()
|
||||
|
||||
fun findClassesFromPackage(fqName: FqName): List<JavaClass> =
|
||||
javaClasses
|
||||
.filterKeys { it?.parentOrNull() == fqName }
|
||||
@@ -329,4 +338,4 @@ class JavacWrapper(
|
||||
return symbol.let { SymbolBasedClass(it, this@JavacWrapper, it.classfile) }
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
+11
-2
@@ -17,7 +17,10 @@
|
||||
package org.jetbrains.kotlin.javac.wrappers.symbols
|
||||
|
||||
import org.jetbrains.kotlin.javac.JavacWrapper
|
||||
import org.jetbrains.kotlin.load.java.structure.JavaAnnotation
|
||||
import org.jetbrains.kotlin.load.java.structure.JavaPackage
|
||||
import org.jetbrains.kotlin.load.java.structure.MapBasedJavaAnnotationOwner
|
||||
import org.jetbrains.kotlin.load.java.structure.buildLazyValueForMap
|
||||
import org.jetbrains.kotlin.name.FqName
|
||||
import org.jetbrains.kotlin.name.Name
|
||||
import javax.lang.model.element.PackageElement
|
||||
@@ -25,7 +28,7 @@ import javax.lang.model.element.PackageElement
|
||||
class SymbolBasedPackage(
|
||||
element: PackageElement,
|
||||
javac: JavacWrapper
|
||||
) : SymbolBasedElement<PackageElement>(element, javac), JavaPackage {
|
||||
) : SymbolBasedElement<PackageElement>(element, javac), JavaPackage, MapBasedJavaAnnotationOwner {
|
||||
|
||||
override val fqName: FqName
|
||||
get() = FqName(element.qualifiedName.toString())
|
||||
@@ -33,9 +36,15 @@ class SymbolBasedPackage(
|
||||
override val subPackages: Collection<JavaPackage>
|
||||
get() = javac.findSubPackages(FqName(element.qualifiedName.toString()))
|
||||
|
||||
|
||||
override val annotations: Collection<JavaAnnotation>
|
||||
get() = element.annotationMirrors.map { SymbolBasedAnnotation(it, javac) }
|
||||
|
||||
override val annotationsByFqName: Map<FqName?, JavaAnnotation> by buildLazyValueForMap()
|
||||
|
||||
override fun getClasses(nameFilter: (Name) -> Boolean) =
|
||||
javac.findClassesFromPackage(fqName).filter { nameFilter(it.name) }
|
||||
|
||||
override fun toString() = element.qualifiedName.toString()
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
+12
-5
@@ -16,6 +16,7 @@
|
||||
|
||||
package org.jetbrains.kotlin.javac.wrappers.trees
|
||||
|
||||
import com.sun.source.tree.CompilationUnitTree
|
||||
import com.sun.source.util.TreePath
|
||||
import com.sun.tools.javac.tree.JCTree
|
||||
import org.jetbrains.kotlin.javac.JavacWrapper
|
||||
@@ -27,11 +28,17 @@ import org.jetbrains.kotlin.name.ClassId
|
||||
import org.jetbrains.kotlin.name.Name
|
||||
|
||||
class TreeBasedAnnotation(
|
||||
val annotation: JCTree.JCAnnotation,
|
||||
val treePath: TreePath,
|
||||
val javac: JavacWrapper
|
||||
private val annotation: JCTree.JCAnnotation,
|
||||
private val compilationUnit: CompilationUnitTree,
|
||||
private val javac: JavacWrapper
|
||||
) : JavaElement, JavaAnnotation {
|
||||
|
||||
constructor(
|
||||
annotation: JCTree.JCAnnotation,
|
||||
treePath: TreePath,
|
||||
javac: JavacWrapper
|
||||
) : this(annotation, treePath.compilationUnit, javac)
|
||||
|
||||
override val arguments: Collection<JavaAnnotationArgument>
|
||||
get() = annotation.arguments.map { TreeBasedAnnotationArgument(Name.identifier(it.toString())) }
|
||||
|
||||
@@ -39,8 +46,8 @@ class TreeBasedAnnotation(
|
||||
get() = resolve()?.computeClassId()
|
||||
|
||||
override fun resolve() =
|
||||
javac.resolve(TreePath.getPath(treePath.compilationUnit, annotation.annotationType)) as? JavaClass
|
||||
javac.resolve(TreePath.getPath(compilationUnit, annotation.annotationType)) as? JavaClass
|
||||
|
||||
}
|
||||
|
||||
class TreeBasedAnnotationArgument(override val name: Name) : JavaAnnotationArgument, JavaElement
|
||||
class TreeBasedAnnotationArgument(override val name: Name) : JavaAnnotationArgument, JavaElement
|
||||
|
||||
+1
-1
@@ -154,4 +154,4 @@ class TreeBasedClass(
|
||||
|
||||
override fun findInnerClass(name: Name) = innerClasses[name]
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
+10
-2
@@ -18,12 +18,15 @@ package org.jetbrains.kotlin.javac.wrappers.trees
|
||||
|
||||
import com.intellij.openapi.vfs.VirtualFile
|
||||
import org.jetbrains.kotlin.javac.JavacWrapper
|
||||
import org.jetbrains.kotlin.load.java.structure.JavaAnnotation
|
||||
import org.jetbrains.kotlin.load.java.structure.JavaPackage
|
||||
import org.jetbrains.kotlin.load.java.structure.MapBasedJavaAnnotationOwner
|
||||
import org.jetbrains.kotlin.load.java.structure.buildLazyValueForMap
|
||||
import org.jetbrains.kotlin.name.FqName
|
||||
import org.jetbrains.kotlin.name.Name
|
||||
import javax.tools.JavaFileObject
|
||||
|
||||
class TreeBasedPackage(val name: String, val javac: JavacWrapper, val file: JavaFileObject) : JavaPackage {
|
||||
class TreeBasedPackage(val name: String, val javac: JavacWrapper, val file: JavaFileObject) : JavaPackage, MapBasedJavaAnnotationOwner {
|
||||
|
||||
override val fqName: FqName
|
||||
get() = FqName(name)
|
||||
@@ -38,10 +41,15 @@ class TreeBasedPackage(val name: String, val javac: JavacWrapper, val file: Java
|
||||
override fun getClasses(nameFilter: (Name) -> Boolean) =
|
||||
javac.findClassesFromPackage(fqName).filter { nameFilter(it.fqName!!.shortName()) }
|
||||
|
||||
override val annotations
|
||||
get() = javac.getPackageAnnotationsFromSources(fqName)
|
||||
|
||||
override val annotationsByFqName: Map<FqName?, JavaAnnotation> by buildLazyValueForMap()
|
||||
|
||||
override fun equals(other: Any?) = (other as? TreeBasedPackage)?.name == name
|
||||
|
||||
override fun hashCode() = name.hashCode()
|
||||
|
||||
override fun toString() = name
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user