Skip to main content

In-memory · Cypher · Rust

Everything LoraDB supports — and what it doesn’t.

A complete map of the engine — Cypher coverage, surfaces, architecture, and the lines we won’t pretend to cross. Pick what you came here to verify.

  • One Rust engine · seven surfaces
  • Query pipeline — parse, analyze, compile, execute
  • Local-first · embeddable · open source

Design principles

The bets the engine took.

01

Relationships are first-class

Edges are typed, directed, and property-bearing. Traversal is O(degree), not a stack of self-joins.

02

Cypher where it counts

A pragmatic subset of Cypher — MATCH, WITH, WHERE, CREATE, RETURN. Short queries, readable intent.

03

Schema-free by design

Add a label, an edge type, or a property by writing it. No ALTER, no migration, no restart.

04

Small enough to read

A compiler-style pipeline of focused crates from parser to executor. If the database matters to your product, you should be able to read it.

Cypher coverage

The Cypher you actually write — supported.

Pattern matching, writes, aggregation pipelines, paths, temporal and spatial predicates — composed top-to-bottom with WITH.

Pattern matching

MATCH (a:Person)-[:KNOWS]->(b:Person)
WHERE a.city = 'Berlin'
RETURN a.name, collect(b.name) AS friends
MATCH reference

Writing data

MERGE (u:User {email: $email})
ON CREATE SET u.created = temporal.now()
ON MATCH  SET u.last_seen = temporal.now()
MERGE reference

Variable-length paths

MATCH p = shortestPath(
  (a:Stop {code: $from})-[:CONNECTS*..6]->(b:Stop {code: $to})
)
RETURN path.length(p) AS hops, [n IN path.nodes(p) | n.code] AS via
Paths reference

Aggregation pipelines

MATCH (u:User)-[:PLACED]->(o:Order {status: 'paid'})
WITH u, count(o) AS orders, sum(o.total) AS spend
WHERE orders >= 3
RETURN u.email, orders, spend ORDER BY spend DESC
Aggregation reference

Temporal predicates

MATCH (e:Event)
WHERE e.at >= temporal.now() - 'P7D'::DURATION
RETURN temporal.truncate('day', e.at) AS day, count(*) AS events
ORDER BY day
Temporal types

Spatial distance

WITH {latitude: 52.52, longitude: 13.405}::POINT AS origin
MATCH (s:Store)
WHERE geo.distance(s.loc, origin) < 5000
RETURN s.name, geo.distance(s.loc, origin) AS metres
ORDER BY metres
Spatial types

Functions & types

60+ built-ins. Every value typed.

Architecture

A compiler-style pipeline you can read.

Every query walks a real pipeline — parser, analyzer, compiler, executor — written from scratch in Rust. Each stage is one crate; the names line up with the source tree.

  1. 01

    Parse

    lora-parser

    A PEG grammar lifts Cypher text into a typed AST with source spans.

  2. 02

    Analyze

    lora-analyzer

    Variable scoping, label and type validation against live graph state, function resolution.

  3. 03

    Compile

    lora-compiler

    Lower the resolved IR into a logical plan, optimize (filter push-down), then a physical plan.

  4. 04

    Execute

    lora-executor

    Interpret the physical plan against the in-memory store and project results in the requested shape.

Open the sourceRead the engine on GitHub

Ways to use it

One engine, seven places to reach it.

Pick the surface that fits the host process. Cypher, parameters, and result shapes are identical across all of them.

lora-database · main.rs
use lora_database::Database;

let db = Database::in_memory();
db.execute("CREATE (:User {name: 'Ada'})", None)?;

let result = db.execute(
"MATCH (u:User) RETURN u.name",
None,
)?;
Rust guide

Know the boundary

What LoraDB does not pretend to be.

LoraDB is an in-memory engine, not a clustered production database. Below is what to expect — stated up front so you can decide whether the trade-offs match your workload.

In-memory engine

The graph lives in process memory. Durability is optional via snapshots and WAL, not a separate persistent storage backend.

Scoped indexes

RANGE, TEXT, POINT, LOOKUP, VECTOR, and FULLTEXT indexes exist for declared hot paths. The planner is still intentionally small: no global join optimizer or ANN vector structure.

Single-writer commits

Read-only queries can overlap on snapshots. Write commits and explicit read-write transactions serialize, so this is not built for high-fan-out write concurrency.

No auth or TLS in core

lora-server is meant to live behind your own ingress. The crate has no auth surface — you control the host process.

FAQ

Common questions about LoraDB.

Short answers to what evaluators usually ask before installing. The full reference lives in the docs.

Does LoraDB support the full OpenCypher language?

No. LoraDB ships a pragmatic subset of Cypher — read clauses (MATCH, OPTIONAL MATCH, WHERE, WITH, RETURN), write clauses (CREATE, MERGE, SET, DELETE, REMOVE, FOREACH), iteration (UNWIND), variable-length paths, aggregation, and most built-in functions. The Limitations page lists everything that is not supported, including general-purpose CALL, LOAD CSV, quantified path patterns, and BETWEEN.

Is there an HTTP API?

Yes. lora-server is an Axum-based HTTP service that exposes POST /query, GET /health, and opt-in admin endpoints for snapshots and WAL operations. It is meant to live behind your own ingress — the crate has no auth surface, so you control the host process.

How does LoraDB persist data?

Two layers. Snapshots write the full graph to a single file with an atomic rename and are available on every binding (Rust, Node.js, Python, WASM, Go, Ruby, HTTP). WAL-backed durability is available on every filesystem-backed surface — commits append to a write-ahead log and replay on recover above the snapshot fence. WASM stays snapshot-only because the runtime has no filesystem.

How large a dataset can LoraDB handle?

LoraDB is bounded by the RAM of one host process. There is no sharding, no replication, no distributed storage. If the working set fits in memory and you want graph queries close to the code that uses them, LoraDB is the right tool; if the dataset is too large to fit in RAM on one machine, LoraDB is the wrong tool.

Can I run LoraDB in a serverless function or edge worker?

Yes, via the WebAssembly binding. The WASM build runs in any browser or modern WASM-capable runtime (Cloudflare Workers, Deno Deploy, browser tabs). The Playground itself is a static site running LoraDB entirely in the browser via WASM. The WASM surface is snapshot-only — there is no filesystem to write a WAL to.

Is LoraDB production-ready?

LoraDB is pre-1.0. The release journey is public — see the v0.1 through v0.14 blog posts for what was shipped and what was deferred. Security fixes land on main and ship in the next tagged release; older tags are not patched. Use it where you can roll forward; do not depend on storage format stability across minor versions until 1.0.

Open a database. Run a query.

Three lines of Rust, a curl call, or a single import. The fastest way to feel LoraDB is to write a query against it.