Files
kotlin-fork/compiler/testData/codegen/box/annotations/instances/annotationInstances.kt
T
Leonid Startsev 648c1f4599 Support instantiation of annotations with type parameters
By ignoring type parameters. Since type parameters in annotations are a
very limited feature, their sole use is to be able to specify them as
KClass argument: annotation class Foo<T: Any>(val bar: KClass<T>).
Since we can encounter type param only as a KClass type argument (and
never as a property type), simple approach of ignoring them works fine.
In that case, since we simply copy property types to synthetic
implementation class, its properties in IR start look like this:
annotation class FooImpl(override val bar: KClass<T of Foo>). This IR
seems to be not completely correct, since FooImpl.bar type contains T of
Foo param, which is out of its scope. However, so far I didn't
encounter any problems with this during testing and after MR discussion
this approach has been considered possible.

#KT-59558 Fixed
#KT-59036 Fixed
2023-07-26 17:16:13 +00:00

74 lines
1.8 KiB
Kotlin
Vendored

// IGNORE_BACKEND: JVM
// (supported: JVM_IR, JS_IR(_ES6), NATIVE)
// Regular JS works too, but without proper hashCode or equals
// WITH_STDLIB
// !LANGUAGE: +InstantiationOfAnnotationClasses
// note: taken from ../parameters.kt and ../parametersWithPrimitiveValues.kt
import kotlin.reflect.KClass
import kotlin.test.assertEquals
import kotlin.test.assertTrue as assert
enum class E { E0 }
annotation class Empty
annotation class A(
val b: Byte,
val s: Short,
val i: Int,
val f: Float,
val d: Double,
val l: Long,
val c: Char,
val bool: Boolean
)
@Retention(AnnotationRetention.RUNTIME)
annotation class Anno(
val s: String,
val i: Int,
val f: Double,
val u: UInt,
val e: E,
val a: A,
val k: KClass<*>,
val arr: Array<String>,
val intArr: IntArray,
val arrOfE: Array<E>,
val arrOfA: Array<Empty>,
val arrOfK: Array<KClass<*>>
)
fun box(): String {
val anno = Anno(
"OK", 42, 2.718281828, 43u, E.E0,
A(1, 1, 1, 1.0.toFloat(), 1.0, 1, 'c', true),
A::class, emptyArray(), intArrayOf(1, 2), arrayOf(E.E0), arrayOf(Empty()), arrayOf(E::class, Empty::class)
)
assertEquals(anno.s, "OK")
assertEquals(anno.i, 42)
assert(anno.f > 2.0 && anno.f < 3.0)
assertEquals(anno.u, 43u)
assertEquals(anno.e, E.E0)
assert(anno.a is A)
assert(anno.k == A::class)
assert(anno.arr.isEmpty())
assert(anno.intArr.contentEquals(intArrayOf(1, 2)))
assert(anno.arrOfE.contentEquals(arrayOf(E.E0)))
assert(anno.arrOfA.size == 1)
assert(anno.arrOfK.size == 2)
val ann = anno.a
assertEquals(ann.b, 1.toByte())
assertEquals(ann.s, 1.toShort())
assertEquals(ann.i, 1)
assertEquals(ann.f, 1.toFloat())
assertEquals(ann.d, 1.0)
assertEquals(ann.l, 1.toLong())
assertEquals(ann.c, 'c')
assert(ann.bool)
return "OK"
}