Versioned graph database

The graph that
keeps its whole history.

patinaDB speaks Cypher and the Bolt protocol, runs as a Raft-replicated cluster with automatic failover — and every write becomes history you can query. No snapshots to restore, no audit table to maintain. The past is just another query.

Coming soon
Cypher-native · Bolt 4.4 · Raft-replicated
time-travel.cypher
-- ask the graph what it looked like last quarter
USE sales AS OF TAG 'end-of-q4'
MATCH (c:Customer)-[:PLACED]->(o:Order)
WHERE o.total > 1000
RETURN c.name, count(o) ORDER BY count(o) DESC

-- or diff two points in time, and see who changed what
CALL patinadb.diff('<engram-id>') YIELD op, entity, before, after

The name is the idea

Patina is the layer time leaves.

On bronze it's the record of every year the metal has seen. In patinaDB it's the same thing for your data: each commit is an engram — an immutable, queryable layer over the last one. Travel to any point, diff two states, trace the provenance of a single value. History isn't a backup you hope you never need. It's a first-class part of the graph.

genesis import q1 close schema change AS OF here ↑ HEAD

Performance

Often faster — because of how it's built, not how hard it tries.

Speed here comes from architecture, not from a bigger machine. A few of the reasons queries land quickly:

Cost-based planner

It picks the selective path

A statistics catalog — cardinality, distinct values, histograms — lets the planner choose the access path and join order that touches the fewest rows, instead of trusting the order you wrote.

Decode-aware cache

It stops re-decoding hot data

A multi-level cache sits above the storage page cache and keeps decoded objects, properties and adjacency — so a hot read skips the deserialize work entirely, scan-resistant and RAM-budgeted.

Sorted adjacency

Top-N traversals don't fan out

An edge-scoped sorted index serves “the 10 newest orders for this customer” as a seek-and-take, not a full expansion followed by a sort.

Space-filling curves

Geo queries seek, not scan

Points index on a Morton/Z-order curve, so a radius or bounding-box query walks a handful of key ranges — byte-identical to a full scan, without being one.

Streaming execution

Memory stays bounded

Reads stream row-by-row with bounded operator buffers, and bulk writes commit in chunks — so result size and import size don't dictate RAM.

Single-file storage

ACID without a journal tax

Built on a single-file B-tree store with native cross-tree atomic commits — durability comes from one barrier per batch, not a write-ahead log replayed on every key.

What you get

A full graph database — with a memory.

Everything you'd reach for Neo4j to do, plus the timeline. Drop in your existing drivers and tools.

Engrams — time-travel, built in

Every commit is an engram, a versioned snapshot you can travel to: AS OF any timestamp or named tag, and diff engrams to see exactly what each one created, changed or removed.

Cypher & Bolt native

A broad Cypher dialect over the Bolt protocol — the official Neo4j drivers and the Neo4j Browser connect and just work.

Replicated & highly available

A Raft-replicated cluster with automatic failover and streamed snapshots — many isolated databases on one cluster, each with its own users and roles.

Search & algorithms

Full-text (BM25), vector similarity, and graph algorithms — PageRank, connected components, degree — as first-class CALL procedures.

Embedded WASM procedures

Deterministic, sandboxed user-defined functions in any language that compiles to WebAssembly — registered with CREATE FUNCTION, called with CALL, and replicated across the cluster.

Spatial & geo

Native point and polygon types across cartesian and WGS-84, distance/within/bbox functions, and seek-based radius and k-nearest-neighbour queries.

Bulk in & out

Import and export CSV, Parquet and Arrow with a neo4j-admin-style convention, plus streaming LOAD CSV and change streams for CDC.

Fine-grained security

Per-database, per-label and per-relationship-type roles over authenticated GRANT/REVOKE, native TLS on every plane, and a durable audit log.

Anamnesis — provenance, auto-projected

Anamnesis projects every write into a W3C-PROV companion graph — which agent, which activity, which source, at what confidence — queryable like any other graph, opt-in per database and replicated across the cluster.

Correctness

Deterministic simulation tested

Snapshot isolation, optimistic concurrency, and crash recovery are validated by deterministic simulation — thousands of seeded, reproducible concurrent transaction schedules checked against a formal snapshot-isolation anomaly model, plus crash-injection recovery testing. Every failure reproduces exactly from its seed.

Deploy

One image. Run a node — or a cluster.

Single node

One container is a drop-in server with Bolt + REST — it self-elects and accepts writes immediately.

# pull, run, done
docker run -p 7687:7687 patinadb --bootstrap

High availability

Add peers for a quorum — automatic failover and streamed snapshots, no acked write lost on a leader kill.

# grow into a cluster
patinadb --join node-1:8080

Many databases

Isolated graphs on one cluster, each with its own users and roles — created live over Cypher.

# tenant isolation
CREATE DATABASE sales

Get started

Pull the image. Query the past.

Distributed as a container and a static binary — Cypher, Bolt, and the whole timeline, out of the box.

shell
# pull & run a single-node server
docker run -p 7687:7687 -p 8080:8080 \
  patinadb/patinadb --bootstrap

# then point any Neo4j driver at
bolt://localhost:7687
Coming soon