Skip to content

Run locally ​

You need Node.js 18+ and pnpm 10.25+. npm and yarn are deliberately blocked by a preinstall check, so stick with pnpm.

First run ​

From the repository root:

bash
cp .env.example .env
pnpm install

Bring up Postgres and Redis (realtime pushes need both), then migrate and start the platform:

bash
docker compose --project-directory . \
  -f docker/compose/docker-compose.dev.yml \
  up -d postgres redis
pnpm --filter @repo/db migrate
pnpm dev

pnpm dev starts the platform apps through Turborepo, including the default workers process (realtime outbox worker on port 8792). Docs are separate — run pnpm docs:dev when you need the VitePress site on port 3003. Live server setup, host nginx, certificates, and release runbooks are documented under Production and Monitoring.

Ensure .env has DATABASE_URL and REDIS_URL (see Environment variables). Without Redis, the API still boots but WebSocket realtime pushes will not work.

If you only need one surface, run it on its own:

bash
pnpm --filter web dev      # player site, port 3000
pnpm --filter admin dev    # admin panel, port 3001
pnpm --filter support dev  # support desk, port 3002
pnpm --filter api dev      # Hono API, port 8787
pnpm --filter workers dev  # realtime outbox worker, port 8792

Opt-in workers (analytics, notifier, customerio) stay on their own scripts — see environments.

Database ​

The platform expects PostgreSQL. Point DATABASE_URL at your instance in .env, then apply the schema:

bash
pnpm --filter @repo/db migrate

This creates (among other things) the private_state_* tables and realtime_event_outbox used by the realtime worker. Migrations 0086 (support_operator_users_fk) and 0087 (realtime_event_outbox) are required for support WebSocket events. Most migrations are generated from the Drizzle schema, but a few under packages/db/drizzle/ are hand-written SQL. If you change packages/db/src/schema, regenerate and review the diff with pnpm --filter @repo/db generate.

Redis and realtime worker ​

Redis backs one-time WebSocket tickets and cross-instance pub/sub for all private realtime topics (wallet balance, support, withdrawal, notification inbox). Local default:

bash
docker compose --project-directory . \
  -f docker/compose/docker-compose.dev.yml \
  up -d redis

Set REDIS_URL=redis://127.0.0.1:6379 (or your compose password URL). The realtime worker is the workers package default (pnpm --filter workers dev / included in pnpm dev) and listens on port 8792. See Realtime messaging for architecture and verification (pnpm test:realtime-e2e).

Signing in to the admin panel ​

The admin panel only lets through users with an admin session, and the seeded superadmin role bypasses every permission check. Use a seeded or manually promoted admin account for your environment. If you are exploring a specific area, the access model lists which permission each page needs.

Payments in development ​

Crypto deposits go through CryptoCloud and fiat through Payou. Both rely on keys in .env and on webhooks that need a publicly reachable HTTPS URL, so end-to-end payment flows usually require a tunnel (or a staging environment) rather than plain localhost. Everything else — accounts, the lobby, segments, promotions — runs fine locally.

Handy commands ​

bash
pnpm lint           # ESLint across the workspace
pnpm check-types    # TypeScript across the workspace
pnpm test           # Vitest across workspace packages
pnpm docs:dev       # these docs, on port 3003
pnpm docs:build     # static build of these docs