Backend

Hosted or self-hosted

You can use the hosted primary at fd0.sh or run your own primary. The client command surface is the same.

Hosted

[sync]
server = "https://api.fd0.sh"

fd0.sh stores ciphertext and signed events only. The operator cannot decrypt user secrets.

Self-host

$ mkdir fd0-server
$ cd fd0-server
$ curl -fsSLO https://fd0.sh/files/compose.yml
$ umask 077
$ printf 'METRICS_TOKEN=%s\n' "$(openssl rand -hex 32)" > .env
$ case "$(uname -m)" in arm64|aarch64) printf 'FD0_SERVER_IMAGE=%s\n' 'ghcr.io/valentinkolb/fd0-server:latest-arm64' >> .env ;; esac
$ docker compose up -d

This starts one fd0-server on localhost port 4048. Put your own TLS terminator in front before pointing real clients at it. Use the production hosting runbook for backup, TLS, metrics, witness, and key-rotation details.

Disaster recovery

A standby can mirror the primary with FD0_REPLICATE_FROM. The standby is a recovery source, not a second writable primary.

# standby
FD0_REPLICATE_FROM=https://fd0.example.com
FD0_REPLICATE_INTERVAL=30s

# primary
FD0_PEERS=https://fd0-backup.example.com
The quickstart writes the arm64 image override when it detects an ARM host. For production, pin a released image tag in .env.