How to get annotation with default value in scala

226 views
Skip to first unread message

蒋震宇

unread,
Nov 6, 2016, 10:10:31 AM11/6/16
to scala-user
Hi,all:

How to get annotation object with default value of comment?

import scala.annotation.StaticAnnotation
import scala.reflect.runtime._
import scala.reflect.runtime.universe._
// The annotation has default value
case class Table(idField: String = "") extends StaticAnnotation
@Table()
case class SomeEntity()

println(getClassAnnotation[Table](classOf[SomeEntity]).idField)
def getClassAnnotation[A: TypeTag](beanClazz: Class[_]): A = {
  val typeAnnotation=currentMirror.typeOf[A]
  currentMirror.classSymbol(beanClazz).toType.typeSymbol.asClass.annotations.find(a => a.tree.tpe == typeAnnotation).map {
    annotation =>
      val value = annotation.tree.children.tail.map(_.productElement(0).asInstanceOf[Constant].value)
      currentMirror.reflectClass(typeAnnotation.typeSymbol.asClass).
        reflectConstructor(typeAnnotation.decl(termNames.CONSTRUCTOR).asMethod)(value: _*)
  }.get.asInstanceOf[A]
}

The error is
java.lang.ClassCastException: scala.reflect.internal.Trees$Select cannot be cast to scala.reflect.api.Constants$ConstantApi

If override value will pass , like this
@Table(idField="code")
case class SomeEntity()

Thanks.

Jasper-M

unread,
Nov 7, 2016, 5:33:22 AM11/7/16
to scala-user
Hi,

When a default value is defined a call to Table() will be transformed into something like Table(Table.defaultValue$init$1)
So in that case the Tree of the argument passed to the Table constructor will not be a Literal Constant but a representation of a method call (a Select apparently). So if you want to get its value, you'll have to call that method somehow.

Something like this:

def getValue(tree: Tree) = tree match {
  case select @ Select(_,_) =>
    import scala.tools.reflect.ToolBox
    val tb = runtimeMirror(getClass.getClassLoader).mkToolBox()
    tb.eval(tb.untypecheck(select))
  case Literal(Constant(value)) => value
}

kr,
Jasper

Op zondag 6 november 2016 16:10:31 UTC+1 schreef 蒋震宇:
Reply all
Reply to author
Forward
0 new messages