Hey HN! I built Velo to solve a problem I kept running into: testing database migrations and debugging production issues without copying around massive database dumps or waiting for slow clones.
The core idea: use ZFS copy-on-write snapshots to branch PostgreSQL databases the way you branch Git repos. A 100GB database branches in ~2 seconds and takes ~100KB of space initially. Each branch is a complete, isolated PostgreSQL instance running in Docker.
How it works:
- Runs CHECKPOINT to flush PostgreSQL buffers (ensures consistency)
- Creates a ZFS snapshot (filesystem-level, instant)
- Clones the snapshot to a new dataset (CoW means no data copying)
- Spins up a new PostgreSQL container pointing at the clone
The mental model is: Project = Git repo, Branch = Git branch. Commands like `velo branch create api/test-migration` or `velo branch reset api/dev`.
I also added point-in-time recovery using WAL archiving, so you can create branches from specific timestamps (e.g., "5 minutes before the incident").
Being able to branch from my db and merge after testing was a killer feature for me in PlanetScale. Great to see this functionality as an open source project.
Hey HN! I built Velo to solve a problem I kept running into: testing database migrations and debugging production issues without copying around massive database dumps or waiting for slow clones.
The core idea: use ZFS copy-on-write snapshots to branch PostgreSQL databases the way you branch Git repos. A 100GB database branches in ~2 seconds and takes ~100KB of space initially. Each branch is a complete, isolated PostgreSQL instance running in Docker.
How it works:
- Runs CHECKPOINT to flush PostgreSQL buffers (ensures consistency)
- Creates a ZFS snapshot (filesystem-level, instant)
- Clones the snapshot to a new dataset (CoW means no data copying)
- Spins up a new PostgreSQL container pointing at the clone
The mental model is: Project = Git repo, Branch = Git branch. Commands like `velo branch create api/test-migration` or `velo branch reset api/dev`.
I also added point-in-time recovery using WAL archiving, so you can create branches from specific timestamps (e.g., "5 minutes before the incident").
Requirements: Linux + ZFS + Docker.
Built using Bun and TypeScript.
Let me know what you think :)
Being able to branch from my db and merge after testing was a killer feature for me in PlanetScale. Great to see this functionality as an open source project.
It's a killer feature indeed. Glad you liked it! :)