Skip to content

Local Supabase

Local Supabase stack for Treeper dev. Runs Postgres, GoTrue (auth), Storage, Realtime, and Studio in Docker via the Supabase CLI.

  • Docker engine running (Docker Desktop or colima — see colima note below)
  • Supabase CLI: brew install supabase/tap/supabase

Supabase CLI probes /var/run/docker.sock directly even when DOCKER_HOST is exported. On colima the socket lives at ~/.colima/default/docker.sock, so symlink it once:

Terminal window
sudo ./scripts/colima-docker-sock.sh

The script refuses to clobber an existing non-symlink at /var/run/docker.sock (so Docker Desktop installs are safe). The link survives reboots and is shared by every project on this machine.

Why ports 55321–55329 (not the default 54321)?

Section titled “Why ports 55321–55329 (not the default 54321)?”

Supabase CLI defaults every project to host ports 54321–54329, so two local stacks collide on the host even though their Docker containers are namespaced by project_id. This project uses +1000 offsets so it can run alongside another local Supabase stack:

ServiceDefaultTreeper
API (GoTrue + REST + Storage)5432155321
Postgres5432255322
Studio5432355323
Inbucket5432455324
Analytics5432755327
DB pooler5432955329

Ports are pinned in config.toml. To run a third stack, copy that pattern (another offset) in that project’s config.toml.

Terminal window
cd infra
supabase start # first run pulls ~3GB of images, takes 5–15 min
supabase status # prints URLs and keys
supabase stop # halts containers, keeps data
supabase stop --no-backup # halts and wipes the local DB volume

After start, you’ll see output like:

API URL: http://127.0.0.1:55321
GraphQL URL: http://127.0.0.1:55321/graphql/v1
DB URL: postgresql://postgres:[email protected]:55322/postgres
Studio URL: http://127.0.0.1:55323
Inbucket URL: http://127.0.0.1:55324 (catches all auth emails)
anon key: eyJhbGciOi...
service_role: eyJhbGciOi...

Use the API URL as SUPABASE_URL and the anon key as SUPABASE_ANON_KEY when running the mobile app:

Terminal window
cd ../apps/mobile
fvm flutter run \
--dart-define=SUPABASE_URL=http://127.0.0.1:55321 \
--dart-define=SUPABASE_ANON_KEY=<paste anon key from supabase status>

iOS simulator and Android emulator can both reach 127.0.0.1 on the host — the simulator shares the host loopback. If you run on a physical device, replace 127.0.0.1 with your Mac’s LAN IP and ensure the firewall allows port 55321.

Auth confirmation emails go to Inbucket at http://127.0.0.1:55324 — open it to grab confirmation links / OTP codes during dev.

Terminal window
supabase migration new <name> # creates supabase/migrations/<ts>_<name>.sql
supabase db reset # rebuilds local DB from migrations + seed.sql
supabase db diff -f <name> # captures Studio-made changes as a migration

Migrations are committed; the running container is ephemeral.

Terminal window
supabase link --project-ref <ref>
supabase db push # apply local migrations to the hosted DB