Files
a13labs.infra/.opencode/plans/image-build-push.md
T
alexandre.pires 8724360fb2 Enhance infrastructure and application configurations
- Updated AGENTS.md to include new directories for execution plans and implemented feature reports.
- Modified Ansible host variables for dev-02 and gpu-01 to change API endpoints and add new configurations for Scaleway.
- Adjusted firewall rules in gpu-01 to allow HTTPS traffic instead of the previous Ollama port.
- Added OAuth2 proxy configurations to gpu-01 for enhanced security.
- Removed deprecated open-webui module from Terraform app configurations.
- Updated Terraform configurations to reflect changes in local variables and removed unused secrets.
- Created a new sectool.json file for CloudNS integration with Bitwarden.
- Enhanced SELinux configurations for nginx to allow connections to any port and added oauth2-proxy port.
2026-07-12 16:28:45 -04:00

7.4 KiB

Image Build & Push to Scaleway Registry

Goal

Build runner profile container images from ansible/files/dockerfiles/linux-runners/, scan for vulnerabilities, and push to the Scaleway container registry (a13labs namespace).

Decisions

Decision Choice Rationale
Registry namespace a13labs (existing) Clean project branding
Tagging strategy Git tag + SHA + latest Full traceability and history
Initial scope Runner profiles only (7 → 4) Consolidated image-build, infra-tools, security-scan into cicd-base
Trivy scan severity Warn only Review manually, never block builds
Update consumers Not this iteration Build+push pipeline first, consumers later
Path filtering In-workflow check Gitea paths filter unreliable with tags
PR scanning Disabled Keep PR builds fast

Image Inventory & Dependencies

docker.io/gitea/runner:latest
        ↓
  gitea-runner-base  (build stage 1, pushed first)
        ↓
  ┌─────────────────────────────┐
  │ cicd-base, cpp-build, go-build │ (build stage 2, all parallel)
  └─────────────────────────────┘
Image Dockerfile Base
gitea-runner-base Dockerfile.gitea-runner-base docker.io/gitea/runner:latest
cicd-base Dockerfile.cicd-base local/gitea-runner-base:latest
cpp-build Dockerfile.cpp-build local/gitea-runner-base:latest
go-build Dockerfile.go-build local/gitea-runner-base:latest

Note: image-build, infra-tools, and security-scan runners were decommissioned and their tooling consolidated into cicd-base. All workflows now run on cicd-base or the language-specific runners (cpp-build, go-build).

Registry Naming

Images pushed as fr-par-2.registry.scaleway.com/a13labs/{image-name}:{tag}

Phases

Phase A: Prepare CI Runner (DONE)

Step 1 — Add build tools to Dockerfile.cicd-base

DONE. Added the following packages to the existing cicd-base image:

  • Build packages: buildah, fuse-overlayfs, podman, shadow-uidmap, skopeo, slirp4netns, iptables (from Dockerfile.image-build)
  • Storage config: storage.conf (vfs driver) and containers.conf (from Dockerfile.image-build)
  • Trivy binary download (from Dockerfile.security-scan, v0.72.0)

Step 2 — Register updated cicd-base on Gitea runner (DONE)

cicd-base image rebuilt on ci-01 and Gitea runner container registration updated.

Phase B: Scaleway IaC Changes (DONE - code changes, manual apply needed)

Step 3 — Add CI IAM app (terraform/iac/scaleway/iam.tf) - DONE

  • New scaleway_iam_application "ci_app" with RegistryFullAccess permission set
  • New scaleway_iam_policy "registry_full_access" granting ci_app registry access
  • New scaleway_iam_api_key "ci_app_api" for ci_app credentials

Step 4 — Add registry outputs (terraform/iac/scaleway/outputs.tf) - DONE

  • registry_endpoint — from scaleway_registry_namespace.a13labs.endpoint
  • ci_app_api_access_key, ci_app_api_secret_key — sensitive

Step 5 — No sectool.env changes needed - DONE The CI app resources are hardcoded, no TF_VAR mappings required.

Step 6 — Apply and extract secrets (MANUAL)

  • Add SCALEWAY_CI_ACCESS_KEY and SCALEWAY_CI_SECRET_KEY to Bitwarden
  • Run sectool exec tofu apply in terraform/iac/scaleway/
  • Add SCALEWAY_REGISTRY_ENDPOINT, SCALEWAY_CI_ACCESS_KEY, SCALEWAY_CI_SECRET_KEY as Gitea repo secrets

