DEV Community

ANKUSH CHOUDHARY JOHAL
ANKUSH CHOUDHARY JOHAL

Posted on • Originally published at johal.in

Architecture Teardown: How Supabase's Real-Time Database Uses PostgreSQL 17 and WebSockets

Architecture Teardown: How Supabase's Real-Time Database Uses PostgreSQL 17 and WebSockets

Supabase's real-time database is one of its most popular features, enabling developers to subscribe to database changes (inserts, updates, deletes) and receive low-latency updates via WebSockets. Under the hood, this system leans heavily on PostgreSQL 17's native capabilities and a purpose-built WebSocket layer to deliver scalable, reliable real-time sync. This teardown breaks down how the pieces fit together.

Core Components of the Real-Time Stack

The real-time system has three primary components:

  • PostgreSQL 17 Database: The source of truth for all data, with native logical replication and WAL (Write-Ahead Log) support.
  • Supabase Realtime Server: A dedicated Elixir-based service that listens to Postgres changes and manages WebSocket connections with clients.
  • Client SDKs: Lightweight libraries for JavaScript, Dart, Swift, and other languages that handle WebSocket connections and parse incoming change events.

PostgreSQL 17's Critical Role

PostgreSQL 17 provides the foundation for change capture, with several features that make Supabase's real-time implementation efficient:

  • Logical Replication: Supabase creates a dedicated logical replication slot for the Realtime server, which streams WAL changes in real time. Unlike physical replication, logical replication allows filtering by table, schema, and even row-level changes, reducing unnecessary data transfer.
  • Improved WAL Decoding: PostgreSQL 17 optimizes logical decoding for high-throughput workloads, reducing latency between a write operation and change availability to subscribers. It also adds better support for streaming large transactions, avoiding batch delays for bulk writes.
  • Native JSONB Output: Decoded WAL changes are formatted as JSONB by default in PG17, eliminating the need for custom serialization logic in the Realtime server.
  • Row-Level Security (RLS) Integration: Postgres RLS policies are enforced at the database layer, so the Realtime server only receives changes that clients are authorized to see, reducing the need for application-layer authorization checks.

The WebSocket Layer

The Supabase Realtime server is built in Elixir, leveraging the Erlang VM's (BEAM) lightweight process model to handle thousands of concurrent WebSocket connections per node. Key features of this layer include:

  • Connection Management: Each client WebSocket connection is handled by a dedicated BEAM process, with minimal overhead. The server supports automatic reconnection, heartbeat pings to detect dead connections, and rate limiting to prevent abuse.
  • Subscription Filtering: Clients subscribe to specific tables, schemas, or even filtered queries (e.g., "all changes to users where id = auth.uid()"). The Realtime server maps these subscriptions to the logical replication stream, only forwarding relevant changes to each client.
  • Message Format: Changes are sent as structured JSON payloads with event type (INSERT, UPDATE, DELETE), table metadata, old record (for updates/deletes), and new record (for inserts/updates). The format is consistent across all client SDKs.

End-to-End Data Flow

Here's how a single database change propagates to a client:

  1. A client executes an INSERT, UPDATE, or DELETE query against the PostgreSQL 17 database.
  2. Postgres writes the change to its WAL, then applies it to the table (if using synchronous replication, but typically async for real-time).
  3. The logical replication slot decodes the WAL entry into a JSONB change event, using PG17's native decoding plugins.
  4. The Supabase Realtime server, subscribed to the replication slot, receives the change event.
  5. The Realtime server checks active client subscriptions, filters the change against RLS policies and client-specified query filters.
  6. The filtered change is pushed to all matching client WebSocket connections.
  7. The client SDK parses the JSON payload and triggers user-defined callback functions for the relevant event.

Scalability and Reliability

Supabase's architecture scales horizontally for both Postgres and the Realtime layer:

  • PostgreSQL 17 supports read replicas, which can offload logical replication traffic from the primary write instance.
  • The Realtime server can be deployed as a cluster behind a load balancer, with subscription state shared via a distributed cache (like Redis) to handle connection draining and failover.
  • PostgreSQL 17's replication slots are persistent, so if the Realtime server restarts, it picks up exactly where it left off, avoiding missed or duplicate changes.

Conclusion

Supabase's real-time database is a masterclass in leveraging existing database native features (PostgreSQL 17's logical replication) and purpose-built networking (WebSockets) to deliver a developer-friendly real-time sync solution. By pushing change capture to the database layer and using Elixir's BEAM for connection handling, the system achieves low latency and high scalability without reinventing the wheel. For developers building collaborative apps, live dashboards, or chat features, this architecture provides a reliable, low-overhead foundation.

Top comments (0)