dimanche 7 juillet 2019

Dynamic compilation of multiple Scala classes at runtime

I know I can compile individual "snippets" in Scala using the Toolbox like this:

import scala.reflect.runtime.universe
import scala.tools.reflect.ToolBox

object Compiler {
  val tb = universe.runtimeMirror(getClass.getClassLoader).mkToolBox()

  def main(args: Array[String]): Unit = {
    tb.eval(tb.parse("""println("hello!")"""))
  }
}

Is there any way I can compile more than just "snippets", i.e., classes that refer to each other? Like this:

import scala.reflect.runtime.universe
import scala.tools.reflect.ToolBox

object Compiler {
  private val tb = universe.runtimeMirror(getClass.getClassLoader).mkToolBox()

  val a: String =
    """
      |package pkg {
      |
      |class A {
      |def compute(): Int = 42
      |}}
    """.stripMargin

  val b: String =
    """
      |import pkg._
      |
      |class B {
      |def fun(): Unit = {
      |    new A().compute()
      |}
      |}
    """.stripMargin

  def main(args: Array[String]): Unit = {
    val compiledA = tb.parse(a)
    val compiledB = tb.parse(b)
    tb.eval(compiledB)
  }
}

Obviously, my snippet doesn't work as I have to tell the toolbox how to resolve "A" somehow:

Exception in thread "main" scala.tools.reflect.ToolBoxError: reflective compilation has failed:

not found: type A





Aucun commentaire:

Enregistrer un commentaire