Supabase foundations
Understand the Supabase platform
See Supabase as PostgreSQL plus Auth, APIs, Storage, Realtime, Functions, and operational services rather than a new database engine.
9 minute lesson
Supabase is a hosted platform built around one idea: every Supabase project contains a full PostgreSQL database. Not a compatible clone, not a proprietary store behind an API — actual Postgres you can reach with any Postgres client.
You can prove that in one command:
psql "postgresql://postgres:[email protected]:5432/postgres" \
-c "select version();"
# PostgreSQL 15.8 on aarch64-unknown-linux-gnu ...
Around that database, Supabase adds the services most applications need anyway: generated data APIs, authentication, object storage, realtime services, functions, pooling, backups, and a dashboard. Each one saves you from running a separate piece of infrastructure.
How a request actually flows
The piece that confuses beginners most is the Data API. When you write this:
import { createClient } from '@supabase/supabase-js'
const supabase = createClient(
'https://abcdefghijkl.supabase.co',
'sb_publishable_x3PLxbGmiQ04GJ5uOOZBww_T5xRcLhV'
)
const { data, error } = await supabase.from('notes').select()
no application server of yours is involved. The request hits Supabase’s API gateway, which translates it into SQL and runs it against your Postgres database. Supabase Auth is the layer that authenticates: it checks the user’s token and attaches their identity. PostgreSQL is the layer that authorizes: Row Level Security policies decide which rows that identity may see.
Draw that path once on paper — browser, Auth, Data API, Postgres — and mark the two jobs. Authentication happens before the database. Authorization happens inside it.
It is still Postgres
SQL, constraints, indexes, transactions, roles, and query plans still matter. The platform removes setup work; it does not remove database design or authorization decisions.
The classic first-week surprise makes the point. You enable Row Level Security on a table, write no policies, and every select starts returning an empty array — no error, just data: []. Nothing is broken and nothing is lost. Postgres is doing exactly what you told it: no policy allows any rows. The fix is a policy, and writing one is a database skill, not a platform setting.
Treat Supabase as Postgres with the boring parts handled, and everything you know about relational databases keeps paying off.
Lesson completed