All checks were successful
Podman Rootless Demo / test-backend (push) Has been skipped
Podman Rootless Demo / test-frontend (push) Has been skipped
Podman Rootless Demo / build-backend (push) Has been skipped
Podman Rootless Demo / build-frontend (push) Has been skipped
Podman Rootless Demo / deploy-prod (push) Successful in 48s
269 lines
No EOL
9.1 KiB
YAML
269 lines
No EOL
9.1 KiB
YAML
name: Podman Rootless Demo
|
||
on: [push, pull_request]
|
||
|
||
jobs:
|
||
test-backend:
|
||
runs-on: [ci]
|
||
if: false
|
||
|
||
# Point all steps at the host's rootless Podman socket
|
||
env:
|
||
# Point the client at the mounted socket
|
||
CONTAINER_HOST: unix:///run/user/1001/podman/podman.sock
|
||
# Make sure podman looks in the correct runtime dir hierarchy
|
||
XDG_RUNTIME_DIR: /tmp
|
||
RUN_ID: ${{ github.run_id }}
|
||
POSTGRES_IMG_DIGEST: ${{ secrets.POSTGRES_IMG_DIGEST }}
|
||
RUST_IMG_DIGEST: ${{ secrets.RUST_IMG_DIGEST }}
|
||
PREBUILT_BACKEND_TEST_IMAGE: ${{ secrets.REGISTRY_HOST }}/${{ github.repository }}/sharenet-test-rust
|
||
CACHE_REPO: ${{ secrets.REGISTRY_HOST }}/${{ github.repository }}/sharenet-test-rust-cache
|
||
|
||
steps:
|
||
- name: Checkout code
|
||
uses: actions/checkout@v4
|
||
|
||
|
||
- name: Verify socket visibility
|
||
run: |
|
||
set -euo pipefail
|
||
id -u; id -g
|
||
ls -ld /run/user/1001/podman
|
||
ls -l /run/user/1001/podman/podman.sock
|
||
test -S /run/user/1001/podman/podman.sock
|
||
|
||
- name: Use host rootless Podman
|
||
run: |
|
||
set -euo pipefail
|
||
podman --remote info --format '{{.Host.RemoteSocket.Path}} (remote={{.Host.RemoteSocket.Exists}})'
|
||
podman --remote version
|
||
podman --remote run --rm alpine:3.20 echo "Hello from host rootless Podman!"
|
||
|
||
- name: Login to container registry with PAT
|
||
run: |
|
||
echo "${{ secrets.REGISTRY_TOKEN }}" | podman --remote login \
|
||
-u "${{ secrets.REGISTRY_USERNAME }}" \
|
||
--password-stdin \
|
||
"${{ secrets.REGISTRY_HOST }}"
|
||
|
||
- name: Create network
|
||
run: podman --remote network create integ-${{ env.RUN_ID }}
|
||
|
||
- name: Generate cache key from lockfile
|
||
id: cache-key
|
||
run: |
|
||
cd "$GITHUB_WORKSPACE/backend"
|
||
LOCK_HASH=$(sha256sum Cargo.lock | cut -d' ' -f1)
|
||
SHORT_HASH=$(echo "$LOCK_HASH" | cut -c1-12)
|
||
echo "cache_key=$SHORT_HASH" >> $GITHUB_OUTPUT
|
||
echo "Using cache key: $SHORT_HASH"
|
||
|
||
- name: Build dependencies cache image
|
||
run: |
|
||
# Build deps stage with layer caching
|
||
podman --remote build \
|
||
--layers \
|
||
--cache-to "$CACHE_REPO" \
|
||
--cache-from "$CACHE_REPO" \
|
||
--target deps \
|
||
-f Dockerfile.test-rust \
|
||
-t "$PREBUILT_BACKEND_TEST_IMAGE:deps-${{ steps.cache-key.outputs.cache_key }}" \
|
||
backend
|
||
|
||
podman --remote push \
|
||
"$PREBUILT_BACKEND_TEST_IMAGE:deps-${{ steps.cache-key.outputs.cache_key }}"
|
||
|
||
- name: Build full test image with cached dependencies
|
||
run: |
|
||
# Build final image using cached deps
|
||
podman --remote build \
|
||
--layers \
|
||
--cache-from "$CACHE_REPO" \
|
||
--target runner \
|
||
-f Dockerfile.test-rust \
|
||
-t "$PREBUILT_BACKEND_TEST_IMAGE:test-${{ github.sha }}" \
|
||
backend
|
||
|
||
- name: Start PostgreSQL
|
||
run: |
|
||
podman --remote run -d \
|
||
--name test-postgres-${{ env.RUN_ID }} \
|
||
--network integ-${{ env.RUN_ID }} \
|
||
-e POSTGRES_PASSWORD=password \
|
||
-e POSTGRES_USER=postgres \
|
||
-e POSTGRES_DB=sharenet_test \
|
||
"$POSTGRES_IMG_DIGEST"
|
||
|
||
- name: Wait for PostgreSQL
|
||
run: |
|
||
timeout 60 bash -euc '
|
||
until podman --remote exec test-postgres-${{ env.RUN_ID }} \
|
||
pg_isready -h 127.0.0.1 -p 5432 -U postgres; do
|
||
sleep 1
|
||
done
|
||
'
|
||
|
||
- name: Ensure host Cargo cache directory exists
|
||
run: |
|
||
podman --remote run --rm \
|
||
-v /home/ci-service/.cache:/c \
|
||
alpine:3.20 sh -lc 'mkdir -p /c/cargo'
|
||
|
||
- name: Run backend tests
|
||
run: |
|
||
# Run tests in the pre-built test image
|
||
podman --remote run --rm \
|
||
--network integ-${{ env.RUN_ID }} \
|
||
-e DATABASE_URL=postgres://postgres:password@test-postgres-${{ env.RUN_ID }}:5432/sharenet_test \
|
||
"$PREBUILT_BACKEND_TEST_IMAGE:test-${{ github.sha }}"
|
||
|
||
- name: Cleanup
|
||
if: always()
|
||
run: |
|
||
podman --remote rm -f test-postgres-${{ env.RUN_ID }} 2>/dev/null || true
|
||
podman --remote network rm integ-${{ env.RUN_ID }} 2>/dev/null || true
|
||
|
||
- name: Debug DB (on failure)
|
||
if: failure()
|
||
run: podman --remote logs --tail=200 test-postgres-${{ env.RUN_ID }} || true
|
||
|
||
test-frontend:
|
||
runs-on: [ci]
|
||
if: false
|
||
#needs: test-backend
|
||
|
||
steps:
|
||
- name: Checkout code
|
||
uses: actions/checkout@v4
|
||
|
||
- name: Pass-through (no frontend tests yet)
|
||
run: echo "Frontend tests placeholder - no tests implemented yet"
|
||
|
||
build-backend:
|
||
runs-on: [ci]
|
||
if: false
|
||
#needs: [test-backend, test-frontend]
|
||
needs: [test-frontend]
|
||
|
||
env:
|
||
CONTAINER_HOST: unix:///run/user/1001/podman/podman.sock
|
||
XDG_RUNTIME_DIR: /tmp
|
||
RUN_ID: ${{ github.run_id }}
|
||
BACKEND_IMAGE: ${{ secrets.REGISTRY_HOST }}/${{ github.repository }}/sharenet-backend-api-postgres
|
||
|
||
steps:
|
||
- name: Checkout code
|
||
uses: actions/checkout@v4
|
||
|
||
- name: Login to container registry with PAT
|
||
run: |
|
||
echo "${{ secrets.REGISTRY_TOKEN }}" | podman --remote login \
|
||
-u "${{ secrets.REGISTRY_USERNAME }}" \
|
||
--password-stdin \
|
||
"${{ secrets.REGISTRY_HOST }}"
|
||
|
||
- name: Build backend container image
|
||
run: |
|
||
podman --remote build \
|
||
-f backend/Dockerfile \
|
||
-t "$BACKEND_IMAGE:${{ github.sha }}" \
|
||
-t "$BACKEND_IMAGE:latest" \
|
||
backend
|
||
|
||
- name: Push backend container image
|
||
run: |
|
||
podman --remote push "$BACKEND_IMAGE:${{ github.sha }}"
|
||
podman --remote push "$BACKEND_IMAGE:latest"
|
||
|
||
build-frontend:
|
||
runs-on: [ci]
|
||
if: false
|
||
#needs: [test-backend, test-frontend]
|
||
needs: [test-frontend]
|
||
|
||
env:
|
||
CONTAINER_HOST: unix:///run/user/1001/podman/podman.sock
|
||
XDG_RUNTIME_DIR: /tmp
|
||
RUN_ID: ${{ github.run_id }}
|
||
FRONTEND_IMAGE: ${{ secrets.REGISTRY_HOST }}/${{ github.repository }}/sharenet-frontend
|
||
|
||
steps:
|
||
- name: Checkout code
|
||
uses: actions/checkout@v4
|
||
|
||
- name: Login to container registry with PAT
|
||
run: |
|
||
echo "${{ secrets.REGISTRY_TOKEN }}" | podman --remote login \
|
||
-u "${{ secrets.REGISTRY_USERNAME }}" \
|
||
--password-stdin \
|
||
"${{ secrets.REGISTRY_HOST }}"
|
||
|
||
- name: Build frontend container image
|
||
run: |
|
||
podman --remote build \
|
||
-f frontend/Dockerfile \
|
||
-t "$FRONTEND_IMAGE:${{ github.sha }}" \
|
||
-t "$FRONTEND_IMAGE:latest" \
|
||
frontend
|
||
|
||
- name: Push frontend container image
|
||
run: |
|
||
podman --remote push "$FRONTEND_IMAGE:${{ github.sha }}"
|
||
podman --remote push "$FRONTEND_IMAGE:latest"
|
||
|
||
deploy-prod:
|
||
runs-on: [prod]
|
||
#needs: [build-backend, build-frontend]
|
||
|
||
env:
|
||
CONTAINER_HOST: unix:///run/user/1001/podman/podman.sock
|
||
XDG_RUNTIME_DIR: /tmp
|
||
RUN_ID: ${{ github.run_id }}
|
||
APP_NAME: ${{ github.repository }}
|
||
REGISTRY_HOST: ${{ secrets.REGISTRY_HOST }}
|
||
IMAGE_TAG: latest
|
||
POSTGRES_DATABASE_NAME: ${{ secrets.PROD_DB_DATABASE_NAME }}
|
||
POSTGRES_USERNAME: ${{ secrets.PROD_DB_USERNAME }}
|
||
POSTGRES_PASSWORD: ${{ secrets.PROD_DB_PASSWORD }}
|
||
POSTGRES_PORT: ${{ secrets.PROD_DB_PORT }}
|
||
PROD_BACKEND_PORT: ${{ secrets.PROD_BACKEND_PORT }}
|
||
PROD_FRONTEND_PORT: ${{ secrets.PROD_FRONTEND_PORT }}
|
||
PROD_BACKEND_HOST: ${{ secrets.PROD_BACKEND_HOST }}
|
||
|
||
steps:
|
||
- name: Checkout code
|
||
uses: actions/checkout@v4
|
||
|
||
- name: Login to container registry with PAT
|
||
run: |
|
||
echo "${{ secrets.REGISTRY_TOKEN }}" | podman --remote login \
|
||
-u "${{ secrets.REGISTRY_USERNAME }}" \
|
||
--password-stdin \
|
||
"${{ secrets.REGISTRY_HOST }}"
|
||
|
||
- name: Pull production images
|
||
run: |
|
||
podman --remote pull "$REGISTRY_HOST/$APP_NAME/sharenet-backend-api-postgres:$IMAGE_TAG"
|
||
podman --remote pull "$REGISTRY_HOST/$APP_NAME/sharenet-frontend:$IMAGE_TAG"
|
||
|
||
- name: Render nginx.conf and put on host (no unshare)
|
||
run: |
|
||
set -euo pipefail
|
||
apk add --no-cache gettext >/dev/null # envsubst
|
||
# Render template locally in the job container
|
||
envsubst < nginx/nginx.conf > /tmp/nginx.conf
|
||
|
||
# Write it to the host via a remote Podman helper container.
|
||
# Run as uid:gid 1001:1001 so writes match prod-service’s ownership.
|
||
podman --remote run --rm -i \
|
||
--userns=keep-id \
|
||
-v /opt/sharenet/nginx:/host-nginx:rw \
|
||
alpine:3.20 sh -c 'install -D -m 0644 /dev/stdin /host-nginx/nginx.conf' \
|
||
< /tmp/nginx.conf
|
||
|
||
- name: Install envsubst (Alpine)
|
||
run: apk add --no-cache gettext
|
||
|
||
- name: Deploy production pod
|
||
run: |
|
||
# Process the pod template with environment variables
|
||
envsubst < deploy/prod-pod.yml | podman --remote kube play - |