Skip to content

Getting started

Self-hosting

A client installs the product on a server of their own from one release archive, natively or in Docker, and upgrades it from the next one. This guide takes a new server to its first administrator. The archive carries this guide as self-hosting.md.

What you need

  • A server. Ubuntu 24.04 or Debian 12 or newer, amd64 or arm64, with a public IPv4 address. 1 GB of memory serves a small team: the installer adds 2 GB of swap to a machine with less than 2 GB. Recording meetings, on the Docker path only, needs 4 GB.
  • A domain. For example office.example.com, with an A record that points at the server.
  • A license key, bought on the Sharkbyte website.
    • A standard license installs a platform for one organisation.
    • An extended license installs a multi-tenant platform for resale. That needs more: a host for the central admin (such as console.example.com), a domain for tenants' subdomains with a wildcard record (such as *.tenants.example.com), and an OpenID Connect identity provider that operators sign in with.
  • A Mailgun account with a sending domain and an API key. People sign in with links sent by email.
  • The archive for the server's architecture, vws-<version>-linux-<amd64|arm64>.tar.gz, from My orders, with the license key.
PortProtocolFor
22TCPSSH
80, 443TCPthe web pages, the API and certificates
443UDPHTTP/3
7881TCPmedia, where UDP is blocked
50000–60000UDPmedia

The installer opens these ports in ufw. A cloud firewall in front of the server must allow them too.

Installing

Copy the archive to the server and run, as root:

tar -xzf vws-<version>-linux-amd64.tar.gz
cd vws-<version>-linux-amd64
./install.sh native     # or: ./install.sh docker

It asks for the domain, your email address, the license key and the Mailgun details. With an extended license it also asks for the tenant domain, the central admin's host and the identity provider. ./install.sh --help lists the options that answer the questions in advance; with --yes it asks nothing.

NativeDocker
RunsPostgres 18, Redis, LiveKit, Caddy and the server as systemd servicesthe same in containers, from public images, with the server's image built from the archive
PackagesPostgres from the PostgreSQL apt repository, Caddy from Caddy'sDocker from Docker's apt repository, when missing
Recordingsnoon request, with LiveKit's recorder
DataPostgres's directory, /var/lib/vws/var/lib/vws-postgres, /var/lib/vws

Either way, the installer does the same:

  • Secrets. It generates the database passwords, the signing key, the encryption key and LiveKit's key in /etc/vws/secrets, readable by root only. The server's settings in /etc/vws/vws.env, and LiveKit's, are readable by root and the service only; on the Docker path, /etc/vws/docker.env passes the database passwords to Postgres's container and is readable by root only.
  • Caddy. It serves the app and LiveKit, under /livekit, on the domain, and gets the certificate automatically.
  • License. It activates the license key, which the server checks every day (Licensing).
  • Backups. It schedules a daily dump of the database.
  • Command. It installs vws, the server's command line with its settings, for root.
  • Starter room. On a standard license, it offers a starter world and room on the built-in office map, at /office/lobby (yes by default).

The first administrator

  • Standard license. Open https://<domain>, sign in with your email address from the account menu, and run:

    sudo /opt/vws/current/install.sh admin you@example.com

    Reload the page: Administration is in the account menu. From there you invite people, set up worlds, rooms, maps and sign-in providers, and keep the license.

  • Extended license. The installer lets your email address into the central admin. Open https://<console host>/operator, sign in with your identity provider, and create tenants. Caddy gets certificates for tenants' hosts as they are first visited, once the server confirms it serves them.

Upgrading

Copy the next version's archive to the server, extract it, and run, as root:

./install.sh upgrade

The installer keeps the settings, secrets and data, and switches /opt/vws/current to the new version. The server migrates its database when it starts. The previous version stays in /opt/vws/releases.

Backups and restoring

Every day vws-backup.timer dumps the database into /var/backups/vws, keeping the last seven dumps. Copy them off the server, together with /etc/vws and /var/lib/vws (maps, avatars, uploads and recordings).

To restore a dump into a fresh install of the same version, stop the server first:

  • Native.

    systemctl stop vws
    runuser -u postgres -- pg_restore --clean --if-exists -d vws /var/backups/vws/vws-<time>.dump
    systemctl start vws
  • Docker.

    docker compose -f /opt/vws/compose.yaml stop vws
    docker compose -f /opt/vws/compose.yaml exec -T postgres pg_restore --username=postgres --clean --if-exists -d vws < vws-<time>.dump
    docker compose -f /opt/vws/compose.yaml start vws

Restore /etc/vws from the backup too, as its encryption key opens the sealed secrets in the database.

Day to day

TaskNativeDocker
state of the services and the licenseinstall.sh statusinstall.sh status
the server's logjournalctl -u vwsdocker compose -f /opt/vws/compose.yaml logs vws
restartsystemctl restart vwsdocker compose -f /opt/vws/compose.yaml restart vws
the licensevws license status, or Administration, Licensethe same

Settings are in /etc/vws/vws.env (Configuration). After changing them, restart the server.

Found a mistake? Tell us.