Two properties that usually exclude each other
Embeddability wants the engine to be your application's address space. Disaggregated storage wants durable state to live over the network so compute is stateless. Twill DB resolves the tension by moving the seam inward.
Truly embeddable
Links in-process as a native library over a frozen C ABI. The hot path is a function call, never a network round-trip — SQLite-style ergonomics, link it anywhere Bun, Node, or C can call.
Storage-disaggregated
Durability bottoms out on object storage (S3 / Cloudflare R2 / MinIO) via an LSM page store and an S3-CAS commit log. Compute holds no durable state, so it is disposable.
One pluggable seam
The engine never touches disk — it talks to a single narrow Storage trait. The backend is chosen by URL scheme: file:// embeds, s3:// disaggregates. No rebuild.
Instant branching
A branch is a cheap LSN pointer over shared immutable layers (copy-on-write). Fork a database in O(1); writes diverge into a private overlay and never touch the base.
Scale-to-zero
The lifecycle controller cold-starts on first connection and tears down when idle. At rest you pay only for object-storage bytes — no idle compute bill.
Postgres-wire compatible
The same engine runs behind a Postgres-wire listener. psql, Bun.sql, pgbench, and PostgREST connect unchanged — no bespoke driver, no bespoke REST layer.
Vector search in-core
A vector(N) type and an HNSW index live behind the same storage seam as the rows — so vector search branches and scales-to-zero with the database. An agent can fork its memory.
Snapshot isolation
MVCC throughout: every reader sees a stable snapshot and never blocks a writer, while a first-committer-wins check keeps concurrent transactions correct. One writer per database, lock-free reads.
Crash-safe durability
Commits are WAL-centric: every acked write is fsync-durable before the call returns — never acked from a buffer. Recovery replays the log deterministically and discards a torn trailing frame.
Open a database with a connection string
Build the native library once, then use the typed Bun wrapper. The backend is selected purely by the URL scheme — flip file:// to s3:// and the same code path becomes disaggregated and scale-to-zero, with no recompile.
Branching is a first-class operation: a branch sees the base's data and writes in isolation.
import { open } from "@twilldb/bun";
using db = open("file://./local.db"); // or "s3://bucket/db"
db.exec(`CREATE TABLE notes (id INTEGER PRIMARY KEY, body TEXT)`);
db.query("INSERT INTO notes VALUES (?, ?)", [1, "hello"]);
const rows = db.query("SELECT id, body FROM notes");
// [{ id: "1", body: "hello" }]
// Instant copy-on-write branch: sees the base, writes in isolation.
using preview = db.branch("preview");
preview.exec("INSERT INTO notes VALUES (2, 'branch-only')");
// the base never sees the branch's write
# The same engine, behind a Postgres-wire listener
cargo run -p twill-server -- \
--listen 127.0.0.1:5433 \
--db file://./srv.db # or s3://bucket/db
# Any Postgres client connects (cleartext):
psql "host=127.0.0.1 port=5433 user=postgres sslmode=disable"
Wrap the library in a wire listener
Server mode is the same library wrapped in a Postgres-wire listener — there is no second engine to maintain. Multi-client access, existing Postgres tooling, and connection pooling all come along for the ride.
Whether a caller reaches the engine through an FFI call or a network socket is the only thing that changes.
Four doors into the project
Use the database, follow the design intent, track what shipped and what's next, or meet the person behind it.
Documentation
User guides: how to connect, branch, pool, and operate the engine. Start here to build something.
Releases & roadmap
What's shipped and what's coming next, plus the status of every design specification — the source of truth for design intent.
Changelog
The human-readable version history — what landed in each release and why it matters, newest first.
The author
Who is building Twill DB and why — the philosophy and the quest behind the project.
"SQLite that forgot where its file was — and found it on S3."
Keep the in-process, link-it-anywhere ergonomics; point the storage backend at the network instead of a local file. Embeddable and disaggregated stop being contradictory the moment the seam is a pluggable backend rather than a server you connect to.
Public & source-available, maintainer-led
Twill DB is an experimental, maintainer-led project. The source is public to read, evaluate, and self-host; issues and feedback are welcome. It is not accepting external pull requests right now — those may be closed without review. It ships under the Business Source License 1.1: self-hosting (including in production) is permitted, but offering Twill DB to others as a hosted or managed database service is not. Each released version converts to the Apache License 2.0 on its Change Date (four years after release).
Analytics & cookies
This site uses Google Analytics 4 to understand which docs and specs are read, so we can improve them. We run Google Consent Mode v2 with every signal defaulting to denied: until you click Accept on the consent banner, no analytics cookie is set and only anonymous, cookieless measurement pings are sent. Accepting enables full analytics storage; declining keeps it cookieless. We request IP anonymisation and never use the data for advertising. Your choice is stored locally in your browser; clearing site data resets it and the banner returns. The engine and your databases are wholly unaffected — this concerns the documentation website only.