The runner's job images were built by ansible into localhost/ only, so the nightly CI prune deleted them and every idle stretch ended with CI failing in under a second on `docker pull localhost/gitea-ci:latest` until someone re-ran the role and waited out a rebuild. The previous commit moved them to the Gitea registry; this moves the *build* off the deploy path entirely. - .gitea/workflows/ci-images.yml builds files/Containerfile.* and pushes to git.debyl.io/gitbot/. Per-image change detection, so an ESP-IDF pin bump does not rebuild the other two; weekly schedule for base-image updates; a workflow_dispatch selector. PRs build under a throwaway :pr-<n> tag and drop it -- the build lands in the live runner's store, and act_runner will not re-pull a tag it already has, so a PR using the real tag would hand every later job on this host an unmerged image. - The Containerfiles stop being ansible templates: their version vars are now --build-arg, read by the workflow out of the same defaults/main.yml the role interpolates, so CI and ansible build the same bytes from one set of pins. - LABEL io.debyl.ci-base moves into each Containerfile so neither builder can forget the prune exemption; the workflow re-checks it before pushing. - roles/gitea-actions pulls instead of building. gitea_ci_build_local=true restores the local build+push for seeding a cold registry or when CI is down -- the workflow that builds gitea-ci runs in gitea-ci. - Lint .gitea/ alongside ansible/, and document the flow in the role README. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
41 lines
2.2 KiB
Docker
41 lines
2.2 KiB
Docker
# ESP-IDF firmware job image (managed by ansible: roles/gitea-actions).
|
|
# Adds node (required by actions/checkout and other JS actions), the AWS CLI
|
|
# (firmware artifacts ship to S3), jq (the release script rewrites the protocol
|
|
# manifest with it), and the common-yaml header generator's Python deps on top
|
|
# of the official Espressif toolchain.
|
|
# IDF lives at /opt/esp/idf — firmware jobs source /opt/esp/idf/export.sh.
|
|
# python3-yaml + python3-jinja2 are installed as distro packages so the
|
|
# common-yaml generator runs with a plain `python3 generate.py` — no pip at job
|
|
# time (the base image's system Python is PEP 668 externally-managed) and no
|
|
# need to source the IDF venv just to generate headers.
|
|
#
|
|
# jq is required by esp32-stm32-vcu scripts/release.sh, which publishes the
|
|
# protocol manifest and BLE_API.md to S3 after the firmware upload. Without it
|
|
# the release aborts *after* the firmware and version.json are already live —
|
|
# clients get the new build while the tag, Gitea release and protocol manifest
|
|
# are never written. Keep it installed.
|
|
#
|
|
# Built and published by .gitea/workflows/ci-images.yml; roles/gitea-actions
|
|
# only pulls the result. ESP_IDF_VERSION is a build arg rather than an ansible
|
|
# template var so CI and ansible build the same bytes -- its value is read from
|
|
# esp_idf_version in roles/gitea-actions/defaults/main.yml by both.
|
|
ARG ESP_IDF_VERSION
|
|
FROM espressif/idf:${ESP_IDF_VERSION}
|
|
|
|
# Exempts the image from the nightly CI prune -- see podman_prune_ci_keep_label
|
|
# in roles/podman/defaults/main.yml. Declared here rather than passed as a
|
|
# --label at build time so neither builder can forget it: without the label the
|
|
# prune deletes the image every night and the next job re-pulls 7.8 GB.
|
|
LABEL io.debyl.ci-base="true"
|
|
|
|
RUN apt-get update && apt-get install -y --no-install-recommends \
|
|
curl ca-certificates unzip jq python3-yaml python3-jinja2 \
|
|
&& curl -fsSL https://deb.nodesource.com/setup_20.x | bash - \
|
|
&& apt-get install -y --no-install-recommends nodejs \
|
|
&& rm -rf /var/lib/apt/lists/*
|
|
|
|
RUN curl -fsSL "https://awscli.amazonaws.com/awscli-exe-linux-x86_64.zip" -o /tmp/awscliv2.zip \
|
|
&& unzip -q /tmp/awscliv2.zip -d /tmp \
|
|
&& /tmp/aws/install \
|
|
&& rm -rf /tmp/aws /tmp/awscliv2.zip
|