Deployment guide

Rybbit

Overview

Rybbit is an open-source, privacy-friendly web and product analytics platform and a self-hostable alternative to Google Analytics and Plausible. A single lightweight script on your pages tracks page visits, unique visitors, referrers, countries, devices and real-time users. You can also send your own custom events with structured properties. Rybbit is cookie-free, so it tracks visitors without cookie banners.

This image runs Rybbit 2.7.0 on Ubuntu 24.04 LTS as a Docker Compose stack managed by systemd. A Next.js dashboard (the client) and a Fastify API (the backend, which handles event ingestion, statistics and authentication) sit on top of ClickHouse for events, PostgreSQL for accounts, organizations and sites, and Redis for sessions and queues. A host nginx serves the dashboard over HTTPS on port 443 and keeps a health endpoint and the event ingestion path on port 80. The datastores stay on the internal Compose network and are never exposed.

What you get:

  • Rybbit 2.7.0 self-host stack pinned by exact image digest, run under Docker Compose via a rybbit.service systemd unit
  • The dashboard served over HTTPS on :443 with a per-VM self-signed certificate generated on first boot
  • A single administrator account whose password is generated on first boot and recorded in a root-only file, with public sign-up disabled afterwards
  • Every secret (PostgreSQL, ClickHouse and Redis passwords and the BETTER_AUTH_SECRET) generated fresh per VM on first boot, so no upstream example secret survives into the image
  • A database bound to the instance only (the upstream compose file publishes PostgreSQL to the network, and this image does not), and product telemetry turned off
  • An unauthenticated /healthz endpoint on port 80 for Azure Load Balancer health probes
  • 24/7 SecureAnyCloud support

Prerequisites

  • An Azure subscription and the Azure CLI (or the Azure Portal)
  • An SSH key pair
  • Inbound TCP 443 (dashboard), TCP 80 (HTTPS redirect and event ingestion) and TCP 22 (SSH) open to the addresses you use

Step 1 - Deploy from the Azure Marketplace

In the Azure Marketplace, find Rybbit Analytics on Ubuntu 24.04 LTS by SecureAnyCloud and click Create. Choose a Standard_B2s (or larger) size, provide your SSH public key, and allow inbound ports 443, 80 and 22. Create the VM and note its public IP address.

Step 2 - Deploy from the Azure CLI

To launch from the CLI instead, accept the image terms once per subscription, open the ports, and create the VM:

az vm image terms accept --urn sac1647283583153:rybbit-ubuntu-24-04:default:latest
az network nsg rule create --resource-group myResourceGroup --nsg-name myNsg \
  --name allow-rybbit --priority 1010 \
  --destination-port-ranges 443 80 22 --access Allow --protocol Tcp --direction Inbound
az vm create \
  --resource-group myResourceGroup \
  --name rybbit-vm \
  --image sac1647283583153:rybbit-ubuntu-24-04:default:latest \
  --size Standard_B2s \
  --admin-username azureuser \
  --generate-ssh-keys \
  --public-ip-sku Standard

Step 3 - Connect to your VM

Connect over SSH:

ssh azureuser@<public-ip>

The first boot initialises the stack. It generates every secret and the admin password, creates the administrator account, and generates a self-signed TLS certificate for this VM. This takes two to three minutes.

Step 4 - Confirm the services are running

Check the systemd units and the Docker Compose stack:

sudo systemctl is-active docker nginx rybbit rybbit-firstboot
sudo docker compose -f /opt/rybbit/docker-compose.yml ps --format 'table {{.Service}}\t{{.Status}}'

Every service reports active, and each container reports Up.

Step 5 - Retrieve your admin password

The first boot generates the administrator password and writes it to a root-only file. Read the file:

sudo cat /root/rybbit-credentials.txt

Note the RYBBIT_ADMIN_EMAIL, the RYBBIT_ADMIN_PASSWORD and the console URL.

Step 6 - Confirm the health endpoint and versions

