Local development with the Supabase CLI

Run the full Supabase stack on your machine with the Supabase CLI and develop against it, then ship to SupaHost. Which CLI commands work, which don't, and how to set up a project.

The Supabase CLI runs a complete Supabase stack in Docker on your machine: Postgres, Auth, the Data API, Storage, Realtime, Edge Functions and Studio. Developing against it is fast, free and safe, and everything you build there runs on SupaHost because SupaHost runs the same open-source stack.

What doesn't carry over is the CLI's connection to the hosted platform. Commands such as supabase link, supabase db push to a linked project and supabase functions deploy talk to Supabase's Management API, which SupaHost doesn't provide. You develop locally with the CLI, then ship to SupaHost through the MCP server, Studio or (on Business) the SSH tunnel.

What works and what doesn't

Command With SupaHost
supabase init, start, stop, status Works (local)
supabase migration new, migration list (local) Works
supabase db diff, db reset, db lint Works (local)
supabase gen types against the local database Works
supabase test db Works (local)
supabase functions new, functions serve Works (local)
supabase link Doesn't work
supabase db push / db pull to a linked project Doesn't work
supabase functions deploy, secrets set, config push Doesn't work
supabase gen types with a project ref Doesn't work

On Business and Enterprise, database commands that accept a Postgres URL can reach your project through the SSH tunnel; see Migrations workflow. For the full list, see Supabase CLI commands that don't work with SupaHost.

Install the CLI and Docker

You need Docker Desktop (or another Docker-compatible runtime) running. Then install the CLI, for example as a dev dependency so everyone on the project uses the same version:

npm install supabase --save-dev
npx supabase --version

It's also available through Homebrew (brew install supabase/tap/supabase) and Scoop on Windows.

The CLI is at version 3. Version 3 runs database commands against the local stack by default; version 2 needed --local on some of them. The commands on this page work on both unless noted.

Set up a project

In your app's repository:

npx supabase init

This creates a supabase/ folder with config.toml, a migrations/ folder and a place for functions and seed data. Commit it.

SupaHost runs Postgres 17, so make sure the local database matches:

# supabase/config.toml
[db]
major_version = 17

Start the stack:

npx supabase start

The first start downloads the images and takes a few minutes. When it's done, the CLI prints your local URLs and keys:

Service Default local address
API (Auth, REST, Storage, Functions) http://127.0.0.1:54321
Postgres postgresql://postgres:[email protected]:54322/postgres
Studio http://127.0.0.1:54323
Email testing inbox http://127.0.0.1:54324

Run npx supabase status any time to see them again, and npx supabase stop when you're done.

Point your app at the local stack

Use one set of environment variables for local work and another for SupaHost. For a Next.js app:

# .env.development.local
NEXT_PUBLIC_SUPABASE_URL=http://127.0.0.1:54321
NEXT_PUBLIC_SUPABASE_ANON_KEY=<anon key printed by supabase start>
# Production env vars on your host
NEXT_PUBLIC_SUPABASE_URL=https://app-one.acme.supahost.space
NEXT_PUBLIC_SUPABASE_ANON_KEY=<anon key from the Connect tab>

Your code doesn't change between the two. Sign-up emails sent locally land in the email testing inbox instead of a real mailbox.

Develop the schema locally

Create a migration, write SQL, and apply it to your local database:

npx supabase migration new create_bookings
-- supabase/migrations/20261111093000_create_bookings.sql
create table public.bookings (
  id bigint generated always as identity primary key,
  guest_id uuid not null references auth.users (id) default auth.uid(),
  room text not null,
  starts_at timestamptz not null,
  nights int not null check (nights > 0)
);

alter table public.bookings enable row level security;

create policy "Guests see their own bookings"
  on public.bookings for select
  to authenticated
  using ((select auth.uid()) = guest_id);
npx supabase db reset   # rebuilds the local DB from all migrations and the seed file

Prefer clicking in local Studio? Make the change there, then capture it as a migration file:

npx supabase db diff -f add_room_index

Generate types

npx supabase gen types typescript > src/database.types.ts

On CLI version 2, add --local. You can also generate types from a SupaHost project with the MCP tool generate_typescript_types. See Generating TypeScript types.

Edge Functions locally

supabase functions new and supabase functions serve run functions on your machine against the local stack. To put a function on SupaHost, deploy it from the project's Functions tab (paste the files into the editor and click Deploy function) or ask an AI agent to deploy it over MCP. Keep the entry file named index.ts. See Deploying functions.

Settings that live outside migrations

config.toml controls local Auth settings, but the CLI can't push it to SupaHost. Set the real values on your project's Auth tab: Site URL, Redirect URLs, providers and sign-in options. Function secrets go on the Functions tab.

Next steps

Updated 11 November 2026 · View as Markdown · Something wrong or missing? Tell us