World's first sealed Postgres
The Cellar
The Cellar is Zipper’s sealed Postgres. Queries arrive as HTTP statements through Zipper A. There is no Postgres wire protocol, no long-lived connection string, and no public :5432. Every client holds a capability seal (role, tables, ops, TTL). Branches are overlay copies — a preview fork writes only the rows that change. Tenant SQL is parsed in Zipper’s dialect and never sent to the host Postgres parser. Default-deny row policies, envelope encryption, and plan row caps are on. It is not Amazon RDS and it is not Neon’s storage split; it is production sealed-query Postgres on two VPS nodes. Included on every Zipper plan.
Cloudflare analogue: Neon / Supabase Postgres
What it is
The Cellar is Zipper’s sealed Postgres. Queries arrive as HTTP statements through Zipper A. There is no Postgres wire protocol, no long-lived connection string, and no public :5432. Every client holds a capability seal (role, tables, ops, TTL). Branches are overlay copies — a preview fork writes only the rows that change. Tenant SQL is parsed in Zipper’s dialect and never sent to the host Postgres parser. Default-deny row policies, envelope encryption, and plan row caps are on. It is not Amazon RDS and it is not Neon’s storage split; it is production sealed-query Postgres on two VPS nodes.
Closest analogue: Neon / Supabase Postgres. SLA 99.95% · p99 35ms. Admins create cellars, branches, and seals. Operators may run select seals.
- ▸World’s first sealed Postgres (no :5432)
- ▸Capability seals, not connection strings
- ▸Overlay branches (copy-on-write rows)
- ▸Tenant SQL never reaches host Postgres
How it works
The Cellar is the world’s first sealed Postgres: there is no public :5432 and no long-lived connection string. Clients present a capability seal (role, tables, ops, TTL). Zipper A parses a restricted SQL dialect and executes it against overlay-addressed rows. Tenant SQL never reaches the host Postgres parser.
Branches are overlays. Forking preview from main copies nothing. Writes on preview create tombstones or row overlays; reads walk preview then main. That is Zipper’s analogue of Neon branching, without a storage-compute split.
Row policies default-deny. Service seals bypass policies the way a service-role key would; anon and authenticated seals must match a published predicate. Envelope encryption (AES-256-GCM) is on by default. Statement time, payload, and plan row caps fail closed.
Use cases
Concrete ways teams use this service on day one.
Replace a connection string
An app today stores DATABASE_URL=postgres://… on a Vercel or Supabase project.
- Dashboard → The Cellar → Open a cellar named app. Copy the bootstrap seal once.
- Ship Authorization: Bearer zc_… (or X-Zipper-Seal) with POST /api/v1/cellar/{id}/query.
- SQL is parameterized. Stacked statements, comments, and pg_catalog identifiers are refused.
Preview data like a git branch
A feature branch should mutate orders without touching production rows.
- POST /api/v1/cellar/{id}/branches with name preview. Only changed rows are stored on the overlay.
- Query with { "sql": "…", "branch": "preview" }.
- Merge by copying overlay rows you want, or drop the branch. Production main is untouched.
Set it up in the dashboard
Dashboard → Services → The Cellar.
Open a cellar, fork overlay branches, mint seals. Run sealed SQL in the console. Copy a seal only once.
Leave require RLS, envelope encryption, fail-closed seals, and overlay branches on.
API
Control-plane: GET|POST /api/v1/cellar · POST /api/v1/cellar/{id}/query · POST /api/v1/cellar/{id}/seals. Send Authorization: Bearer tz_live_YOUR_TOKEN.
Creates count against the plan quota. A 402 plan_limit means you are at the cap — upgrade or delete an unused resource.
Create a cellar
curl -sS -X POST https://tinyzipper.com/api/v1/cellar \
-H "Authorization: Bearer tz_live_YOUR_TOKEN" \
-H "Idempotency-Key: $(uuidgen)" \
-H "Content-Type: application/json" \
-d '{"name":"app","region":"af"}'Sealed query
curl -sS -X POST https://tinyzipper.com/api/v1/cellar/CELLAR_ID/query \
-H "Authorization: Bearer zc_YOUR_SEAL" \
-H "Content-Type: application/json" \
-d '{"sql":"SELECT id, status FROM orders WHERE user_id = $1","params":["user_a"],"branch":"main"}'Public sandbox
const res = await fetch("https://tinyzipper.com/api/v1/cellar/demo", {
method: "POST",
headers: {
Authorization: `Bearer ${process.env.ZIPPER_TOKEN}`,
"Content-Type": "application/json",
"Idempotency-Key": crypto.randomUUID()
},
body: JSON.stringify({ sql: "SELECT id, total FROM orders", branch: "preview" })
});
const json = await res.json();
if (!res.ok) throw new Error(json.error ?? res.statusText);
console.log(json);List the same resource in JavaScript
const res = await fetch("https://tinyzipper.com/api/v1/cellar", {
method: "GET",
headers: {
Authorization: `Bearer ${process.env.ZIPPER_TOKEN}`,
"Content-Type": "application/json"
}
});
const json = await res.json();
if (!res.ok) throw new Error(json.error ?? res.statusText);
console.log(json);Tips
The Cellar is not Amazon RDS and does not speak the Postgres wire protocol. It is Zipper’s sealed-query Postgres on Zipper A.
Never log seal secrets. Rotate by minting a new seal and deleting the old prefix.
Do not send SQL from the browser with a service seal. Use authenticated or anon seals with RLS predicates.
- ▸SOC 2
- ▸AES-256-GCM
- ▸Default-deny RLS
- ▸No :5432
Runbook
Create a cellar, fork overlay branches for previews, mint a service seal, then POST sealed SQL to /api/v1/cellar/{id}/query. Rotate seals by bumping the branch epoch. Pause the service to refuse writes. Tenant SQL never reaches host Postgres.
Next: Honest production · All docs · Create a free account