Platform overview
Saaslivery is one product made of many small apps. A workspace installs the apps it needs, every member works inside a single tabbed shell at {workspace}.saaslivery.com, and the apps cooperate through events rather than shared tables. This page is the map; each section links to the full spec.
Core ideas
Apps are plugins. Every app, first-party or third-party, is a Heaven plugin that the platform discovers and mounts at startup. It brings its own routes, templates, migrations, and manifest; it inherits auth, sessions, tenancy, permissions, and asset serving. See What is an app?
One origin per workspace. All app UI runs under {workspace}.saaslivery.com/app/{slug}/ inside the shell. The API lives on api.saaslivery.com. See Architecture & routing.
Workspace isolation is absolute. Every query, event, file, and WebSocket message is scoped to a workspace_id the platform sets before app code runs. See Multi-tenancy.
Five security layers. Authentication, workspace membership, platform role, app access, and app permissions. Apps declare permissions and authz rules; the platform enforces them. See Security & permissions.
Events, not queries. Apps never read each other's tables. They emit events and build local read models from other apps' events, with real-time push to connected browsers. See Event system.
A marketplace with real economics. Workspace admins install apps from the marketplace; third-party developers publish through GitHub review and keep 80% of their app's revenue. See Pricing & billing.
Architecture at a glance
┌──────────────────────────────────────────────────────────┐
│ Event Bus │
│ core.* events · ext.* events · system.* │
├────────────┬────────────┬────────────┬───────────────────┤
│ Tasks │ CRM │ Files │ Your App │
│ /app/tasks │ /app/crm │ /app/files │ /app/{slug}/ │
├────────────┴────────────┴────────────┴───────────────────┤
│ {workspace}.saaslivery.com (shell + tabs) │
│ api.saaslivery.com (all JSON APIs) │
├───────────────────────────────────────────────────────────┤
│ Heaven framework │
│ subdomain routing · middleware · sessions · WebSockets │
├───────────────────────────────────────────────────────────┤
│ Platform layer │
│ auth · tenancy · permissions · billing · marketplace │
└───────────────────────────────────────────────────────────┘
Tech stack
| Layer | Technology | Role |
|---|---|---|
| Backend | Heaven | Async Python ASGI framework: routing, middleware, sessions, WebSockets |
| Templating | Jinja2 | Server-rendered HTML via res.render() |
| Interactivity | HTMX | Fragment loading for a SPA feel, no client router |
| Client logic | Alpine.js | Declarative, minimal, client-side-only state |
| Validation | pytastic | TypedDict schemas with Annotated constraints |
| Styling | Bootstrap 5 + platform design system | No build step |
| Real time | WebSockets + PostgreSQL LISTEN/NOTIFY | Live UI updates across workers |
Reading order
If you are new, read What is an app?, then Architecture & routing, then Multi-tenancy. After that, build something with Your first app and come back to Events when your app needs to talk to another one.