Skip to content

Instantly share code, notes, and snippets.

@seratch
Last active December 15, 2015 12:49
Show Gist options
  • Save seratch/5262490 to your computer and use it in GitHub Desktop.
Save seratch/5262490 to your computer and use it in GitHub Desktop.
"Type-safe" Dynamic implemenatation in Scala 2.10
$ sbt test
[info] Loading global plugins from /Users/sera/.sbt/plugins
[info] Set current project to default-eb7de3 (in build file:/Users/sera/tmp/typesafe-dynamic-example/)
[info] Compiling 1 Scala source to /Users/sera/tmp/typesafe-dynamic-example/target/scala-2.10/test-classes...
[error] /Users/sera/tmp/typesafe-dynamic-example/src/test/scala/foo/ExampleSpec.scala:23: GetName should be uncapitalized!
[error] example.GetName should equal("GETNAME")
[error] ^
[error] one error found
[error] (test:compile) Compilation failed
[error] Total time: 4 s, completed Mar 28, 2013 8:25:02 PM
$
scalaVersion := "2.10.1"
libraryDependencies <++= (scalaVersion) { scalaVersion => Seq(
"org.scala-lang" % "scala-reflect" % scalaVersion % "compile",
"org.scala-lang" % "scala-compiler" % scalaVersion % "optional",
"org.scalatest" %% "scalatest" % "[1.8,)" % "test"
)}
package foo
import scala.language.experimental.macros
import scala.reflect.macros._
object ExampleMacros {
def selectDynamicImpl(c: Context)(name: c.Expr[String]): c.Expr[String] = {
import c.universe._
val _name: String = c.eval(c.Expr[String](c.resetAllAttrs(name.tree.duplicate)))
if (_name.matches("^[A-Z0-9].+")) {
// compilation error!
c.error(c.enclosingPosition, s"${_name} should be uncapitalized!")
}
reify(name.splice.toUpperCase)
}
}
package foo
import scala.language.experimental.macros
import scala.language.dynamics
class Example extends Dynamic {
def selectDynamic(name: String): String = macro foo.ExampleMacros.selectDynamicImpl
}
import org.scalatest._
import org.scalatest.matchers._
class ExampleSpec extends FlatSpec with ShouldMatchers {
behavior of "type-safe dynamic"
it should "be compilation error" in {
val example = new Example
// works fine
example.getName should equal("GETNAME")
// compilation error!
example.GetName should equal("GETNAME")
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment