Local quick start

Prerequisites: Docker.

git clone https://github.com/lbrty/observer.git
cd observer
cp .env.example .env
just generate-keys
just docker-up
just run

Open http://localhost:9000/health in your browser. If you see "status":"healthy", the backend is running.

Then start the web interface:

just web-dev

Open http://localhost:5173.

What you just started

You now have a backend on :9000, a frontend on :5173, and a Postgres + Redis pair in Docker — all on a single machine.

Production deployment

For production, you need:

WhatWhy
A server (VPS or on-premise)Observer is self-hosted — your data never leaves your infrastructure
PostgreSQLThe only external service Observer needs
About 30 minutesRun docker compose up on a server with your domain pointed at it

See Deployment for the step-by-step production setup.

For developers: local setup

If you want to work on Observer itself, you’ll need these tools installed:

ToolVersionInstall
Go1.25.*https://go.dev/dl/
Bunlatesthttps://bun.sh/
Docker + Composelatesthttps://docs.docker.com/get-docker/
Justlatesthttps://github.com/casey/just#installation

1. Clone and install dependencies

git clone https://github.com/lbrty/observer.git
cd observer
go mod download
bun install

2. Configure environment

cp .env.example .env

The defaults work out of the box with the provided docker-compose.yml.

3. Generate signing keys

just generate-keys

This creates a key pair that Observer uses to sign login tokens.

4. Start everything

just docker-up    # starts PostgreSQL and Redis
just run          # starts the backend on :9000 (runs migrations automatically)
just web-dev      # starts the frontend on :5173

Something not working?

Port 5432 already in use — You probably have a local PostgreSQL running. Stop it, or change the port in docker-compose.yml.

“no such file or directory” for key paths — You need to run just generate-keys first.

Migration fails with “connection refused” — The database container might not be ready yet. Wait a few seconds after just docker-up and try again.