Postgres
A Fly.Postgres is a Managed Postgres
(MPG) cluster. It is billed. Do not wrap unmanaged fly postgres.
Create the cluster, pass migrations the same way you would on
Neon or PlanetScale, then bind
ConnectPostgres on a
Service. Pass
conn.connectionString to Drizzle.Postgres or SQL.Postgres.
Create a cluster
Section titled “Create a cluster”region is required. The cluster is regional. An
App is global. Alchemy generates a unique name
unless you pass one.
const db = yield* Fly.Postgres("Db", { region: "iad",});Alchemy defaults compute to iad. Pass
another code to put the cluster somewhere else.
Connect from a Service
Section titled “Connect from a Service”Yield ConnectPostgres in Service init. Provide
ConnectPostgresHttp. Pass the connection string to Drizzle or
SQL.
import * as Drizzle from "alchemy/Drizzle/Postgres";import * as HttpServerResponse from "effect/unstable/http/HttpServerResponse";
export default class Api extends Fly.Service<Api>()( "Api", { app: Site, main: import.meta.url, port: 3000 }, Effect.gen(function* () { const conn = yield* Fly.ConnectPostgres(Db); const db = yield* Drizzle.Postgres(conn.connectionString); return { fetch: Effect.gen(function* () { const rows = yield* db.execute("select 1 as ok"); return HttpServerResponse.json({ rows }); }), }; }).pipe(Effect.provide(Fly.ConnectPostgresHttp)),) {}connectionString is the cluster’s pooled PgBouncer URI Output.
directConnectionString is the direct URI. Both come from
Fly.Postgres, packed into the Service env — not Config.redacted.
Migrations
Section titled “Migrations”Pass a directory, { dir, table? }, or a Drizzle.Schema
resource. Alchemy applies pending files on deploy over the direct
URI and records them in __alchemy_migrations.
const schema = yield* Drizzle.Schema("app-schema", { schema: "./src/schema.ts", out: "./migrations",});
const db = yield* Fly.Postgres("Db", { region: "iad", migrations: schema,});const db = yield* Fly.Postgres("Db", { region: "iad", migrations: "./migrations", importFiles: ["./seed.sql"],});MPG is on the org private network. Deploy-time apply needs a route to that network.
plan is the hardware size: basic, starter, launch,
scale, performance. Default is basic.
const db = yield* Fly.Postgres("Db", { region: "iad", plan: "starter",});Volume size
Section titled “Volume size”volumeSizeGb is the initial disk. Fly defaults to 10 GB.
const db = yield* Fly.Postgres("Db", { region: "iad", volumeSizeGb: 20,});PostGIS
Section titled “PostGIS”postgis: true enables PostGIS at create.
const db = yield* Fly.Postgres("Db", { region: "iad", postgis: true,});Where next
Section titled “Where next”Regions lists codes. Default is iad.
Services is the always-on Machine that
binds the cluster.
Drizzle on Postgres is the schema-to-query
flow.
Secrets covers Config.redacted for values
from .env.
The Postgres reference lists every
prop.
The ConnectPostgres reference
is the runtime binding.
Example: fly-postgres
is the complete runnable project.