Deployment
Docker Compose Deployment
Self-hosted deployment with Docker Compose for small teams and on-premises.
Compose Modes
The checked-in compose files now split cleanly into two modes:
docker-compose.yml: stable demo / self-hosted base stack using built containers for the API, worker, sandbox, platform admin app, tenant admin app, and the profile-gated web/docs UIs.docker-compose.dev.yml: opt-in contributor overlay that swaps the API and Next.js surfaces to source-mounted dev servers.
If you want the contributor loop:
bun run compose:dev:up
For deployment-specific customization, use a user-owned override:
cp docker-compose.override.example.yml docker-compose.override.yml
Edit docker-compose.override.yml to:
- Add resource limits
- Configure restart policies
- Pin images, ports, or secrets for your environment
Building Images
# From the repo root (context must be repo root for workspace deps)
docker build -f packages/core/Dockerfile -t orginabox-core:latest .
docker build -f packages/web/Dockerfile -t orginabox-web:latest .
docker build -f packages/platform-web/Dockerfile -t orginabox-platform-web:latest .
docker build -f packages/tenant-web/Dockerfile -t orginabox-tenant-web:latest .
docker build -f packages/docs/Dockerfile -t orginabox-docs:latest .
docker build -f packages/sandbox/Dockerfile -t orginabox/sandbox:latest .
Starting Production Stack
Set OPENCODE_SERVER_PASSWORD first, or run bun orginabox up once so the CLI can auto-provision it into .env.
docker compose \
-f docker-compose.yml \
--profile web \
up -d
Add gateway profiles as needed:
docker compose \
-f docker-compose.yml \
--profile web \
--profile docs \
--profile slack \
--profile teams \
up -d
platform-web and tenant-web are part of the base stack and do not need a separate profile. The public docs UI remains opt-in behind the docs profile.
Backups
Back up the PostgreSQL volume regularly:
docker exec orginabox-postgres \
pg_dump -U orginabox orginabox | gzip > backup-$(date +%Y%m%d).sql.gz
TLS
For HTTPS, put a reverse proxy (nginx, Caddy, Traefik) in front:
server {
listen 443 ssl;
server_name api.yourcompany.com;
location / {
proxy_pass http://localhost:8787;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
}
}
Or use Caddy for automatic TLS:
api.yourcompany.com {
reverse_proxy localhost:8787
}