Hey, all. I want to figure out how to use Scala.js tools to compile Scala expressions to Javascript during runtime. Here's a simplified setup, as an example.
Say, we have a simple DSL that consists of Ctx => Boolean
functions and boolean operations on them, a la the following:
implicit class Simple[Ctx](f: Ctx => Boolean) {
def &&(g: Ctx => Boolean): Ctx => Boolean = ctx => f(ctx) && g(ctx)
def ||(g: Ctx => Boolean): Ctx => Boolean = ctx => f(ctx) || g(ctx)
def unary_!: Ctx => Boolean = ctx => !f(ctx)
}
And let's assume that we have some "building blocks" hardcoded, compiled into Javascript, and exported, as follows:
@ExportJSTopLevel("foo") def foo[Ctx](ctx: Ctx): Boolean = ???
@ExportJSTopLevel("bar") def bar[Ctx](ctx: Ctx): Boolean = ???
// and so on
Now one can assemble simple boolean expressions out of these building blocks, such as: foo && bar
or foo || !bar
, etc.
Let's say that some persistent entities are created at runtime, with such expressions as their bodies. I want to be able to compile them to Javascript, as functions with the same signature as the building blocks above, which call those building blocks.
I found several references online to the mysterious class called ScalaJSOptimizer
somewhere in Scala.js tools. However, the links provided to that class are always broken or show it belonging to a package that the latest version of the "scalajs-tools" artifact doesn't even have.
What is the best way to accomplish what I want to do?
What you are trying to do is possible and has been researched extensively in many languages (deep DSL embedding). To achieve what you want you would have to:
The frameworks I know that you could use are:
Rep
types in your DSLs. You would have to check with the authors if these frameworks compile with Scala.js and what is the state of their JS backends.
Your proposal tries to use Scala.js as a deep embedding framework, but Scala.js can't be compiled with Scala.js.