Architecture Overview
System Architecture
Section titled “System Architecture”Rebase is a full-stack platform with four layers:
┌─────────────────────────────────────────────────────────────────┐│ Frontend Layer ││ React Admin UI • Custom Views • Plugins • Your App ││ @rebasepro/core • @rebasepro/ui • @rebasepro/studio │└───────────────────────────┬─────────────────────────────────────┘ │ HTTP + WebSocket ▼┌─────────────────────────────────────────────────────────────────┐│ Backend Layer ││ Hono HTTP Server • REST API • Auth • Storage • WS ││ @rebasepro/server-core │└───────────────────────────┬─────────────────────────────────────┘ │ Drizzle ORM ▼┌─────────────────────────────────────────────────────────────────┐│ Database Layer ││ PostgreSQL • Tables • RLS Policies • Realtime sync │└─────────────────────────────────────────────────────────────────┘Key Components
Section titled “Key Components”Database Adapter System
Section titled “Database Adapter System”The backend initializes through a unified database adapter pattern. Database-specific logic is decoupled into its own package, and the adapter handles connection pooling, schema resolution, and real-time event routing automatically.
import { createPostgresAdapter } from "@rebasepro/server-postgresql";
database: createPostgresAdapter({ connectionString: process.env.DATABASE_URL!})Collections automatically resolve against the configured adapter through the internal dependency injection registry.
Collection Registry
Section titled “Collection Registry”The BackendCollectionRegistry is the runtime index of all collections, their PostgreSQL tables, enums, and Drizzle relations. It’s populated at startup from your collection definitions.
Realtime Service
Section titled “Realtime Service”Real-time sync uses PostgreSQL’s native LISTEN/NOTIFY mechanism:
- A data mutation happens (insert, update, delete)
- The backend emits a
NOTIFYon a channel - The
RealtimeServicereceives the notification - It broadcasts the change to all connected WebSocket clients
- React components re-render with the new data
For multi-instance deployments (e.g., Cloud Run with multiple replicas), provide a connectionString in your PostgresBootstrapper so all replicas share the same LISTEN connection.
Storage Registry
Section titled “Storage Registry”Like drivers, storage backends are registered in a registry. You can have multiple storage providers (local, S3) and route different file fields to different backends using storageId.
Package Map
Section titled “Package Map”| Package | Role | Used By |
|---|---|---|
@rebasepro/types | TypeScript interfaces for collections, properties, entities, plugins | Everything |
@rebasepro/backend | Backend server initialization, REST API, auth, storage, WebSocket | Backend |
@rebasepro/client | Client SDK — HTTP transport, WebSocket, auth | Frontend |
@rebasepro/core | React framework — Scaffold, controllers, forms, routes, hooks | Frontend |
@rebasepro/ui | Standalone UI component library (Tailwind v4 + Radix) | Frontend |
@rebasepro/auth | Login views, auth controller hooks, user management | Frontend |
@rebasepro/studio | Collection editor, SQL console, JS console, RLS editor, storage browser | Frontend |
@rebasepro/cli | CLI for schema generation, DB migrations, SDK generation | Dev tooling |
@rebasepro/formex | Lightweight React form state management | Frontend |
@rebasepro/data_enhancement | AI-powered field autocompletion plugin | Frontend |
@rebasepro/data_import_export | CSV/JSON/Excel import and export | Frontend |
@rebasepro/schema_inference | Auto-detect schema from existing database data | Backend/CLI |
Data Flow
Section titled “Data Flow”Read Flow
Section titled “Read Flow”- User opens a collection in the admin UI
- Client SDK sends
GET /api/data/:slug+ opens a WebSocket subscription - Backend queries PostgreSQL via Drizzle ORM
- Data transformer deserializes database records into entity format
- Response sent to frontend, components render
- WebSocket keeps the view synced in real-time
Write Flow
Section titled “Write Flow”- User edits an entity in the form
beforeSavecallbacks run (validation, transformation)- Client SDK sends
PUT /api/data/:slug/:id - Backend serializes values, runs Drizzle
UPDATE afterSavecallbacks run (side effects)NOTIFYbroadcast triggers WebSocket update to all clients- If history is enabled, a snapshot is recorded
Next Steps
Section titled “Next Steps”- Schema as Code — The TypeScript-first approach
- Backend Overview — Server configuration
- Collections — Define your data schema