Skip to content

Backend Overview

The Rebase backend is a Node.js server built on Hono that provides:

  • REST API — Auto-generated CRUD endpoints for each collection
  • Authentication — JWT tokens, Google OAuth, user/role management
  • Storage — File upload/download with local filesystem or S3
  • WebSocket — Real-time data sync via PostgreSQL LISTEN/NOTIFY
  • Entity History — Audit trail for every data change
  • Database Branching — Instant, isolated database copies for dev/staging/testing
  • Cron Jobs — Scheduled background tasks with monitoring dashboard

Everything is initialized with a single function:

import { initializeRebaseBackend } from "@rebasepro/server-core";
import { createPostgresAdapter } from "@rebasepro/server-postgresql";
import { env } from "./env";
const instance = await initializeRebaseBackend({
app,
server,
collectionsDir: "./config/collections",
database: createPostgresAdapter({
connection: db,
schema: { tables, enums, relations }
}),
auth: {
jwtSecret: env.JWT_SECRET,
},
storage: { type: "local", basePath: "./uploads" },
history: true,
enableSwagger: env.NODE_ENV !== "production"
});

After initialization, these routes are mounted:

PathPurpose
/api/auth/*Authentication (signup, login, refresh, Google OAuth)
/api/admin/*User and role management (admin-only)
/api/storage/*File upload, download, and deletion
/api/data/collectionsCollection metadata endpoint
/api/data/:slugCRUD operations per collection (GET, POST, PUT, DELETE)
/api/data/:slug/:id/historyEntity change history (when enabled)
/api/data/docsOpenAPI spec (when enableSwagger: true)
/api/data/swaggerSwagger UI (dev mode, when enableSwagger: true)
/api/functions/*Custom function routes (when functionsDir is set)
/api/cron/*Cron job management (admin-only, when cronsDir is set)
WebSocket on upgradeReal-time subscriptions
interface RebaseBackendConfig {
// HTTP framework
app: Hono; // Hono application instance
server: Server; // Node.js HTTP server (for WebSocket attachment)
basePath?: string; // Route prefix (default: "/api")
// Collections
collections?: EntityCollection[]; // Your collection definitions
collectionsDir?: string; // Auto-load collections from a directory
// Database adapter (PostgreSQL, SQLite, etc.)
database?: DatabaseAdapter;
// Authentication configuration or custom adapter
auth?: RebaseAuthConfig | AuthAdapter;
// File storage
storage?: BackendStorageConfig | Record<string, BackendStorageConfig>;
// Entity history
history?: boolean | HistoryConfig;
// OpenAPI/Swagger
enableSwagger?: boolean;
// Custom API endpoints
functionsDir?: string; // Auto-load Hono routes from a directory
// Scheduled tasks
cronsDir?: string; // Auto-load cron jobs from a directory
// Logging
logging?: { level?: "error" | "warn" | "info" | "debug" };
}

initializeRebaseBackend returns a RebaseBackendInstance with access to internal services:

const instance = await initializeRebaseBackend(config);
// Internal service access
instance.driver // Default data driver
instance.driverRegistry // All drivers (for multi-database)
instance.realtimeService // Default realtime service
instance.userService // User management
instance.roleService // Role management
instance.storageController // Default storage
instance.storageRegistry // All storage backends
instance.collectionRegistry // Collection metadata
instance.historyService // Entity history
instance.cronScheduler // Cron job scheduler (when cronsDir is set)

Note: While the instance exposes these internal services, application code (such as custom functions and cron jobs) should use the global rebase singleton from @rebasepro/server-core to interact with the backend API.

The REST API is auto-generated from your collections. Every collection gets these endpoints:

MethodPathDescription
GET/api/data/:slugList entities (with filter, sort, limit, search)
GET/api/data/:slug/:idGet a single entity
POST/api/data/:slugCreate a new entity
PUT/api/data/:slug/:idUpdate an entity
DELETE/api/data/:slug/:idDelete an entity
ParamDescriptionExample
filterJSON-encoded filter conditions?filter={"active":["==",true]}
orderBySort field?orderBy=created_at
orderSort direction?order=desc
limitPage size?limit=25
startAfterCursor for pagination?startAfter=encodedCursor
searchFull-text search?search=laptop

The WebSocket server attaches to the same HTTP server and provides real-time subscriptions:

  • Subscribe to collection changes — get notified when any entity in a collection is created, updated, or deleted
  • Subscribe to entity changes — get notified when a specific entity changes
  • Automatic reconnection handling in the client SDK

The backend uses PostgreSQL LISTEN/NOTIFY internally. For multi-instance deployments, provide a connectionString in your PostgresBootstrapper to enable cross-instance broadcasting.

The backend includes an error handler that catches all exceptions and returns structured error responses:

{
"error": {
"message": "Entity not found",
"code": "not-found",
"status": 404
}
}

If initialization fails (e.g., database connection error), the server still starts but returns 503 for all API requests, with a descriptive error message in the logs.