Search docsComing soon

Self-host deployment

This guide walks through the recommended run order for a community deployment: Postgres → control-plane → relay-manager → WebUI → relay-daemon.

Prerequisites

  • Docker + Docker Compose
  • Go 1.22+
  • Yarn
  • WireGuard tooling (wg, wg-quick) on Linux hosts

1) Postgres (Docker)

Use the bundled Compose file to start Postgres locally.

docker compose -f deploy/docker-compose.yml up -d db

Default credentials (update in deploy/docker-compose.yml if needed):

  • POSTGRES_DB=nanami
  • POSTGRES_USER=nanami
  • POSTGRES_PASSWORD=nanami

2) Control-plane (Go)

export DATABASE_URL=postgres://nanami:nanami@localhost:5432/nanami?sslmode=disable
export JWT_SECRET=change_me
export APP_ENV=dev
export APP_MODE=community

go run ./apps/control-plane/cmd

The API starts on http://localhost:8080.

3) Relay-manager (Go)

Create a join key with scope relay_manager in the WebUI or via API, then run:

export CONTROL_PLANE_URL=http://localhost:8080
export JOIN_KEY=your_join_key
export TENANT_SLUG=your-tenant-slug
export NODE_JOIN_KEY=node-secret-key

go run ./apps/relay-manager/cmd

The manager listens on http://localhost:8081 and expects relay-daemons to use the same NODE_JOIN_KEY.

4) WebUI (Next.js)

cd apps/webui
yarn install
CONTROL_PLANE_URL=http://localhost:8080 yarn dev

Open http://localhost:3000 and complete bootstrap (create the first admin).

5) Relay-daemon (Docker, Linux, macOS)

Docker (recommended for dev)

Build and run the relay-daemon container (requires NET_ADMIN):

docker compose -f deploy/docker-compose.yml --profile relay up -d relay-daemon

Required env vars (see compose file):

  • CONTROL_PLANE_URL and RELAY_DAEMON_JOIN_KEY (registration)
  • RELAY_MANAGER_URL and NODE_JOIN_KEY (heartbeat to relay-manager)
  • NODE_ENDPOINT (optional public endpoint for WG)

Linux (host)

export RELAY_MANAGER_URL=http://localhost:8081
export NODE_JOIN_KEY=node-secret-key
export CONTROL_PLANE_URL=http://localhost:8080
export RELAY_DAEMON_JOIN_KEY=your_relay_join_key
export NODE_ENDPOINT=public-ip:51820

go run ./apps/relay/cmd/relay-daemon

macOS (observed-state only)

macOS runtime reports observed-state but WireGuard apply is pending:

export RELAY_MANAGER_URL=http://localhost:8081
export NODE_JOIN_KEY=node-secret-key
export CONTROL_PLANE_URL=http://localhost:8080
export RELAY_DAEMON_JOIN_KEY=your_relay_join_key

go run ./apps/relay/cmd/relay-daemon

Known limitations

  • macOS/Windows WG runtime is pending (status shows "WG runtime pending").
  • Relay-daemon in Docker requires host WireGuard support.
  • External endpoints behind NAT must be configured manually.