Open lrytz opened 4 days ago
There was a comment on dotty that they might re-engineer defaults to be inline. Your bullet 3 is very appealing, or to coin a phrase, "it would be great if".
A workaround, at least for the case when the annotation parameters have distinct types, is defining constructor overloads:
class ann(x: Int, y: String) extends annotation.StaticAnnotation {
def this(x: Int) = this(x, null)
def this(s: String) = this(null, s)
}
scala> @ann(s = "ka") class K
scala> typeOf[K].typeSymbol.annotations.head
val res0: $r.intp.global.AnnotationInfo = ann("ka")
Before typing, the annotation is represented as
new ann(y = Nil.size)
. To construct theAnnotationInfo
, that expression is type checked like ordinary code, resulting inThe
AnnotationInfo
only hasann(x$2, x$1)
, the block is thrown away it seems, there's now way get to the actual arguments.Ideas
AnnotationInfo
. But IMO this is not a good solution, it leaves processing annotations too difficult.new ann(y = Nil.size)
can be typed asnew ann(<init>$default$1, Nil.size)
AnnotationInfo
, i.e.,new ann(1, Nil.size)
.For the last one, the question is how to get to the default value AST. One option is to make the compiler attach it to to a symbol, so the
class ann
above would becomeWhen constructing the
AnnotationInfo
fromnew ann(<init>$default$1, Nil.size)
we can get the AST for the default from the annotation parameter symbol.Earlier tickets: https://github.com/scala/bug/issues/7656, https://github.com/scala/bug/issues/9612
I did some prototyping when discussing
@apiStatus
(https://github.com/scala/scala/pull/8820 / https://github.com/scala/scala/compare/2.13.x...lrytz:constAnnDefaults). The goal here was to allow subclasses of annotations to define certain defaults, which would be great for@unused
: https://github.com/scala/bug/issues/12367.Fixing that at the same time would be good.