Molecule is a type safe and intuitive Scala meta-DSL for the Datomic database.
Visit ScalaMolecule.org to learn more or visit the Molecule forum
A meta-DSL
Molecule is a "meta-DSL" in the sense that your domain terms form the tokens of your queries and transactions.
So instead of fitting in your domain terms between commands like SELECT name, age FROM Person
etc, or other query constructs in other database languages, you directly use your domain terms as tokens:
Person.name.age.get
This is possible since a schema is initially defined based on your domain terms:
trait Person {
val name = oneString
val age = oneInt
}
When you compile your project with sbt compile
, Molecule generates the necessary boilerplate code in order to be able to write the more intuitive query. Since the types of each attribute name
and age
is encoded in the schema definition we'll also get typed data back from our query.
val personsWithAge: List[(String, Int)] = Person.name.age.get
// or asynchronously
val personsWithAgeFut: Future[List[(String, Int)]] = Person.name.age.getAsync
Sync and Async APIs
Molecule offers both a synchronous and an asynchronous API for all query getters and transaction operations.
Producing Datalog
Molecule transform "molecules" like Person.name.age.get
to Datalog queries for Datomic. The returned untyped data from Datomic is then casted by Molecule to the expected Scala type.
All queries are prepared at compile time by macros. So there is no overhead at runtime when running the queries.
Getting started
- Introduction to Datomic/Molecule
- Quick-start: define a schema and create a new Datomic database
- Setup: populate a Datomic database with Molecule
- Molecule Seattle tutorial examples of using Molecule
Try demo project
git clone https://github.com/scalamolecule/molecule-demo.git
cd molecule-demo
sbt compile
- Open in your IDE
- Run tests and poke around...
Molecule in Scala project
Molecule is currently available for Scala (JVM, version 8 and later) and Scala.js (JavaScript). Scala 2.12 and Scala 2.13 are supported.
Add the following to your build files:
project/build.properties
:
sbt.version=1.4.1
project/buildinfo.sbt
:
addSbtPlugin("org.scalamolecule" % "sbt-molecule" % "0.9.0")
build.sbt
:
lazy val yourProject = project.in(file("app"))
.enablePlugins(MoleculePlugin)
.settings(
resolvers ++= Seq(
"datomic" at "http://files.datomic.com/maven",
"clojars" at "http://clojars.org/repo",
Resolver.sonatypeRepo("releases")
),
libraryDependencies ++= Seq(
"org.scalamolecule" %% "molecule" % "0.22.8",
"com.datomic" % "datomic-free" % "0.9.5697"
),
moleculeSchemas := Seq("app") // paths to your schema definition files...
)
Molecule in a Scala.js project
Molecule AST's and other generic interfaces have been ported to Scala.js so that you can also work with Molecule on the client side. See the molecule-admin project for an example of how Molecule is used both on the server and client side.
project/buildinfo.sbt
:
addSbtPlugin("org.scalamolecule" % "sbt-molecule" % "0.9.0")
addSbtPlugin("org.scala-js" % "sbt-scalajs" % "1.3.0")
addSbtPlugin("org.portable-scala" % "sbt-scalajs-crossproject" % "1.0.0")
build.sbt
(CrossType.Full example):
import sbtcrossproject.CrossPlugin.autoImport.crossProject
lazy val yourProject = crossProject(JSPlatform, JVMPlatform)
.in(file("."))
lazy val yourProjectJVM = yourProject.jvm
.enablePlugins(MoleculePlugin)
.settings(
resolvers ++= Seq(
"datomic" at "http://files.datomic.com/maven",
"clojars" at "http://clojars.org/repo",
Resolver.sonatypeRepo("releases")
),
libraryDependencies ++= Seq(
"org.scalamolecule" %% "molecule" % "0.22.8",
"com.datomic" % "datomic-free" % "0.9.5697"
),
moleculeSchemas := Seq("app") // paths to your schema definition files...
)
lazy val yourProjectJS = yourProject.js
.settings(
libraryDependencies ++= Seq(
("org.scalamolecule" %%% "molecule" % "0.22.8")
.exclude("com.datomic", "datomic-free")
),
moleculeSchemas := Seq("app") // paths to your schema definition files...
)
Note how we exclude the Datomic dependency on the js side (since Datomic is obviously not compiled to javascript).
Molecule is available at maven.
Test
Test in IDE or with sbt
(Scala 2.13.2):
sbt
// All tests
sbt:molecule> test
// All JS or JVM tests
sbt:molecule> moleculeJS/test
sbt:molecule> moleculeJVM/test
// Single test
sbt:molecule> testOnly molecule.coretests.expression.Comparison
Author
Marc Grue
Credits/inspiration/acknowledgements
- Datomisca, a Scala API for Datomic
License
Molecule is licensed under the Apache License 2.0