this repo has no description
1# BSPDS Production Installation on OpenBSD 2 3> **Warning**: These instructions are untested and theoretical, written from the top of Lewis' head. They may contain errors or omissions. This warning will be removed once the guide has been verified. 4 5This guide covers installing BSPDS on OpenBSD 7.8 (current release as of December 2025). 6 7## Prerequisites 8 9- A VPS with at least 2GB RAM and 20GB disk 10- A domain name pointing to your server's IP 11- Root access (or doas configured) 12 13## Why nginx over relayd? 14 15OpenBSD's native `relayd` supports WebSockets but does **not** support HTTP/2. For a modern PDS deployment, we recommend nginx which provides HTTP/2, WebSocket support, and automatic OCSP stapling. 16 17## 1. System Setup 18 19```sh 20pkg_add curl git 21``` 22 23## 2. Install Rust 24 25```sh 26pkg_add rust 27``` 28 29OpenBSD 7.8 ships Rust 1.82+. For the latest stable (1.92+), use rustup: 30 31```sh 32pkg_add rustup 33rustup-init -y 34source ~/.cargo/env 35rustup default stable 36``` 37 38## 3. Install postgres 39 40OpenBSD 7.8 includes PostgreSQL 17 (PostgreSQL 18 may not yet be in ports): 41 42```sh 43pkg_add postgresql-server postgresql-client 44 45mkdir -p /var/postgresql/data 46chown _postgresql:_postgresql /var/postgresql/data 47su - _postgresql -c "initdb -D /var/postgresql/data -U postgres -A scram-sha-256" 48 49rcctl enable postgresql 50rcctl start postgresql 51 52psql -U postgres -c "CREATE USER bspds WITH PASSWORD 'your-secure-password';" 53psql -U postgres -c "CREATE DATABASE pds OWNER bspds;" 54psql -U postgres -c "GRANT ALL PRIVILEGES ON DATABASE pds TO bspds;" 55``` 56 57## 4. Install minio 58 59OpenBSD doesn't have a minio package. Options: 60 61**Option A: Use an external S3-compatible service (recommended for production)** 62 63aws s3, backblaze b2, or upcloud managed object storage. Skip to step 5 and configure the S3 credentials in step 9. 64 65**Option B: Build minio from source** 66 67```sh 68pkg_add go 69 70mkdir -p /tmp/minio-build && cd /tmp/minio-build 71ftp -o minio.tar.gz https://github.com/minio/minio/archive/refs/tags/RELEASE.2025-10-15T17-29-55Z.tar.gz 72tar xzf minio.tar.gz 73cd minio-* 74go build -o minio . 75cp minio /usr/local/bin/ 76 77mkdir -p /var/minio/data 78useradd -d /var/minio -s /sbin/nologin _minio 79chown -R _minio:_minio /var/minio 80 81cat > /etc/minio.conf << 'EOF' 82MINIO_ROOT_USER=minioadmin 83MINIO_ROOT_PASSWORD=your-minio-password 84EOF 85chmod 600 /etc/minio.conf 86 87cat > /etc/rc.d/minio << 'EOF' 88#!/bin/ksh 89 90daemon="/usr/local/bin/minio" 91daemon_user="_minio" 92daemon_flags="server /var/minio/data --console-address :9001" 93 94. /etc/rc.d/rc.subr 95 96rc_pre() { 97 . /etc/minio.conf 98 export MINIO_ROOT_USER MINIO_ROOT_PASSWORD 99} 100 101rc_cmd $1 102EOF 103 104chmod +x /etc/rc.d/minio 105rcctl enable minio 106rcctl start minio 107``` 108 109Create the blob bucket: 110 111```sh 112ftp -o /usr/local/bin/mc https://dl.min.io/client/mc/release/openbsd-amd64/mc 113chmod +x /usr/local/bin/mc 114 115mc alias set local http://localhost:9000 minioadmin your-minio-password 116mc mb local/pds-blobs 117``` 118 119## 5. Install redis 120 121OpenBSD has redis in ports (valkey may not be available yet): 122 123```sh 124pkg_add redis 125 126rcctl enable redis 127rcctl start redis 128``` 129 130## 6. Install deno (for frontend build) 131 132```sh 133curl -fsSL https://deno.land/install.sh | sh 134export PATH="$HOME/.deno/bin:$PATH" 135echo 'export PATH="$HOME/.deno/bin:$PATH"' >> ~/.profile 136``` 137 138## 7. Clone and Build BSPDS 139 140```sh 141mkdir -p /opt && cd /opt 142git clone https://tangled.org/lewis.moe/bspds.git 143cd bspds 144 145cd frontend 146deno task build 147cd .. 148 149cargo build --release 150``` 151 152## 8. Install sqlx-cli and Run Migrations 153 154```sh 155cargo install sqlx-cli --no-default-features --features postgres 156 157export DATABASE_URL="postgres://bspds:your-secure-password@localhost:5432/pds" 158sqlx migrate run 159``` 160 161## 9. Configure BSPDS 162 163```sh 164mkdir -p /etc/bspds 165cp /opt/bspds/.env.example /etc/bspds/bspds.conf 166chmod 600 /etc/bspds/bspds.conf 167``` 168 169Edit `/etc/bspds/bspds.conf` and fill in your values. Generate secrets with: 170 171```sh 172openssl rand -base64 48 173``` 174 175## 10. Create rc.d Service 176 177```sh 178useradd -d /var/empty -s /sbin/nologin _bspds 179 180cp /opt/bspds/target/release/bspds /usr/local/bin/ 181mkdir -p /var/bspds 182cp -r /opt/bspds/frontend/dist /var/bspds/frontend 183chown -R _bspds:_bspds /var/bspds 184 185cat > /etc/rc.d/bspds << 'EOF' 186#!/bin/ksh 187 188daemon="/usr/local/bin/bspds" 189daemon_user="_bspds" 190daemon_logger="daemon.info" 191 192. /etc/rc.d/rc.subr 193 194rc_pre() { 195 export FRONTEND_DIR=/var/bspds/frontend 196 while IFS='=' read -r key value; do 197 case "$key" in 198 \#*|"") continue ;; 199 esac 200 export "$key=$value" 201 done < /etc/bspds/bspds.conf 202} 203 204rc_cmd $1 205EOF 206 207chmod +x /etc/rc.d/bspds 208rcctl enable bspds 209rcctl start bspds 210``` 211 212## 11. Install and Configure nginx 213 214```sh 215pkg_add nginx 216 217cat > /etc/nginx/nginx.conf << 'EOF' 218worker_processes 1; 219 220events { 221 worker_connections 1024; 222} 223 224http { 225 include mime.types; 226 227 server { 228 listen 80; 229 listen [::]:80; 230 server_name pds.example.com; 231 232 location /.well-known/acme-challenge/ { 233 root /var/www/acme; 234 } 235 236 location / { 237 return 301 https://$host$request_uri; 238 } 239 } 240 241 server { 242 listen 443 ssl http2; 243 listen [::]:443 ssl http2; 244 server_name pds.example.com; 245 246 ssl_certificate /etc/ssl/pds.example.com.fullchain.pem; 247 ssl_certificate_key /etc/ssl/private/pds.example.com.key; 248 ssl_protocols TLSv1.2 TLSv1.3; 249 ssl_ciphers HIGH:!aNULL:!MD5; 250 ssl_prefer_server_ciphers on; 251 ssl_session_cache shared:SSL:10m; 252 253 location / { 254 proxy_pass http://127.0.0.1:3000; 255 proxy_http_version 1.1; 256 proxy_set_header Upgrade $http_upgrade; 257 proxy_set_header Connection "upgrade"; 258 proxy_set_header Host $host; 259 proxy_set_header X-Real-IP $remote_addr; 260 proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; 261 proxy_set_header X-Forwarded-Proto $scheme; 262 proxy_read_timeout 86400; 263 } 264 } 265} 266EOF 267 268mkdir -p /var/www/acme 269rcctl enable nginx 270``` 271 272## 12. Obtain SSL Certificate with acme-client 273 274OpenBSD's native acme-client works well: 275 276```sh 277cat >> /etc/acme-client.conf << 'EOF' 278 279authority letsencrypt { 280 api url "https://acme-v02.api.letsencrypt.org/directory" 281 account key "/etc/acme/letsencrypt-privkey.pem" 282} 283 284domain pds.example.com { 285 domain key "/etc/ssl/private/pds.example.com.key" 286 domain full chain certificate "/etc/ssl/pds.example.com.fullchain.pem" 287 sign with letsencrypt 288} 289EOF 290 291mkdir -p /etc/acme 292 293rcctl start nginx 294 295acme-client -v pds.example.com 296 297rcctl restart nginx 298``` 299 300Set up auto-renewal in root's crontab: 301 302```sh 303crontab -e 304``` 305 306Add: 307``` 3080 0 * * * acme-client pds.example.com && rcctl reload nginx 309``` 310 311## 13. Configure Packet Filter (pf) 312 313```sh 314cat >> /etc/pf.conf << 'EOF' 315 316# BSPDS rules 317pass in on egress proto tcp from any to any port { 22, 80, 443 } 318EOF 319 320pfctl -f /etc/pf.conf 321``` 322 323## 14. Verify Installation 324 325```sh 326rcctl check bspds 327ftp -o - https://pds.example.com/xrpc/_health 328ftp -o - https://pds.example.com/.well-known/atproto-did 329``` 330 331## Maintenance 332 333View logs: 334```sh 335tail -f /var/log/daemon 336``` 337 338Update BSPDS: 339```sh 340cd /opt/bspds 341git pull 342cd frontend && deno task build && cd .. 343cargo build --release 344rcctl stop bspds 345cp target/release/bspds /usr/local/bin/ 346cp -r frontend/dist /var/bspds/frontend 347DATABASE_URL="postgres://bspds:your-secure-password@localhost:5432/pds" sqlx migrate run 348rcctl start bspds 349``` 350 351Backup database: 352```sh 353pg_dump -U postgres pds > /var/backups/pds-$(date +%Y%m%d).sql 354```