Run CIHub with Docker
Run CIHub, its Postgres and an HTTPS proxy on one machine with Docker Compose, then update it.
One machine with Docker runs the whole instance: Postgres, a one-shot service that applies the migrations, CIHub, and Caddy, which gets a TLS certificate for your address.
You need:
- A machine with Docker and Docker Compose, which GitHub can reach on the ports 80 and 443.
- A DNS name that points to it, for example
cihub.example.com. - The App of your CIHub and its keys: Create the GitHub App.
Write the files
In a new directory, write four files.
compose.yaml:
services:
postgres:
image: postgres:17
restart: unless-stopped
environment:
POSTGRES_PASSWORD: ${POSTGRES_PASSWORD}
CIHUB_DATABASE_PASSWORD: ${CIHUB_DATABASE_PASSWORD}
volumes:
- postgres:/var/lib/postgresql/data
- ./create-cihub-database.sh:/docker-entrypoint-initdb.d/create-cihub-database.sh:ro
healthcheck:
test: ["CMD", "pg_isready", "-U", "postgres"]
interval: 5s
migrate:
image: ghcr.io/getcihub/server:0.2
command: ["migrate", "up"]
environment:
CIHUB_DATABASE_URL: postgres://cihub:${CIHUB_DATABASE_PASSWORD}@postgres:5432/cihub
depends_on:
postgres:
condition: service_healthy
cihub:
image: ghcr.io/getcihub/server:0.2
restart: unless-stopped
environment:
CIHUB_DATABASE_URL: postgres://cihub:${CIHUB_DATABASE_PASSWORD}@postgres:5432/cihub
CIHUB_DATABASE_SECRET: ${CIHUB_DATABASE_SECRET}
CIHUB_HTTP_PUBLIC_URL: https://${CIHUB_HOST}
CIHUB_GITHUB_APP_ID: ${CIHUB_GITHUB_APP_ID}
CIHUB_GITHUB_PRIVATE_KEY_FILE: /run/secrets/github-app
CIHUB_GITHUB_WEBHOOK_SECRET: ${CIHUB_GITHUB_WEBHOOK_SECRET}
CIHUB_GITHUB_CLIENT_ID: ${CIHUB_GITHUB_CLIENT_ID}
CIHUB_GITHUB_CLIENT_SECRET: ${CIHUB_GITHUB_CLIENT_SECRET}
secrets:
- github-app
depends_on:
migrate:
condition: service_completed_successfully
caddy:
image: caddy:2
restart: unless-stopped
command: caddy reverse-proxy --from ${CIHUB_HOST} --to cihub:8080
ports:
- "80:80"
- "443:443"
volumes:
- caddy:/data
depends_on:
- cihub
secrets:
github-app:
file: ./github-app.private-key.pem
volumes:
postgres:
caddy:create-cihub-database.sh, which Postgres runs once, at its first start. CIHub refuses to connect as a
superuser: it gets its own role, which owns its database.
#!/bin/sh
set -e
psql -v ON_ERROR_STOP=1 --username postgres <<SQL
CREATE ROLE cihub LOGIN PASSWORD '${CIHUB_DATABASE_PASSWORD}';
CREATE DATABASE cihub OWNER cihub;
SQL.env, with your address, the passwords and the sealing key, generated once, then the keys of the
GitHub App:
cat > .env <<EOF
CIHUB_HOST=cihub.example.com
POSTGRES_PASSWORD=$(openssl rand -hex 16)
CIHUB_DATABASE_PASSWORD=$(openssl rand -hex 16)
CIHUB_DATABASE_SECRET=$(openssl rand -hex 32)
CIHUB_GITHUB_APP_ID=<App ID>
CIHUB_GITHUB_WEBHOOK_SECRET=<webhook secret>
CIHUB_GITHUB_CLIENT_ID=<Client ID>
CIHUB_GITHUB_CLIENT_SECRET=<client secret>
EOF
chmod 600 .envgithub-app.private-key.pem: the private key of the App, which GitHub downloaded, under this name. The container
reads it as the user 65532:
chmod +x create-cihub-database.sh
chmod 644 github-app.private-key.pemStart CIHub
docker compose up -d
docker compose psmigrate ends with the exit code 0, then cihub starts. Open https://cihub.example.com: the dashboard asks you to
sign in with GitHub.
The .env file and the private key are secrets: keep them out of a repository, and back them up with the volume
postgres. A lost CIHUB_DATABASE_SECRET signs every person out; the queues keep their data.
Create an API token
Once the App is installed on your organization, a script or a CI that calls the API needs a token of the organization. The command prints it once:
docker compose run --rm cihub token create --org <login of the organization>Update CIHub
Change the tag of the two image: lines (0.2 follows the fixes of the version 0.2), then:
docker compose pull
docker compose up -dmigrate applies the migrations of the new version before cihub starts again.
Go back to an older version
When the older version has fewer migrations, the running version reverts its own first. --to takes the newest
migration of the older version: the last file of migrations/ in its tag.
docker compose run --rm cihub migrate down --to <version>Then put the older tag back on the two image: lines and run docker compose up -d. The data of the reverted
migrations is lost.
Without Caddy
If the machine already has a proxy or a load balancer that terminates TLS, remove the service caddy, publish the
port of CIHub to that proxy, and route your address to it:
cihub:
ports:
- "127.0.0.1:8080:8080"The proxy sends every path to CIHub: the dashboard, /api, /auth and /webhooks/github.
Next
Install the App on your repositories, then merge your first pull request.
Create the GitHub App
Create the GitHub App of your CIHub instance, give its keys to CIHub, install it on your repositories, and check that GitHub reaches the instance.
Run CIHub on Kubernetes
Install CIHub on a Kubernetes cluster with its Helm chart, get a Postgres for it (CloudNativePG, a managed service or your own server), expose it, and update it.