Architecture
@dortdb/core is a small, language-neutral
engine. It owns the query lifecycle (registration, planning, optimization, and
execution) but ships no query language itself. Languages, functions, indices,
and optimizer rules are all plug-ins that attach to the core.
The query pipeline
Every query follows the same path:
- Register. In-memory data is registered as a source (an operation). Optionally, it is indexed.
- Parse. The selected language plug-in parses the query text into an abstract syntax tree (AST).
- Build a plan. The AST is lowered into a logical plan of unified-algebra operators. Because every language targets the same algebra, a query that mixes languages still becomes one plan.
- Optimize. The rule-based optimizer rewrites the plan (pushing down selections, using indices, and so on).
- Execute. The executor evaluates the plan lazily over the registered sources.
- Serialize. The executor works with an internal representation, so a language serializer converts results back into ordinary JavaScript values before they are returned.
The DortDB methods map
onto these stages:
parse,
buildPlan,
executePlan,
and the all-in-one
query. See
Running Queries.
Packages
DortDB is a set of small packages so that a deployment bundles only what it uses:
@dortdb/core: the engine, optimizer, index abstractions, and every extension point.@dortdb/lang-sql,@dortdb/lang-cypher,@dortdb/lang-xquery: the provided language plug-ins, one per data model.@dortdb/datetime: an example extension bundling date/time functions.
Each language declares the core as a peer dependency, so one core instance backs all loaded languages.
Extending the algebra: the visitor pattern
The core processes plans with an extended visitor pattern. A plan operator's
accept()
method receives a dictionary of visitors keyed by language, and dispatch keys
on both the operator's type and the language that instantiated it: a core
operator built by SQL is handled by SQL's visitor, the same operator type built
by Cypher by Cypher's. A language implements the full visitor interface,
usually by subclassing the core visitor and overriding only the methods for the
operators it adds, which is what lets it grow the algebra without changing the
core. For instance, XQuery adds a
TreeJoin operator for path navigation.
See Plan Visitors for the individual passes.
This is the seam that Extending DortDB builds on. The formal side, what the operators mean, is covered in the Formalism section.
Execution model
Execution is lazy, synchronous, and single-threaded: iterating a result pulls rows through the operator tree on the calling thread, so functions and aggregates must be synchronous. The engine is schema-free: sources are plain in-memory values read through data adapters, which is what keeps registration free and languages decoupled from data shape. See Limitations for the consequences of these choices.