diff --git a/.github/actions/docker-setup/action.yml b/.github/actions/docker-setup/action.yml index 8b917dcf..ca3dd0dc 100644 --- a/.github/actions/docker-setup/action.yml +++ b/.github/actions/docker-setup/action.yml @@ -18,6 +18,9 @@ outputs: release-suffix: description: 'Release suffix for non-production builds' value: ${{ steps.env-vars.outputs.release_suffix }} + build-date: + description: 'RFC3339 UTC build timestamp for the org.opencontainers.image.created OCI label.' + value: ${{ steps.oci-meta.outputs.build_date }} runs: using: 'composite' @@ -85,6 +88,14 @@ runs: docker buildx inspect --bootstrap echo "::endgroup::" + - name: Compute OCI build metadata + id: oci-meta + shell: bash + run: | + # RFC3339 UTC stamp consumed by docker-bake as the BUILD_DATE variable, + # which fills org.opencontainers.image.created (see shared/versions.hcl). + echo "build_date=$(date -u +%Y-%m-%dT%H:%M:%SZ)" >> "$GITHUB_OUTPUT" + - name: Determine if this is a production build id: build-type shell: bash diff --git a/.github/workflows/base.yml b/.github/workflows/base.yml index c37404c5..253013b5 100644 --- a/.github/workflows/base.yml +++ b/.github/workflows/base.yml @@ -49,6 +49,8 @@ jobs: env: BUILDX_BAKE_ENTITLEMENTS_FS: 0 RELEASE_SUFFIX: ${{ steps.setup.outputs.release-suffix }} + GIT_SHA: ${{ github.sha }} + BUILD_DATE: ${{ steps.setup.outputs.build-date }} with: source: . files: | @@ -179,6 +181,8 @@ jobs: env: BUILDX_BAKE_ENTITLEMENTS_FS: 0 RELEASE_SUFFIX: ${{ steps.setup.outputs.release-suffix }} + GIT_SHA: ${{ github.sha }} + BUILD_DATE: ${{ steps.setup.outputs.build-date }} with: source: . files: | @@ -335,6 +339,8 @@ jobs: env: BUILDX_BAKE_ENTITLEMENTS_FS: 0 RELEASE_SUFFIX: ${{ steps.setup.outputs.release-suffix }} + GIT_SHA: ${{ github.sha }} + BUILD_DATE: ${{ steps.setup.outputs.build-date }} with: source: . files: | diff --git a/.github/workflows/cluster.yml b/.github/workflows/cluster.yml index c24f630a..12f9fba8 100644 --- a/.github/workflows/cluster.yml +++ b/.github/workflows/cluster.yml @@ -57,6 +57,8 @@ jobs: env: BUILDX_BAKE_ENTITLEMENTS_FS: 0 RELEASE_SUFFIX: ${{ steps.setup.outputs.release-suffix }} + GIT_SHA: ${{ github.sha }} + BUILD_DATE: ${{ steps.setup.outputs.build-date }} with: source: . files: | diff --git a/.github/workflows/nvidia.yml b/.github/workflows/nvidia.yml index 731e16fb..a2dc85b7 100644 --- a/.github/workflows/nvidia.yml +++ b/.github/workflows/nvidia.yml @@ -49,6 +49,8 @@ jobs: env: BUILDX_BAKE_ENTITLEMENTS_FS: 0 RELEASE_SUFFIX: ${{ steps.setup.outputs.release-suffix }} + GIT_SHA: ${{ github.sha }} + BUILD_DATE: ${{ steps.setup.outputs.build-date }} with: source: . files: | diff --git a/.github/workflows/rocm.yml b/.github/workflows/rocm.yml index a2b06061..a1d4044d 100644 --- a/.github/workflows/rocm.yml +++ b/.github/workflows/rocm.yml @@ -49,6 +49,8 @@ jobs: env: BUILDX_BAKE_ENTITLEMENTS_FS: 0 RELEASE_SUFFIX: ${{ steps.setup.outputs.release-suffix }} + GIT_SHA: ${{ github.sha }} + BUILD_DATE: ${{ steps.setup.outputs.build-date }} with: source: . files: | diff --git a/official-templates/autoresearch/Dockerfile b/official-templates/autoresearch/Dockerfile index 9d32277b..cae92e23 100644 --- a/official-templates/autoresearch/Dockerfile +++ b/official-templates/autoresearch/Dockerfile @@ -13,10 +13,15 @@ RUN wget -q --https-only --secure-protocol=TLSv1_2 --max-redirect=3 \ tar -xz -C /usr/local/bin -f /tmp/runpodctl.tar.gz runpodctl && \ rm /tmp/runpodctl.tar.gz -# Clone autoresearch to /opt (safe from volume mounts) -ARG AUTORESEARCH_REF=master -RUN git clone --branch "${AUTORESEARCH_REF}" --depth 1 \ - https://github.com/runpod/autoresearch.git /opt/autoresearch +# Clone autoresearch to /opt (safe from volume mounts). Pinned to an immutable +# commit SHA for reproducible builds — `git clone --branch` only accepts a +# branch/tag, so we init + shallow-fetch the exact commit and detach onto it. +# Bump AUTORESEARCH_REF to update. +ARG AUTORESEARCH_REF=d173f4ec6353213bf644631a8d30fa80974cc65f +RUN git init /opt/autoresearch && \ + git -C /opt/autoresearch remote add origin https://github.com/runpod/autoresearch.git && \ + git -C /opt/autoresearch fetch --depth 1 origin "${AUTORESEARCH_REF}" && \ + git -C /opt/autoresearch checkout --detach FETCH_HEAD WORKDIR /opt/autoresearch @@ -32,6 +37,7 @@ RUN --mount=type=cache,target=/root/.cache/uv,sharing=locked \ # and symlink .venv back to /opt (12GB, stays on fast container layer) COPY pre_start.sh /pre_start.sh -# Override the NVIDIA CUDA entrypoint which blocks boot on hosts with older -# drivers (e.g. driver 550 only supports CUDA 12.4, but this image has 12.8). -ENTRYPOINT ["/start.sh"] +# PID 1 (ENTRYPOINT tini + CMD /start.sh) is inherited from runpod/base. tini's +# ENTRYPOINT also supersedes the NVIDIA CUDA base entrypoint, which otherwise +# blocks boot on hosts with older drivers (e.g. driver 550 supports only CUDA +# 12.4 while this image ships 12.8) — so no ENTRYPOINT override is needed here. diff --git a/official-templates/autoresearch/docker-bake.hcl b/official-templates/autoresearch/docker-bake.hcl index 1851b19e..beb78cd9 100644 --- a/official-templates/autoresearch/docker-bake.hcl +++ b/official-templates/autoresearch/docker-bake.hcl @@ -18,9 +18,14 @@ group "default" { } target "autoresearch-base" { + inherits = ["_oci-labels"] context = "official-templates/autoresearch" dockerfile = "Dockerfile" platforms = ["linux/amd64"] + labels = { + "org.opencontainers.image.title" = "Runpod Autoresearch" + "org.opencontainers.image.description" = "Runpod autoresearch image built on runpod/base with CUDA 12.8.1." + } } target "autoresearch-matrix" { diff --git a/official-templates/base/Dockerfile b/official-templates/base/Dockerfile index bd78fd6d..8a929f55 100644 --- a/official-templates/base/Dockerfile +++ b/official-templates/base/Dockerfile @@ -70,7 +70,7 @@ RUN apt-get update --yes && \ libgl1 libhdf5-dev libjpeg-dev liblapack-dev libnuma-dev libpng-dev libpostproc-dev \ libsm6 libssl-dev libswscale-dev libtiff-dev libv4l-dev libx264-dev libxrender-dev \ libxvidcore-dev lsof make mtr nano nfs-common nginx openssh-server rsync \ - software-properties-common sudo tmux unzip vim wget zip zstd && \ + software-properties-common sudo tini tmux unzip vim wget zip zstd && \ rm -f /etc/ssh/ssh_host_*_key /etc/ssh/ssh_host_*_key.pub && \ rm -rf /var/lib/apt/lists/* @@ -185,4 +185,6 @@ and https://blog.runpod.io BANNER EOF +# Run everything under tini as PID 1 +ENTRYPOINT ["/usr/bin/tini", "-g", "--"] CMD ["/start.sh"] diff --git a/official-templates/base/docker-bake.hcl b/official-templates/base/docker-bake.hcl index a4e37234..11ac625a 100644 --- a/official-templates/base/docker-bake.hcl +++ b/official-templates/base/docker-bake.hcl @@ -7,6 +7,7 @@ group "default" { } target "common-base" { + inherits = ["_oci-labels"] context = "official-templates/base" dockerfile = "Dockerfile" platforms = ["linux/amd64"] @@ -17,6 +18,10 @@ target "common-base" { requirements = "official-templates/base" scrub_stale_metadata = "scripts" } + labels = { + "org.opencontainers.image.title" = "Runpod Base" + "org.opencontainers.image.description" = "Base image for Runpod official templates: CUDA/Ubuntu runtime with SSH, Jupyter, and the Runpod container tooling." + } } target "cpu-ubuntu2204" { diff --git a/official-templates/nvidia-pytorch/docker-bake.hcl b/official-templates/nvidia-pytorch/docker-bake.hcl index ba269bb3..339c2fc1 100644 --- a/official-templates/nvidia-pytorch/docker-bake.hcl +++ b/official-templates/nvidia-pytorch/docker-bake.hcl @@ -13,6 +13,7 @@ group "pytorch2511" { } target "nvidia-base" { + inherits = ["_oci-labels"] context = "official-templates/base" dockerfile = "Dockerfile" platforms = ["linux/amd64"] @@ -26,6 +27,10 @@ target "nvidia-base" { args = { RP_SKIP_PYTHON = "1" } + labels = { + "org.opencontainers.image.title" = "Runpod NVIDIA PyTorch" + "org.opencontainers.image.description" = "Runpod image built on NVIDIA's NGC PyTorch container with the Runpod base tooling layered on top." + } } target "pytorch-matrix" { diff --git a/official-templates/pytorch-cluster/docker-bake.hcl b/official-templates/pytorch-cluster/docker-bake.hcl index 32e7ff43..89c2f435 100644 --- a/official-templates/pytorch-cluster/docker-bake.hcl +++ b/official-templates/pytorch-cluster/docker-bake.hcl @@ -47,9 +47,14 @@ group "cu1300" { } target "cluster-base" { + inherits = ["_oci-labels"] context = "official-templates/pytorch-cluster" dockerfile = "Dockerfile" platforms = ["linux/amd64"] + labels = { + "org.opencontainers.image.title" = "Runpod PyTorch Cluster" + "org.opencontainers.image.description" = "Runpod PyTorch image with cluster extras (GPU monitoring + RDMA) layered on top of the published runpod/pytorch base." + } } target "cluster-matrix" { diff --git a/official-templates/pytorch/docker-bake.hcl b/official-templates/pytorch/docker-bake.hcl index f52be3cf..fa367263 100644 --- a/official-templates/pytorch/docker-bake.hcl +++ b/official-templates/pytorch/docker-bake.hcl @@ -100,9 +100,14 @@ group "cu1300" { } target "pytorch-base" { + inherits = ["_oci-labels"] context = "official-templates/pytorch" dockerfile = "Dockerfile" platforms = ["linux/amd64"] + labels = { + "org.opencontainers.image.title" = "Runpod PyTorch" + "org.opencontainers.image.description" = "Runpod PyTorch image: runpod/base plus a CUDA-matched PyTorch/torchvision/torchaudio stack." + } } target "pytorch-matrix" { diff --git a/official-templates/rocm/docker-bake.hcl b/official-templates/rocm/docker-bake.hcl index 8bc83a3c..97a3c08a 100644 --- a/official-templates/rocm/docker-bake.hcl +++ b/official-templates/rocm/docker-bake.hcl @@ -15,6 +15,7 @@ group "rocm644" { } target "rocm-base" { + inherits = ["_oci-labels"] context = "official-templates/base" dockerfile = "Dockerfile" platforms = ["linux/amd64"] @@ -28,6 +29,10 @@ target "rocm-base" { args = { RP_SKIP_PYTHON = "1" } + labels = { + "org.opencontainers.image.title" = "Runpod ROCm PyTorch" + "org.opencontainers.image.description" = "Runpod image built on AMD's ROCm PyTorch container with the Runpod base tooling layered on top." + } } target "rocm-matrix" { diff --git a/official-templates/shared/versions.hcl b/official-templates/shared/versions.hcl index 0365ebb5..82e78296 100644 --- a/official-templates/shared/versions.hcl +++ b/official-templates/shared/versions.hcl @@ -1,9 +1,34 @@ -RELEASE_VERSION = "1.0.8" +RELEASE_VERSION = "1.0.9" variable "RELEASE_SUFFIX" { default = "" # Set by CI, not used by humans. } + +variable "GIT_SHA" { + default = "" # Set by CI to the built commit SHA (github.sha). +} + +variable "BUILD_DATE" { + default = "" # Set by CI to an RFC3339 UTC timestamp (docker-setup build-date). +} + +# Shared OCI image labels (https://github.com/opencontainers/image-spec). +# Every family's *-base target inherits this so provenance/metadata stays +# consistent; each family layers its own image.title / image.description on +# top (bake merges the maps). We intentionally omit image.licenses. +target "_oci-labels" { + labels = { + "org.opencontainers.image.source" = "https://github.com/runpod/containers" + "org.opencontainers.image.url" = "https://github.com/runpod/containers" + "org.opencontainers.image.documentation" = "https://github.com/runpod/containers" + "org.opencontainers.image.vendor" = "Runpod" + "org.opencontainers.image.version" = "${RELEASE_VERSION}${RELEASE_SUFFIX}" + "org.opencontainers.image.revision" = "${GIT_SHA}" + "org.opencontainers.image.created" = "${BUILD_DATE}" + } +} + UBUNTU_VERSIONS = [ { version = "22.04"