Kotlin - 如何从注释处理器获取 KClass<*> 注释参数
Kotlin - How to get KClass<*> annotation parameter from annotation processor
我有以下注释:
@Target(AnnotationTarget.CLASS)
@Retention(AnnotationRetention.SOURCE)
@MustBeDocumented
annotation class Model(
val owner: KClass<*>,
val consumer: KClass<*>
)
@Model(DataOwner::class, DataConsumer::class)
interface Student {
val name: String
val group: Group
}
我需要在注释处理器中获取 owner
和 consumer
的值。
我试过这种方法:
private inline fun <reified T> findAnnotationValue(
element: Element,
annotationClass: KClass<*>,
valueName: String
): T? {
return element.annotationMirrors.map {
it to it.annotationType.asElement() as TypeElement
}.firstOrNull { (_, element) ->
element.qualifiedName.contentEquals(annotationClass.qualifiedName)
}?.let { (mirror, _) ->
extractValue(mirror, valueName)
}
}
private inline fun <reified T> extractValue(
annotationMirror: AnnotationMirror,
valueName: String
): T? {
return annotationMirror.elementValues.toList()
.firstOrNull { (key, _) ->
key.simpleName.contentEquals(valueName)
}?.let { (_, value) ->
value.value as T
}
}
val ownerClass: KClass<*> = findAnnotationValue(
element,
Model::class,
"owner"
)
但是它给了我这个错误:
e: [kapt] An exception occurred: java.lang.ClassCastException: com.sun.tools.javac.code.Type$ClassType cannot be cast to kotlin.reflect.KClass
我也试过这个:
val ownerClass: KClass<*> = element.getAnnotation(Model::class.java).owner
但是它给了我这个错误:
e: [kapt] An exception occurred: javax.lang.model.type.MirroredTypeException: Attempt to access Class object for TypeMirror inc.ahmedmourad.systems.tutors.domain.model.DataOwner
inc.ahmedmourad.systems.tutors.domain.model.DataOwner
是传递给注释的 owner
值。
这就是我现在遇到的问题,感谢您的帮助。
谢谢!
让我们从第二种方法不起作用的原因开始:
这显然也适用于 KClass
。
因此对于注释中的 类,您只能得到 TypeMirror
(implemented in this case by Type.ClassType
,但这是您不应依赖的内部细节)而不是 KClass
。通过第一种方法或
inline fun <reified T : Annotation> Element.getAnnotationClassValue(f: T.() -> KClass<*>) = try {
getAnnotation(T::class.java).f()
throw Exception("Expected to get a MirroredTypeException")
} catch (e: MirroredTypeException) {
e.typeMirror
}
可以用作
element.getAnnotationClassValue<Model> { owner }
和 returns TypeMirror
对于 DataOwner
。
我有以下注释:
@Target(AnnotationTarget.CLASS)
@Retention(AnnotationRetention.SOURCE)
@MustBeDocumented
annotation class Model(
val owner: KClass<*>,
val consumer: KClass<*>
)
@Model(DataOwner::class, DataConsumer::class)
interface Student {
val name: String
val group: Group
}
我需要在注释处理器中获取 owner
和 consumer
的值。
我试过这种方法:
private inline fun <reified T> findAnnotationValue(
element: Element,
annotationClass: KClass<*>,
valueName: String
): T? {
return element.annotationMirrors.map {
it to it.annotationType.asElement() as TypeElement
}.firstOrNull { (_, element) ->
element.qualifiedName.contentEquals(annotationClass.qualifiedName)
}?.let { (mirror, _) ->
extractValue(mirror, valueName)
}
}
private inline fun <reified T> extractValue(
annotationMirror: AnnotationMirror,
valueName: String
): T? {
return annotationMirror.elementValues.toList()
.firstOrNull { (key, _) ->
key.simpleName.contentEquals(valueName)
}?.let { (_, value) ->
value.value as T
}
}
val ownerClass: KClass<*> = findAnnotationValue(
element,
Model::class,
"owner"
)
但是它给了我这个错误:
e: [kapt] An exception occurred: java.lang.ClassCastException: com.sun.tools.javac.code.Type$ClassType cannot be cast to kotlin.reflect.KClass
我也试过这个:
val ownerClass: KClass<*> = element.getAnnotation(Model::class.java).owner
但是它给了我这个错误:
e: [kapt] An exception occurred: javax.lang.model.type.MirroredTypeException: Attempt to access Class object for TypeMirror inc.ahmedmourad.systems.tutors.domain.model.DataOwner
inc.ahmedmourad.systems.tutors.domain.model.DataOwner
是传递给注释的 owner
值。
这就是我现在遇到的问题,感谢您的帮助。 谢谢!
让我们从第二种方法不起作用的原因开始:
这显然也适用于 KClass
。
因此对于注释中的 类,您只能得到 TypeMirror
(implemented in this case by Type.ClassType
,但这是您不应依赖的内部细节)而不是 KClass
。通过第一种方法或
inline fun <reified T : Annotation> Element.getAnnotationClassValue(f: T.() -> KClass<*>) = try {
getAnnotation(T::class.java).f()
throw Exception("Expected to get a MirroredTypeException")
} catch (e: MirroredTypeException) {
e.typeMirror
}
可以用作
element.getAnnotationClassValue<Model> { owner }
和 returns TypeMirror
对于 DataOwner
。