From 40f6fd993d3e69d14e0000085929bfe67788a76d Mon Sep 17 00:00:00 2001 From: karti Date: Wed, 12 Aug 2026 20:29:25 -0700 Subject: [PATCH] CI: start Postgres as a step rather than a service container MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The first run got through install, typecheck and all 39 tests, then failed on `getaddrinfo EAI_AGAIN postgres`. This runner does not attach service containers to the job's network, so the `services:` hostname never resolves. Fixed by starting Postgres with `--network container:$HOSTNAME`, sharing the job container's own network namespace so it appears on 127.0.0.1. That works regardless of how the runner is configured — which matters here because the runner is shared with other repositories and should not need reconfiguring to suit this one. Also queries row counts through `docker exec` rather than a local psql, since the runner image is not guaranteed to ship postgresql-client, and removes the container in an `if: always()` step so a failed run does not leave it behind. Co-Authored-By: Claude Opus 5 (1M context) --- .gitea/workflows/ci.yml | 50 ++++++++++++++++++++++++++++------------- 1 file changed, 34 insertions(+), 16 deletions(-) diff --git a/.gitea/workflows/ci.yml b/.gitea/workflows/ci.yml index 909ba11..ccd8d77 100644 --- a/.gitea/workflows/ci.yml +++ b/.gitea/workflows/ci.yml @@ -30,21 +30,17 @@ jobs: verify: runs-on: ubuntu-latest - services: - postgres: - image: postgres:16-alpine - env: - POSTGRES_USER: pig - POSTGRES_PASSWORD: pig - POSTGRES_DB: pig - options: >- - --health-cmd "pg_isready -U pig" - --health-interval 5s - --health-timeout 5s - --health-retries 10 - + # Postgres is started as a step rather than through `services:`. + # + # The runner here does not put service containers on the job's network, so + # `services:` yields "getaddrinfo EAI_AGAIN postgres". Sharing the job + # container's own network namespace (`--network container:$HOSTNAME`) puts + # Postgres on 127.0.0.1 and works regardless of how the runner is + # configured — which matters because this runner is shared with other + # repositories and should not have to be reconfigured to suit this one. env: - DATABASE_URL: postgres://pig:pig@postgres:5432/pig + DATABASE_URL: postgres://pig:pig@127.0.0.1:5432/pig + PG_CONTAINER: pig-ci-pg-${{ github.run_id }} steps: - uses: actions/checkout@v4 @@ -53,6 +49,23 @@ jobs: with: node-version: '22' + - name: Start Postgres + run: | + docker rm -f "$PG_CONTAINER" 2>/dev/null || true + docker run -d --name "$PG_CONTAINER" \ + --network "container:$(cat /etc/hostname)" \ + -e POSTGRES_USER=pig -e POSTGRES_PASSWORD=pig -e POSTGRES_DB=pig \ + postgres:16-alpine + for i in $(seq 1 60); do + if docker exec "$PG_CONTAINER" pg_isready -U pig -q; then + echo "Postgres ready after ${i}s"; exit 0 + fi + sleep 1 + done + echo "Postgres did not become ready" + docker logs "$PG_CONTAINER" | tail -30 + exit 1 + - name: Install run: npm install --no-audit --no-fund @@ -79,9 +92,10 @@ jobs: # pointed at twice, and nobody notices until the counts look odd. run: | npx tsx packages/db/src/seed/index.ts > /dev/null - BEFORE=$(psql "$DATABASE_URL" -tAc "select count(*) from contacts") + count() { docker exec "$PG_CONTAINER" psql -U pig -d pig -tAc "select count(*) from contacts"; } + BEFORE=$(count) npx tsx packages/db/src/seed/index.ts > /dev/null - AFTER=$(psql "$DATABASE_URL" -tAc "select count(*) from contacts") + AFTER=$(count) echo "contacts: $BEFORE -> $AFTER" test "$BEFORE" = "$AFTER" || { echo "SEED IS NOT IDEMPOTENT"; exit 1; } @@ -122,3 +136,7 @@ jobs: - name: Docker image builds run: docker build -t pig:ci . + + - name: Stop Postgres + if: always() + run: docker rm -f "$PG_CONTAINER" 2>/dev/null || true