Skip to content

Self-Hosting

import { Steps } from ‘@astrojs/starlight/components’;

br\u016bhi Cloud is packaged as a single Docker image containing all services. Docker Compose is the recommended deployment method.

  1. Get the source

    Download and extract the brūhi Cloud release package, then navigate to the directory:

    Terminal window
    cd bruhi-cloud
  2. Create your environment file

    Terminal window
    cp .env.example .env

    Edit .env and set at minimum:

    CORS_ORIGINS=https://yourdomain.com
  3. Start

    Terminal window
    docker compose up -d
  4. Verify

    Terminal window
    curl http://localhost:8000/health
    # {"status":"ok"}
VariableDefaultDescription
PORT8000API server port
LOG_LEVELinfoLog verbosity: debug, info, warning, error
CORS_ORIGINS''Space-separated allowed origins for the web dashboard
S3_ENDPOINT_URLS3-compatible endpoint URL (optional)
S3_ACCESS_KEYS3 access key
S3_SECRET_KEYS3 secret key
S3_BUCKETS3 bucket name
S3_REGIONus-east-1S3 region
LIQUIDSOAP_TELNET_HOST127.0.0.1Liquidsoap telnet host
LIQUIDSOAP_TELNET_PORT2000Liquidsoap telnet base port
SMART_PLAYLIST_DB/tmp/bruhi_smart_playlists.dbSmart playlists database path
AUTOMATION_DB/tmp/bruhi_automation.dbAutomation rules database path
OUTPUTS_DB/tmp/bruhi_outputs.dbOutput configurations database path

The default docker-compose.yml:

services:
bruhi:
image: ghcr.io/bruhi/bruhi-cloud:latest
ports:
- "8000:8000" # API + dashboard
- "8005:8005" # Icecast
- "8100:8100" # Station 1 harbor
volumes:
- bruhi_audio:/app/audio_files # Recordings + uploads
- bruhi_playlists:/app/playlists # Liquidsoap playlist files
env_file: .env
healthcheck:
test: ["CMD", "curl", "-f", "http://localhost:8000/health"]
interval: 30s
timeout: 10s
retries: 3
restart: unless-stopped
volumes:
bruhi_audio:
bruhi_playlists:
VolumeMount pathContents
bruhi_audio/app/audio_filesUploaded audio files and WAV recordings
bruhi_playlists/app/playlistsLiquidsoap .m3u8 playlist files (hot-reloaded)

Before exposing br\u016bhi Cloud to the internet:

  • Put br\u016bhi behind a reverse proxy (nginx or Caddy) with TLS
  • Set CORS_ORIGINS to your actual domain (not *)
  • Configure firewall rules: allow ports 80, 443 (HTTPS), 8005 (Icecast), 8100+ (harbors)
  • Set up volume backups for bruhi_audio and bruhi_playlists
  • Set LOG_LEVEL=warning for production (reduces log volume)
  • Configure S3 for media storage if you need persistence beyond the container lifetime
server {
listen 443 ssl;
server_name bruhi.yourdomain.com;
ssl_certificate /etc/ssl/bruhi.crt;
ssl_certificate_key /etc/ssl/bruhi.key;
location / {
proxy_pass http://localhost:8000;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_set_header Host $host;
}
}

The Upgrade and Connection headers are required for WebSocket support (used by the WebRTC signalling connection).

Terminal window
docker compose pull
docker compose up -d

br\u016bhi Cloud follows semantic versioning. Check the release notes before upgrading minor or major versions.

Terminal window
curl -sSL https://bruhi.in/install.sh | bash

The install script will:

  1. Detect your CPU architecture (ARM64 / x86_64)
  2. Verify Docker and Docker Compose are installed
  3. Pull the latest verified image from GHCR
  4. Initialize the config directory at /etc/bruhi/
docker-compose.yml
version: "3.9"
services:
bruhi-engine:
image: ghcr.io/bruhi/engine:latest
ports:
- "8080:8080" # REST API
- "50051:50051" # gRPC
- "9000:9000" # SRT ingest
volumes:
- ./config:/etc/bruhi
- bruhi-data:/var/lib/bruhi
environment:
BRUHI_LOG_LEVEL: info
BRUHI_DB_URL: postgres://bruhi:secret@db:5432/bruhi
depends_on:
- db
- redis
db:
image: postgres:16-alpine
environment:
POSTGRES_USER: bruhi
POSTGRES_PASSWORD: secret
POSTGRES_DB: bruhi
volumes:
- pg-data:/var/lib/postgresql/data
redis:
image: redis:7-alpine
command: redis-server --appendonly yes
volumes:
bruhi-data:
pg-data:
Terminal window
docker compose up -d
ProviderServiceStatus
AWSEC2, ECS, EKS✅ Verified
Google CloudGCE, GKE✅ Verified
DigitalOceanDroplets, K8s✅ Verified
HetznerCloud, Dedicated✅ Community tested