Self-Hosting
Run your own portal — prerequisites, environment, database, and starting the apps.
This guide deploys the Customer Portal: the web app (customer UI) and the
api app (all four surfaces). They run as two processes that share one
database and one .env.
Prerequisites
- Node.js 20+ and pnpm 9+
- A Postgres database — a Neon project works out of the box
- A billing provider account (LemonSqueezy by default)
- An email provider key (Resend by default) — optional in dev
1. Install dependencies
Create your env file
Copy the template and fill in values:
At minimum you need DATABASE_URL and BETTER_AUTH_SECRET:
See Environment Variables for the full list, grouped by feature.
2. Set up the database
(Optional) Seed demo data
This creates sample plans and a demo account so you can click around immediately.
3. Start the apps
This starts both apps via Turborepo:
| App | URL | Purpose |
|---|---|---|
| Web | http://localhost:3000 | Customer portal UI + marketing + docs |
| API | http://localhost:3001 | All four API surfaces |
Open the interactive API reference at http://localhost:3001/api/docs.
Run only one pnpm dev at a time. A second instance fights for ports 3000
and 3001 and can leave orphaned processes holding the ports — the most common
cause of "the API won't start." If that happens, see
Troubleshooting.
4. Configure your plugin identity
Edit packages/config/src/plugin.ts so the portal reflects your product:
Then theme it in packages/config/src/branding.ts and define plans in
packages/config/src/pricing.ts.
5. Build for production
Deploy apps/web to any Next.js host (Vercel, a Node server, a container) and
apps/api as a long-running Node process. Point the web app's API_URL at the
deployed API origin.