Phase C: Gitea Actions & Workflow (DONE)

Step 7 — Create .gitea/actions/setup-scaleway-registry/action.yml - DONE Composite action that:

  • Creates ~/.docker/config.json with Scaleway registry auth
  • Configures buildah storage and network settings for rootless operation
  • Inputs: registry-endpoint, registry-username, registry-password

Step 8 — Create .gitea/workflows/build-and-push-images.yml - DONE

Jobs:

  • check-paths: Determines if dockerfiles changed (handles push, PR, tag events)
  • auth: Sets up registry authentication (gates on path check)
  • build-base: Builds and pushes gitea-runner-base
  • build-images: Matrix build of 6 dependent images

Tagging strategy:

  • Push to main: {sha} + latest
  • Push tag (v*): {tag} + {sha} + latest
  • PR: pr-{number} (no scanning)

Step 9 — Create .gitea/workflows/weekly-image-rebuild.yml - DONE Scheduled weekly (cron: "0 6 * * 1" — Monday 6AM):

  • Same build jobs but only tag :latest
  • Uses --pull-always to force rebuild against updated upstream base images
  • Full Trivy scan (warn only, artifacts)

Build Order & Dependency Resolution

Each dependent Dockerfile says FROM local/gitea-runner-base:latest. The workflow replaces local/gitea-runner-base with the full registry URL in a temp copy before building, so buildah pulls the freshly pushed base image.

Manual Setup Checklist

Before the workflows can run successfully, complete these steps:

  • Push code changes to repo (note: registry.tf changed is_public from false to true on a13labs namespace)
  • SSH to ci-01, rebuild cicd-base image locally, update Gitea runner container — DONE
  • Add SCALEWAY_CI_ACCESS_KEY and SCALEWAY_CI_SECRET_KEY to Bitwarden (leave blank initially, they'll be populated after IaC apply)
  • Apply Scaleway IaC: sectool exec tofu apply in terraform/iac/scaleway/
  • From IaC outputs, extract registry_endpoint, ci_app_api_access_key, ci_app_api_secret_key
  • Add as Gitea repo secrets: SCALEWAY_REGISTRY_ENDPOINT, SCALEWAY_CI_ACCESS_KEY, SCALEWAY_CI_SECRET_KEY
  • Push a test commit touching ansible/files/dockerfiles/linux-runners/ to trigger workflow
  • Verify workflow runs and images appear in Scaleway registry

Gitea Secrets Required

Secret Source Used by
SCALEWAY_REGISTRY_ENDPOINT IaC output registry_endpoint build-and-push, weekly-rebuild
SCALEWAY_CI_ACCESS_KEY IaC output ci_app_api_access_key build-and-push, weekly-rebuild
SCALEWAY_CI_SECRET_KEY IaC output ci_app_api_secret_key build-and-push, weekly-rebuild

File Summary

Action File Status
Modify ansible/files/dockerfiles/linux-runners/Dockerfile.cicd-base DONE
Modify terraform/iac/scaleway/iam.tf DONE
Modify terraform/iac/scaleway/outputs.tf DONE
Modify terraform/iac/scaleway/sectool.env DONE
Create .gitea/actions/setup-scaleway-registry/action.yml DONE
Create .gitea/workflows/build-and-push-images.yml DONE
Create .gitea/workflows/weekly-image-rebuild.yml DONE

Post-Iteration (NOT now)

  • Update runner Dockerfiles to use registry base URLs
  • Update Ansible playbooks to pull from registry instead of build
  • Add PR close job to clean up pr-{number} tags from registry
  • Expand to AI service Dockerfiles (comfyui, ollama, llamacpp variants)

Consolidation

image-build, infra-tools, and security-scan runner profiles have been decommissioned. Their tooling was already absorbed into cicd-base:

  • image-build tools (buildah, podman, storage config) → merged into Dockerfile.cicd-base
  • security-scan tools (trivy) → merged into Dockerfile.cicd-base
  • infra-tools tools (ansible, pip packages) → installed at workflow runtime via requirements/ansible.txt

Unused Dockerfiles removed: Dockerfile.image-build, Dockerfile.infra-tools, Dockerfile.security-scan