Run the following to probe the health endpoint, the backend and the dashboard, and to print the datastore versions:

curl -sI http://127.0.0.1/healthz | head -1
curl -s -o /dev/null -w 'backend HTTP %{http_code}\n' http://127.0.0.1:3001/api/health
curl -sk -o /dev/null -w 'dashboard HTTP %{http_code}\n' https://127.0.0.1/
sudo docker exec rybbit-clickhouse clickhouse-server --version | head -1 sudo docker exec rybbit-postgres postgres --version

The health probe returns 200, the backend and dashboard both answer, and the datastore versions print.

Step 7 - Review the security posture

The image is secure by default. Public sign-up is disabled after the admin account is created, telemetry is off, the datastores are not exposed to the network, and the dashboard has a per-VM TLS certificate. Run the following to check each setting:

grep -E '^DISABLE_SIGNUP|^DISABLE_TELEMETRY' /opt/rybbit/.env
sudo ss -tlnp | grep -E ':(5432|8123|6379) ' || echo 'ClickHouse, PostgreSQL and Redis are NOT exposed to the host'
sudo openssl x509 -noout -subject -ext subjectAltName -in /etc/nginx/ssl/rybbit.crt | head -3

Step 8 - Sign in to the dashboard

Browse to https://<public-ip>/ and sign in with the admin email and password from Step 5.

The dashboard uses a self-signed certificate, so your browser shows a one-time "not secure" warning. Click Advanced, then Proceed. For production, see Step 13.

Step 9 - Open your dashboard

After you sign in, you land on your organization's site list. Public sign-up is disabled, so only your administrator account exists.

Step 10 - Add your first site

Click Add Site, enter your website's domain and a name, and save. Rybbit assigns the site a numeric site ID and shows a tracking snippet. Add the snippet to the <head> of every page you want to track:

<script src="https://<public-ip>/api/script.js" data-site-id="YOUR_SITE_ID" async ></script>

For server-side and API tracking, send events to POST /api/track with a site_id. A real browser's headers (Accept-Language, Accept, sec-fetch-*) distinguish genuine visits from bots, which Rybbit records in a separate bots view.

Step 11 - View your analytics

Open your site from the dashboard to see live analytics. The top of the page shows unique users, sessions, pageviews, bounce rate and session duration. Below it are a time series chart and breakdowns of referrers, pages, countries and devices. Data appears within seconds of an event arriving.

Step 12 - Organization settings and API keys

Open Settings -> Organization to rename the organization, manage members, and create API keys. Use API keys for the Stats API, to read your analytics programmatically, and for server-side event tracking.

Step 13 - Production: assign a domain and a trusted certificate

The self-signed certificate lets you sign in immediately, but browsers do not load the tracking script from a self-signed origin on your production sites. For production:

  • Point a DNS name (for example analytics.example.com) at this VM's public IP.
  • Install a trusted certificate (for example with Let's Encrypt) and set BASE_URL=https://analytics.example.com in /opt/rybbit/.env. Then run sudo docker compose -f /opt/rybbit/docker-compose.yml up -d to apply it.

Your tracking snippet then references your domain and loads cleanly on any HTTPS site.

Maintenance

  • Manage the stack: sudo systemctl restart rybbit restarts the whole stack. sudo docker compose -f /opt/rybbit/docker-compose.yml logs -f backend tails the API logs.
  • Data: ClickHouse holds analytics events, and PostgreSQL holds accounts, organizations and sites. Both use Docker named volumes on the OS disk.
  • Security updates: unattended security upgrades are enabled for the base OS.

Support

This image is maintained by SecureAnyCloud with 24/7 support. If you need help, contact us at secureanycloud.com.

Deploy on Azure

Launch Rybbit Analytics on Ubuntu 24.04 LTS on Azure with 24/7 support from SecureAnyCloud.

View this image

Need Help?

Our support team is available 24/7.

sales@secureanycloud.com

Deploy on Azure