From 83b16e8b61f95b132611d8e6863928a531b219a8 Mon Sep 17 00:00:00 2001 From: chen21019 <19357113+chen21019@users.noreply.github.com> Date: Fri, 23 Oct 2026 20:00:03 +0800 Subject: [PATCH 1/8] build: refresh October security pins and trust stores --- .github/workflows/codeql-verification.yml | 6 +++--- .github/workflows/security-release-gate.yml | 6 +++--- Dockerfile.dapper | 12 +++++++++--- Makefile | 2 +- README.md | 6 +++++- go.mod | 10 +++++----- go.sum | 8 ++++++++ package/ubuntu-apt.lock | 4 +++- scripts/validate | 4 ++-- third_party/control-api-client/go.mod | 2 +- third_party/event-subscriber/go.mod | 2 +- third_party/platform-metadata-client/go.mod | 2 +- 12 files changed, 42 insertions(+), 22 deletions(-) diff --git a/.github/workflows/codeql-verification.yml b/.github/workflows/codeql-verification.yml index 99356c1..d8ead21 100644 --- a/.github/workflows/codeql-verification.yml +++ b/.github/workflows/codeql-verification.yml @@ -35,12 +35,12 @@ jobs: shell: bash run: | set -euo pipefail - archive="$RUNNER_TEMP/go1.27.0.linux-amd64.tar.gz" + archive="$RUNNER_TEMP/go1.27.3.linux-amd64.tar.gz" curl --fail --silent --show-error --location \ --output "$archive" \ - 'https://go.dev/dl/go1.27.0.linux-amd64.tar.gz' + 'https://go.dev/dl/go1.27.3.linux-amd64.tar.gz' printf '%s %s\n' \ - '675c26c449cbb18fc24b74650de1eabbae6e16f64326fd85a283fb3b58280685' \ + '65efbc80fdc1fa2cd2631cad5b481777a68e8725f34e89f50fc6ac714e379b40' \ "$archive" | sha256sum --check tar -C "$RUNNER_TEMP" -xzf "$archive" "$RUNNER_TEMP/go/bin/go" version diff --git a/.github/workflows/security-release-gate.yml b/.github/workflows/security-release-gate.yml index 41f6054..bb4de05 100644 --- a/.github/workflows/security-release-gate.yml +++ b/.github/workflows/security-release-gate.yml @@ -52,12 +52,12 @@ jobs: shell: bash run: | set -euo pipefail - archive="$RUNNER_TEMP/go1.27.0.linux-amd64.tar.gz" + archive="$RUNNER_TEMP/go1.27.3.linux-amd64.tar.gz" curl --fail --silent --show-error --location \ --output "$archive" \ - 'https://go.dev/dl/go1.27.0.linux-amd64.tar.gz' + 'https://go.dev/dl/go1.27.3.linux-amd64.tar.gz' printf '%s %s\n' \ - '675c26c449cbb18fc24b74650de1eabbae6e16f64326fd85a283fb3b58280685' \ + '65efbc80fdc1fa2cd2631cad5b481777a68e8725f34e89f50fc6ac714e379b40' \ "$archive" | sha256sum --check tar -C "$RUNNER_TEMP" -xzf "$archive" "$RUNNER_TEMP/go/bin/go" version diff --git a/Dockerfile.dapper b/Dockerfile.dapper index 2a28843..f6c90d8 100644 --- a/Dockerfile.dapper +++ b/Dockerfile.dapper @@ -8,8 +8,8 @@ COPY package/ubuntu-apt.lock /licenses/ubuntu-apt.lock ARG DAPPER_HOST_ARCH=amd64 ARG DOCKER_VERSION=29.7.2 ARG DOCKER_LINUX_AMD64_SHA256=803d433f226db4776e1768fd319fc6c6e4935a456acf84fcc0080818b854bc8f -ARG GO_VERSION=1.27.0 -ARG GO_LINUX_AMD64_SHA256=675c26c449cbb18fc24b74650de1eabbae6e16f64326fd85a283fb3b58280685 +ARG GO_VERSION=1.27.3 +ARG GO_LINUX_AMD64_SHA256=65efbc80fdc1fa2cd2631cad5b481777a68e8725f34e89f50fc6ac714e379b40 ENV DEBIAN_FRONTEND=noninteractive ENV HOST_ARCH=${DAPPER_HOST_ARCH} \ @@ -18,6 +18,7 @@ ENV HOST_ARCH=${DAPPER_HOST_ARCH} \ SHELL=/bin/bash \ GOTOOLCHAIN=local +ADD --checksum=sha256:5b6326f1932cfd7be57130561dc78192f09ed9f58bfbe6606ed0c50510c3b6cd https://archive.ubuntu.com/ubuntu/pool/main/c/ca-certificates/ca-certificates_20260816ubuntu0.26.04.1_all.deb /opt/pasturestack-ca-certificates.deb RUN set -eux; \ . /licenses/ubuntu-apt.lock; \ find /etc/apt -type f \( -name '*.list' -o -name '*.sources' \) -exec sed -i \ @@ -27,12 +28,17 @@ RUN set -eux; \ apt-get --snapshot "${UBUNTU_APT_SNAPSHOT}" update; \ apt-get --snapshot "${UBUNTU_APT_SNAPSHOT}" install -y --no-install-recommends \ bash="${UBUNTU_APT_BASH_VERSION}" \ - ca-certificates="${UBUNTU_APT_CA_CERTIFICATES_VERSION}" \ + ca-certificates="${UBUNTU_APT_CA_CERTIFICATES_BOOTSTRAP_VERSION}" \ curl="${UBUNTU_APT_CURL_VERSION}" \ git="${UBUNTU_APT_GIT_VERSION}" \ jq="${UBUNTU_APT_JQ_VERSION}" \ tar="${UBUNTU_APT_TAR_VERSION}" \ xz-utils="${UBUNTU_APT_XZ_UTILS_VERSION}"; \ + dpkg -i /opt/pasturestack-ca-certificates.deb && \ + update-ca-certificates --fresh && \ + test "$(dpkg-query -W -f='${Version}' ca-certificates)" = '20260816ubuntu0.26.04.1' && \ + test ! -e /usr/share/ca-certificates/mozilla/emSign_ECC_Root_CA_-_G3.crt && \ + rm -f /opt/pasturestack-ca-certificates.deb && \ { \ printf 'snapshot\t%s\n' "${UBUNTU_APT_SNAPSHOT}"; \ dpkg-query -W -f='${binary:Package}\t${Version}\n' | LC_ALL=C sort; \ diff --git a/Makefile b/Makefile index 0c3512e..f9a7ede 100644 --- a/Makefile +++ b/Makefile @@ -1,6 +1,6 @@ TARGETS := $(shell ls scripts) -DAPPER_IMAGE ?= pasturestack-kubernetes-agent-dapper:go1.27.0 +DAPPER_IMAGE ?= pasturestack-kubernetes-agent-dapper:go1.27.3 DAPPER_HOST_ARCH ?= amd64 DOCKER_VERSION ?= 29.7.2 diff --git a/README.md b/README.md index 7a4a661..039913e 100644 --- a/README.md +++ b/README.md @@ -8,7 +8,7 @@ PastureStack is an independent community effort to preserve, audit, and moderniz ## Project status -Candidate `0.7.3` uses Go 1.27.0, Go modules, client-go 0.36.4, and logrus 1.10.1 while +Candidate `0.7.3` uses Go 1.27.3, Go modules, client-go 0.36.4, and logrus 1.10.1 while retaining the established event and Kubernetes API contracts. Kubernetes 1.36.4 is the supported and tested API line. Its runtime is a digest-pinned distroless image that runs as UID/GID 65532. Source, runtime, and @@ -48,3 +48,7 @@ change a catalog. See [COMPATIBILITY.md](COMPATIBILITY.md), ## License and attribution The inherited project remains licensed under [Apache License 2.0](LICENSE). Copyright and attribution for inherited work and vendored dependencies remain with their respective authors and contributors. PastureStack contributors claim authorship only for their own changes. + +## October 2026 security maintenance + +Maintained Go builds select the patched Go 1.27.3 compiler without raising the existing Go language requirement. Ubuntu build/runtime stages apply the checksum-pinned `ca-certificates 20260816ubuntu0.26.04.1` security package after their frozen APT baseline; the final trust store and installed version are verified. Release artifacts must pass the repository's existing checks before publication. diff --git a/go.mod b/go.mod index ca87b92..32267db 100644 --- a/go.mod +++ b/go.mod @@ -2,7 +2,7 @@ module github.com/PastureStack/kubernetes-agent go 1.26.0 -toolchain go1.27.0 +toolchain go1.27.3 require ( github.com/PastureStack/control-api-client v0.0.0 @@ -53,11 +53,11 @@ require ( github.com/x448/float16 v0.8.4 // indirect go.yaml.in/yaml/v2 v2.4.4 // indirect go.yaml.in/yaml/v3 v3.0.5 // indirect - golang.org/x/net v0.58.0 // indirect + golang.org/x/net v0.60.0 // indirect golang.org/x/oauth2 v0.36.0 // indirect - golang.org/x/sys v0.47.0 // indirect - golang.org/x/term v0.45.0 // indirect - golang.org/x/text v0.41.0 // indirect + golang.org/x/sys v0.48.0 // indirect + golang.org/x/term v0.46.0 // indirect + golang.org/x/text v0.42.0 // indirect golang.org/x/time v0.15.0 // indirect google.golang.org/protobuf v1.36.12 // indirect gopkg.in/evanphx/json-patch.v4 v4.13.0 // indirect diff --git a/go.sum b/go.sum index 4665af7..e162b82 100644 --- a/go.sum +++ b/go.sum @@ -111,14 +111,22 @@ go.yaml.in/yaml/v3 v3.0.5 h1:N6y/pJk8buWs9NY5ERU2HSMfm+IuD/OtfdAnq6kESPw= go.yaml.in/yaml/v3 v3.0.5/go.mod h1:HVTZu1O7/Vkt2N+BFy8Zza+lnLsABggaTM2ZpNIGuKg= golang.org/x/net v0.58.0 h1:ynWG7rqYi4ccpTEuPZ2QGWHktVEM9DMCj9yzDE0Q7To= golang.org/x/net v0.58.0/go.mod h1:YwCddHnFlT7eLQqVprV19OnhLGtc5xOKgE0RyqgfWAU= +golang.org/x/net v0.60.0 h1:79p50tfZlm0J9YfoDsSi639qSXNGVwEzOPLCxM2FsYU= +golang.org/x/net v0.60.0/go.mod h1:2DA/G1UfVbCpQPeWTmMPGY7Cs2PkBkwu743bVX5PIVg= golang.org/x/oauth2 v0.36.0 h1:peZ/1z27fi9hUOFCAZaHyrpWG5lwe0RJEEEeH0ThlIs= golang.org/x/oauth2 v0.36.0/go.mod h1:YDBUJMTkDnJS+A4BP4eZBjCqtokkg1hODuPjwiGPO7Q= golang.org/x/sys v0.47.0 h1:o7XGOvZQCADBQQ4Y7VNq2dRWQR7JmOUW8Kxx4ZsNgWs= golang.org/x/sys v0.47.0/go.mod h1:4GL1E5IUh+htKOUEOaiffhrAeqysfVGipDYzABqnCmw= +golang.org/x/sys v0.48.0 h1:bbX/i/6MgT9BVLM9RT1thmxL04yeTAhbEz4SyadbXoo= +golang.org/x/sys v0.48.0/go.mod h1:hNLxWAXmnKAxqDtdwIYC4bM9oQPEecfsnNMuSxOs3og= golang.org/x/term v0.45.0 h1:NwWyBmoJCbfTHpxrWoZ9C6/VxOf7ic219I8xZZFdrf0= golang.org/x/term v0.45.0/go.mod h1:9aqxs0blBcrm/n0L9QW0aRVD+ktan8ssZromtqJC43w= +golang.org/x/term v0.46.0 h1:3+OXuTbaKDgwk8jTi3aSLHRlmWqHEUDUtxnbFigO4YE= +golang.org/x/term v0.46.0/go.mod h1:+K02xbkittuwc0Am4abfA3Fc+XRGXkvBXNO88NCXPoc= golang.org/x/text v0.41.0 h1:vz/seA0lnX87Othu2f/0L24RcgrXD9/YFTSuGjj3rH8= golang.org/x/text v0.41.0/go.mod h1:jvf1O8ajNzZqhSrQBPbutR/EB83Cc0CFrezNQIwbb5M= +golang.org/x/text v0.42.0 h1:JbOZXgfeCPU9gacVtYliJqOhD+zhrEqK4LfdpmlUZqI= +golang.org/x/text v0.42.0/go.mod h1:ojzP1Z+2QtioaF8DTtO8K5q7JWVVYwZKenzujK0Zd0E= golang.org/x/time v0.15.0 h1:bbrp8t3bGUeFOx08pvsMYRTCVSMk89u4tKbNOZbp88U= golang.org/x/time v0.15.0/go.mod h1:Y4YMaQmXwGQZoFaVFk4YpCt4FLQMYKZe9oeV/f4MSno= google.golang.org/protobuf v1.36.12 h1:pJOKDDOyeXErUroCihFAd5LQuwXBSpVnKGrj5o/fwxc= diff --git a/package/ubuntu-apt.lock b/package/ubuntu-apt.lock index abde4c3..e341215 100644 --- a/package/ubuntu-apt.lock +++ b/package/ubuntu-apt.lock @@ -4,7 +4,9 @@ UBUNTU_APT_SNAPSHOT='20260808T000000Z' UBUNTU_APT_BASH_VERSION='5.3-2ubuntu1' -UBUNTU_APT_CA_CERTIFICATES_VERSION='20260601~26.04.1' +# Frozen APT baseline; the checksum-pinned security overlay below is the final installed CA. +UBUNTU_APT_CA_CERTIFICATES_BOOTSTRAP_VERSION='20260601~26.04.1' +UBUNTU_APT_CA_CERTIFICATES_VERSION='20260816ubuntu0.26.04.1' UBUNTU_APT_CURL_VERSION='8.18.0-1ubuntu2.3' UBUNTU_APT_GIT_VERSION='1:2.53.0-1ubuntu1' UBUNTU_APT_JQ_VERSION='1.8.1-4ubuntu2' diff --git a/scripts/validate b/scripts/validate index 858748e..9b084c7 100755 --- a/scripts/validate +++ b/scripts/validate @@ -31,12 +31,12 @@ fi required_markers=( 'go 1.26.0' - 'toolchain go1.27.0' + 'toolchain go1.27.3' 'FROM docker:29.7.2-cli@sha256:000bb62ff495f986c9f5578eb67cc2cb98b91138eda81d7762d5371eb8a497fe AS snapshot-ca-certificates' 'FROM ubuntu:26.04@sha256:2260313b31c8c011cd2eebe728008efac1b3982be73eb71348ea2648d2c0e09b' "UBUNTU_APT_SNAPSHOT='20260808T000000Z'" 'apt-get --snapshot "${UBUNTU_APT_SNAPSHOT}" update' - 'GO_VERSION=1.27.0' + 'GO_VERSION=1.27.3' 'DOCKER_VERSION=29.7.2' 'FROM gcr.io/distroless/static-debian12@sha256:4b2a093ef4649bccd586625090a3c668b254cfe180dee54f4c94f3e9bd7e381e' 'USER 65532:65532' diff --git a/third_party/control-api-client/go.mod b/third_party/control-api-client/go.mod index 4a35c14..0323054 100644 --- a/third_party/control-api-client/go.mod +++ b/third_party/control-api-client/go.mod @@ -2,7 +2,7 @@ module github.com/PastureStack/control-api-client go 1.26.0 -toolchain go1.27.0 +toolchain go1.27.3 require github.com/gorilla/websocket v1.5.4-0.20250319132907-e064f32e3674 diff --git a/third_party/event-subscriber/go.mod b/third_party/event-subscriber/go.mod index b0f891e..0c335d7 100644 --- a/third_party/event-subscriber/go.mod +++ b/third_party/event-subscriber/go.mod @@ -2,7 +2,7 @@ module github.com/PastureStack/event-subscriber go 1.26.0 -toolchain go1.27.0 +toolchain go1.27.3 require ( github.com/PastureStack/control-api-client v0.0.0 diff --git a/third_party/platform-metadata-client/go.mod b/third_party/platform-metadata-client/go.mod index d01f4bf..adf3b24 100644 --- a/third_party/platform-metadata-client/go.mod +++ b/third_party/platform-metadata-client/go.mod @@ -2,7 +2,7 @@ module github.com/PastureStack/platform-metadata-client go 1.26.0 -toolchain go1.27.0 +toolchain go1.27.3 require github.com/sirupsen/logrus v1.10.2 From bb6540f566f2de63bddc356793b2f857e835817e Mon Sep 17 00:00:00 2001 From: chen21019 <19357113+chen21019@users.noreply.github.com> Date: Fri, 23 Oct 2026 20:13:17 +0800 Subject: [PATCH 2/8] build: align security gates and artifact inputs --- .github/workflows/security-release-gate.yml | 6 +++++- go.sum | 8 -------- third_party/control-api-client/go.mod | 2 +- third_party/control-api-client/go.sum | 2 ++ third_party/event-subscriber/go.mod | 4 ++-- third_party/event-subscriber/go.sum | 3 +++ 6 files changed, 13 insertions(+), 12 deletions(-) diff --git a/.github/workflows/security-release-gate.yml b/.github/workflows/security-release-gate.yml index bb4de05..c0ab624 100644 --- a/.github/workflows/security-release-gate.yml +++ b/.github/workflows/security-release-gate.yml @@ -97,7 +97,11 @@ jobs: go test -mod=mod -race -count=1 ./... ) ( - cd third_party/go-rancher-metadata + cd third_party/platform-metadata-client + go test -mod=mod -race -count=1 ./... + ) + ( + cd third_party/control-api-client go test -mod=mod -race -count=1 ./... ) diff --git a/go.sum b/go.sum index e162b82..3c715e2 100644 --- a/go.sum +++ b/go.sum @@ -109,22 +109,14 @@ go.yaml.in/yaml/v2 v2.4.4 h1:tuyd0P+2Ont/d6e2rl3be67goVK4R6deVxCUX5vyPaQ= go.yaml.in/yaml/v2 v2.4.4/go.mod h1:gMZqIpDtDqOfM0uNfy0SkpRhvUryYH0Z6wdMYcacYXQ= go.yaml.in/yaml/v3 v3.0.5 h1:N6y/pJk8buWs9NY5ERU2HSMfm+IuD/OtfdAnq6kESPw= go.yaml.in/yaml/v3 v3.0.5/go.mod h1:HVTZu1O7/Vkt2N+BFy8Zza+lnLsABggaTM2ZpNIGuKg= -golang.org/x/net v0.58.0 h1:ynWG7rqYi4ccpTEuPZ2QGWHktVEM9DMCj9yzDE0Q7To= -golang.org/x/net v0.58.0/go.mod h1:YwCddHnFlT7eLQqVprV19OnhLGtc5xOKgE0RyqgfWAU= golang.org/x/net v0.60.0 h1:79p50tfZlm0J9YfoDsSi639qSXNGVwEzOPLCxM2FsYU= golang.org/x/net v0.60.0/go.mod h1:2DA/G1UfVbCpQPeWTmMPGY7Cs2PkBkwu743bVX5PIVg= golang.org/x/oauth2 v0.36.0 h1:peZ/1z27fi9hUOFCAZaHyrpWG5lwe0RJEEEeH0ThlIs= golang.org/x/oauth2 v0.36.0/go.mod h1:YDBUJMTkDnJS+A4BP4eZBjCqtokkg1hODuPjwiGPO7Q= -golang.org/x/sys v0.47.0 h1:o7XGOvZQCADBQQ4Y7VNq2dRWQR7JmOUW8Kxx4ZsNgWs= -golang.org/x/sys v0.47.0/go.mod h1:4GL1E5IUh+htKOUEOaiffhrAeqysfVGipDYzABqnCmw= golang.org/x/sys v0.48.0 h1:bbX/i/6MgT9BVLM9RT1thmxL04yeTAhbEz4SyadbXoo= golang.org/x/sys v0.48.0/go.mod h1:hNLxWAXmnKAxqDtdwIYC4bM9oQPEecfsnNMuSxOs3og= -golang.org/x/term v0.45.0 h1:NwWyBmoJCbfTHpxrWoZ9C6/VxOf7ic219I8xZZFdrf0= -golang.org/x/term v0.45.0/go.mod h1:9aqxs0blBcrm/n0L9QW0aRVD+ktan8ssZromtqJC43w= golang.org/x/term v0.46.0 h1:3+OXuTbaKDgwk8jTi3aSLHRlmWqHEUDUtxnbFigO4YE= golang.org/x/term v0.46.0/go.mod h1:+K02xbkittuwc0Am4abfA3Fc+XRGXkvBXNO88NCXPoc= -golang.org/x/text v0.41.0 h1:vz/seA0lnX87Othu2f/0L24RcgrXD9/YFTSuGjj3rH8= -golang.org/x/text v0.41.0/go.mod h1:jvf1O8ajNzZqhSrQBPbutR/EB83Cc0CFrezNQIwbb5M= golang.org/x/text v0.42.0 h1:JbOZXgfeCPU9gacVtYliJqOhD+zhrEqK4LfdpmlUZqI= golang.org/x/text v0.42.0/go.mod h1:ojzP1Z+2QtioaF8DTtO8K5q7JWVVYwZKenzujK0Zd0E= golang.org/x/time v0.15.0 h1:bbrp8t3bGUeFOx08pvsMYRTCVSMk89u4tKbNOZbp88U= diff --git a/third_party/control-api-client/go.mod b/third_party/control-api-client/go.mod index 0323054..6dec477 100644 --- a/third_party/control-api-client/go.mod +++ b/third_party/control-api-client/go.mod @@ -6,4 +6,4 @@ toolchain go1.27.3 require github.com/gorilla/websocket v1.5.4-0.20250319132907-e064f32e3674 -require golang.org/x/net v0.58.0 // indirect +require golang.org/x/net v0.60.0 // indirect diff --git a/third_party/control-api-client/go.sum b/third_party/control-api-client/go.sum index ab25fde..9616320 100644 --- a/third_party/control-api-client/go.sum +++ b/third_party/control-api-client/go.sum @@ -2,3 +2,5 @@ github.com/gorilla/websocket v1.5.4-0.20250319132907-e064f32e3674 h1:JeSE6pjso5T github.com/gorilla/websocket v1.5.4-0.20250319132907-e064f32e3674/go.mod h1:r4w70xmWCQKmi1ONH4KIaBptdivuRPyosB9RmPlGEwA= golang.org/x/net v0.58.0 h1:ynWG7rqYi4ccpTEuPZ2QGWHktVEM9DMCj9yzDE0Q7To= golang.org/x/net v0.58.0/go.mod h1:YwCddHnFlT7eLQqVprV19OnhLGtc5xOKgE0RyqgfWAU= +golang.org/x/net v0.60.0 h1:79p50tfZlm0J9YfoDsSi639qSXNGVwEzOPLCxM2FsYU= +golang.org/x/net v0.60.0/go.mod h1:2DA/G1UfVbCpQPeWTmMPGY7Cs2PkBkwu743bVX5PIVg= diff --git a/third_party/event-subscriber/go.mod b/third_party/event-subscriber/go.mod index 0c335d7..1b16857 100644 --- a/third_party/event-subscriber/go.mod +++ b/third_party/event-subscriber/go.mod @@ -11,8 +11,8 @@ require ( ) require ( - golang.org/x/net v0.58.0 // indirect - golang.org/x/sys v0.47.0 // indirect + golang.org/x/net v0.60.0 // indirect + golang.org/x/sys v0.48.0 // indirect ) replace github.com/PastureStack/control-api-client => ../control-api-client diff --git a/third_party/event-subscriber/go.sum b/third_party/event-subscriber/go.sum index 89bed0f..f9664c5 100644 --- a/third_party/event-subscriber/go.sum +++ b/third_party/event-subscriber/go.sum @@ -8,5 +8,8 @@ go.yaml.in/yaml/v3 v3.0.5 h1:N6y/pJk8buWs9NY5ERU2HSMfm+IuD/OtfdAnq6kESPw= go.yaml.in/yaml/v3 v3.0.5/go.mod h1:HVTZu1O7/Vkt2N+BFy8Zza+lnLsABggaTM2ZpNIGuKg= golang.org/x/net v0.58.0 h1:ynWG7rqYi4ccpTEuPZ2QGWHktVEM9DMCj9yzDE0Q7To= golang.org/x/net v0.58.0/go.mod h1:YwCddHnFlT7eLQqVprV19OnhLGtc5xOKgE0RyqgfWAU= +golang.org/x/net v0.60.0 h1:79p50tfZlm0J9YfoDsSi639qSXNGVwEzOPLCxM2FsYU= +golang.org/x/net v0.60.0/go.mod h1:2DA/G1UfVbCpQPeWTmMPGY7Cs2PkBkwu743bVX5PIVg= golang.org/x/sys v0.47.0 h1:o7XGOvZQCADBQQ4Y7VNq2dRWQR7JmOUW8Kxx4ZsNgWs= golang.org/x/sys v0.47.0/go.mod h1:4GL1E5IUh+htKOUEOaiffhrAeqysfVGipDYzABqnCmw= +golang.org/x/sys v0.48.0/go.mod h1:hNLxWAXmnKAxqDtdwIYC4bM9oQPEecfsnNMuSxOs3og= From af7e11e9a36784b86e8c6cc413bc9a550adf7ade Mon Sep 17 00:00:00 2001 From: chen21019 <19357113+chen21019@users.noreply.github.com> Date: Fri, 23 Oct 2026 20:31:12 +0800 Subject: [PATCH 3/8] fix: apply official CLI and operating-system security updates --- Dockerfile.dapper | 6 +++--- Makefile | 2 +- scripts/validate | 4 ++-- 3 files changed, 6 insertions(+), 6 deletions(-) diff --git a/Dockerfile.dapper b/Dockerfile.dapper index f6c90d8..8f5155c 100644 --- a/Dockerfile.dapper +++ b/Dockerfile.dapper @@ -1,4 +1,4 @@ -FROM docker:29.7.2-cli@sha256:000bb62ff495f986c9f5578eb67cc2cb98b91138eda81d7762d5371eb8a497fe AS snapshot-ca-certificates +FROM docker:29.9.2-cli@sha256:000bb62ff495f986c9f5578eb67cc2cb98b91138eda81d7762d5371eb8a497fe AS snapshot-ca-certificates FROM ubuntu:26.04@sha256:2260313b31c8c011cd2eebe728008efac1b3982be73eb71348ea2648d2c0e09b @@ -6,8 +6,8 @@ COPY --from=snapshot-ca-certificates /etc/ssl/certs/ca-certificates.crt /etc/ssl COPY package/ubuntu-apt.lock /licenses/ubuntu-apt.lock ARG DAPPER_HOST_ARCH=amd64 -ARG DOCKER_VERSION=29.7.2 -ARG DOCKER_LINUX_AMD64_SHA256=803d433f226db4776e1768fd319fc6c6e4935a456acf84fcc0080818b854bc8f +ARG DOCKER_VERSION=29.9.2 +ARG DOCKER_LINUX_AMD64_SHA256=9ac225999fd5e863f7694c728ef23d480616b1e5639328fa309befd4243d69eb ARG GO_VERSION=1.27.3 ARG GO_LINUX_AMD64_SHA256=65efbc80fdc1fa2cd2631cad5b481777a68e8725f34e89f50fc6ac714e379b40 diff --git a/Makefile b/Makefile index f9a7ede..45a4f5f 100644 --- a/Makefile +++ b/Makefile @@ -2,7 +2,7 @@ TARGETS := $(shell ls scripts) DAPPER_IMAGE ?= pasturestack-kubernetes-agent-dapper:go1.27.3 DAPPER_HOST_ARCH ?= amd64 -DOCKER_VERSION ?= 29.7.2 +DOCKER_VERSION ?= 29.9.2 .PHONY: $(TARGETS) deps trash trash-keep dapper-image diff --git a/scripts/validate b/scripts/validate index 9b084c7..bcfa493 100755 --- a/scripts/validate +++ b/scripts/validate @@ -32,12 +32,12 @@ fi required_markers=( 'go 1.26.0' 'toolchain go1.27.3' - 'FROM docker:29.7.2-cli@sha256:000bb62ff495f986c9f5578eb67cc2cb98b91138eda81d7762d5371eb8a497fe AS snapshot-ca-certificates' + 'FROM docker:29.9.2-cli@sha256:000bb62ff495f986c9f5578eb67cc2cb98b91138eda81d7762d5371eb8a497fe AS snapshot-ca-certificates' 'FROM ubuntu:26.04@sha256:2260313b31c8c011cd2eebe728008efac1b3982be73eb71348ea2648d2c0e09b' "UBUNTU_APT_SNAPSHOT='20260808T000000Z'" 'apt-get --snapshot "${UBUNTU_APT_SNAPSHOT}" update' 'GO_VERSION=1.27.3' - 'DOCKER_VERSION=29.7.2' + 'DOCKER_VERSION=29.9.2' 'FROM gcr.io/distroless/static-debian12@sha256:4b2a093ef4649bccd586625090a3c668b254cfe180dee54f4c94f3e9bd7e381e' 'USER 65532:65532' 'org.opencontainers.image.revision="${SOURCE_REVISION}"' From 79963b2f06f1fbdad365445218937603ed4974e3 Mon Sep 17 00:00:00 2001 From: chen21019 <19357113+chen21019@users.noreply.github.com> Date: Fri, 23 Oct 2026 20:51:15 +0800 Subject: [PATCH 4/8] Keep nested module sums tidy after x-net update --- third_party/control-api-client/go.sum | 2 -- 1 file changed, 2 deletions(-) diff --git a/third_party/control-api-client/go.sum b/third_party/control-api-client/go.sum index 9616320..3e23792 100644 --- a/third_party/control-api-client/go.sum +++ b/third_party/control-api-client/go.sum @@ -1,6 +1,4 @@ github.com/gorilla/websocket v1.5.4-0.20250319132907-e064f32e3674 h1:JeSE6pjso5THxAzdVpqr6/geYxZytqFMBCOtn/ujyeo= github.com/gorilla/websocket v1.5.4-0.20250319132907-e064f32e3674/go.mod h1:r4w70xmWCQKmi1ONH4KIaBptdivuRPyosB9RmPlGEwA= -golang.org/x/net v0.58.0 h1:ynWG7rqYi4ccpTEuPZ2QGWHktVEM9DMCj9yzDE0Q7To= -golang.org/x/net v0.58.0/go.mod h1:YwCddHnFlT7eLQqVprV19OnhLGtc5xOKgE0RyqgfWAU= golang.org/x/net v0.60.0 h1:79p50tfZlm0J9YfoDsSi639qSXNGVwEzOPLCxM2FsYU= golang.org/x/net v0.60.0/go.mod h1:2DA/G1UfVbCpQPeWTmMPGY7Cs2PkBkwu743bVX5PIVg= From bde7f6dbf9d056f981ff2f8bc90235c378ec1e13 Mon Sep 17 00:00:00 2001 From: chen21019 <19357113+chen21019@users.noreply.github.com> Date: Fri, 23 Oct 2026 21:08:02 +0800 Subject: [PATCH 5/8] Normalize every maintained nested module graph --- third_party/event-subscriber/go.sum | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/third_party/event-subscriber/go.sum b/third_party/event-subscriber/go.sum index f9664c5..bb23846 100644 --- a/third_party/event-subscriber/go.sum +++ b/third_party/event-subscriber/go.sum @@ -6,10 +6,7 @@ github.com/stretchr/testify v1.12.1 h1:EuwCh5fleGS7H32xRwO3wRGT7DxrDhLAT6FF8MpWD github.com/stretchr/testify v1.12.1/go.mod h1:MDEgiDPPsNp5cuIrHPPCyornHKgEVbtFUmoNlxoYthg= go.yaml.in/yaml/v3 v3.0.5 h1:N6y/pJk8buWs9NY5ERU2HSMfm+IuD/OtfdAnq6kESPw= go.yaml.in/yaml/v3 v3.0.5/go.mod h1:HVTZu1O7/Vkt2N+BFy8Zza+lnLsABggaTM2ZpNIGuKg= -golang.org/x/net v0.58.0 h1:ynWG7rqYi4ccpTEuPZ2QGWHktVEM9DMCj9yzDE0Q7To= -golang.org/x/net v0.58.0/go.mod h1:YwCddHnFlT7eLQqVprV19OnhLGtc5xOKgE0RyqgfWAU= golang.org/x/net v0.60.0 h1:79p50tfZlm0J9YfoDsSi639qSXNGVwEzOPLCxM2FsYU= golang.org/x/net v0.60.0/go.mod h1:2DA/G1UfVbCpQPeWTmMPGY7Cs2PkBkwu743bVX5PIVg= -golang.org/x/sys v0.47.0 h1:o7XGOvZQCADBQQ4Y7VNq2dRWQR7JmOUW8Kxx4ZsNgWs= -golang.org/x/sys v0.47.0/go.mod h1:4GL1E5IUh+htKOUEOaiffhrAeqysfVGipDYzABqnCmw= +golang.org/x/sys v0.48.0 h1:bbX/i/6MgT9BVLM9RT1thmxL04yeTAhbEz4SyadbXoo= golang.org/x/sys v0.48.0/go.mod h1:hNLxWAXmnKAxqDtdwIYC4bM9oQPEecfsnNMuSxOs3og= From 3357af58c0cf315ad478cf7a3e14f6f08f1018ca Mon Sep 17 00:00:00 2001 From: chen21019 <19357113+chen21019@users.noreply.github.com> Date: Fri, 23 Oct 2026 21:14:29 +0800 Subject: [PATCH 6/8] Match the pinned CodeQL action in source validation --- scripts/validate | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/scripts/validate b/scripts/validate index bcfa493..890d8ff 100755 --- a/scripts/validate +++ b/scripts/validate @@ -134,8 +134,8 @@ fi codeql_workflow=.github/workflows/codeql-verification.yml for marker in \ "'verification/kubernetes-agent-*'" \ - 'github/codeql-action/init@ff2f1c621b7f889edc0d3c761ac2e6a3f8cdb0dd # v4.37.7' \ - 'github/codeql-action/analyze@ff2f1c621b7f889edc0d3c761ac2e6a3f8cdb0dd # v4.37.7' \ + 'github/codeql-action/init@db488ddef3bf6cb639b32c2e9a7c0a7ea8271d28 # v4.37.8' \ + 'github/codeql-action/analyze@db488ddef3bf6cb639b32c2e9a7c0a7ea8271d28 # v4.37.8' \ 'build-mode: manual' \ 'upload: never' \ 'codeql_critical_high' \ From e28faeb0e53c323246ce738679a14b8b0e0c1ad0 Mon Sep 17 00:00:00 2001 From: chen21019 <19357113+chen21019@users.noreply.github.com> Date: Fri, 23 Oct 2026 21:18:26 +0800 Subject: [PATCH 7/8] Publish exact scanned runtime without rebuilding release bytes --- .github/workflows/release.yml | 65 +++++++++++++++++++++ .github/workflows/security-release-gate.yml | 18 ++++++ 2 files changed, 83 insertions(+) create mode 100644 .github/workflows/release.yml diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml new file mode 100644 index 0000000..24d858f --- /dev/null +++ b/.github/workflows/release.yml @@ -0,0 +1,65 @@ +name: Publish verified immutable runtime +on: + workflow_dispatch: + inputs: + producer_run: + description: Successful exact-source security gate run + required: true + type: string +permissions: + contents: write + actions: read + packages: write +jobs: + publish: + runs-on: ubuntu-24.04 + timeout-minutes: 30 + env: + GH_TOKEN: ${{ github.token }} + PRODUCER_RUN: ${{ inputs.producer_run }} + RELEASE_TAG: v0.7.3 + steps: + - uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 + with: + ref: v0.7.3 + fetch-depth: 0 + persist-credentials: false + - name: Verify immutable tag and successful producer + shell: bash + run: | + set -euo pipefail + [[ "$PRODUCER_RUN" =~ ^[0-9]+$ ]] + test "$(git cat-file -t "refs/tags/$RELEASE_TAG")" = tag + test "$(git rev-parse HEAD)" = "$(git rev-parse "refs/tags/$RELEASE_TAG^{}")" + gh api "repos/$GITHUB_REPOSITORY/actions/runs/$PRODUCER_RUN" > "$RUNNER_TEMP/producer.json" + jq -e '.status == "completed" and .conclusion == "success" and .path == ".github/workflows/security-release-gate.yml"' "$RUNNER_TEMP/producer.json" + source=$(jq -r .head_sha "$RUNNER_TEMP/producer.json") + [[ "$source" =~ ^[0-9a-f]{40}$ ]] + tree=$(gh api "repos/$GITHUB_REPOSITORY/commits/$source" --jq .commit.tree.sha) + test "$tree" = "$(git rev-parse 'HEAD^{tree}')" + gh run download "$PRODUCER_RUN" --repo "$GITHUB_REPOSITORY" --name "security-runtime-$source" --dir dist/security-runtime + test "$(cat dist/security-runtime/source-revision.txt)" = "$source" + (cd dist/security-runtime && sha256sum --check SHA256SUMS) + - name: Publish exact scanned image and release assets + shell: bash + run: | + set -euo pipefail + gzip -dc dist/security-runtime/images.tar.gz | docker load + printf '%s' "$GH_TOKEN" | docker login ghcr.io -u "$GITHUB_ACTOR" --password-stdin + trap 'docker logout ghcr.io >/dev/null 2>&1 || true' EXIT + source_image='pasturestack/kubernetes-agent:v0.7.3' + remote_image="ghcr.io/pasturestack/kubernetes-agent:$RELEASE_TAG" + if docker manifest inspect "$remote_image" >/dev/null 2>"$RUNNER_TEMP/manifest-error"; then + echo "Refusing to replace an existing immutable image tag: $remote_image" >&2; exit 1 + else + grep -Eq 'manifest unknown|no such manifest' "$RUNNER_TEMP/manifest-error" + fi + docker tag "$source_image" "$remote_image" + docker push "$remote_image" | tee "$RUNNER_TEMP/push-log" + pushed=$(awk '/digest: sha256:/{for(i=1;i<=NF;i++) if($i=="digest:") print $(i+1)}' "$RUNNER_TEMP/push-log") + readback=$(docker buildx imagetools inspect "$remote_image" | awk '$1=="Digest:"{print $2; exit}') + test "$pushed" = "$readback" + [[ "$readback" =~ ^sha256:[0-9a-f]{64}$ ]] + source=$(cat dist/security-runtime/source-revision.txt) + jq -n --arg image "$remote_image" --arg digest "$readback" --arg source "$source" '{image:$image,digest:$digest,source:$source}' > dist/security-runtime/registry-images.json + gh release create "$RELEASE_TAG" --repo "$GITHUB_REPOSITORY" --verify-tag --title "$GITHUB_REPOSITORY $RELEASE_TAG" --notes "Exact tested and scanned producer $source, run $PRODUCER_RUN. The immutable release tag has the same source tree. No deployment." dist/security-runtime/* diff --git a/.github/workflows/security-release-gate.yml b/.github/workflows/security-release-gate.yml index c0ab624..6fe7548 100644 --- a/.github/workflows/security-release-gate.yml +++ b/.github/workflows/security-release-gate.yml @@ -312,6 +312,24 @@ jobs: jq -e '.passed == true and .kubernetes == "1.36.4" and .clientGo == "0.36.4"' \ dist/kubernetes-integration.json >/dev/null + - name: Retain exact runtime for immutable release + shell: bash + run: | + set -euo pipefail + mkdir -p dist/security-runtime + docker image inspect "$IMAGE" > dist/security-runtime/images.json + docker save "$IMAGE" | gzip -n > dist/security-runtime/images.tar.gz + cp dist/runtime-scan.json dist/runtime-sbom.cdx.json dist/security-runtime/ + printf '%s\n' "$GITHUB_SHA" > dist/security-runtime/source-revision.txt + (cd dist/security-runtime && sha256sum -- * > SHA256SUMS) + - name: Upload exact runtime release bytes + uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1 + with: + name: security-runtime-${{ github.sha }} + path: dist/security-runtime/ + if-no-files-found: error + retention-days: 14 + - name: Remove verification-only images and cache if: always() shell: bash From 092f1ce5499c4151d0780591cf9a2b71c6d5267e Mon Sep 17 00:00:00 2001 From: chen21019 <19357113+chen21019@users.noreply.github.com> Date: Fri, 23 Oct 2026 21:20:28 +0800 Subject: [PATCH 8/8] Apply official fixes to installed Dapper OS packages --- Dockerfile.dapper | 3 ++ package/ubuntu-security-packages.lock | 34 ++++++++++++++++ scripts/install-ubuntu-security-updates | 54 +++++++++++++++++++++++++ 3 files changed, 91 insertions(+) create mode 100644 package/ubuntu-security-packages.lock create mode 100644 scripts/install-ubuntu-security-updates diff --git a/Dockerfile.dapper b/Dockerfile.dapper index 8f5155c..845c857 100644 --- a/Dockerfile.dapper +++ b/Dockerfile.dapper @@ -4,6 +4,8 @@ FROM ubuntu:26.04@sha256:2260313b31c8c011cd2eebe728008efac1b3982be73eb71348ea264 COPY --from=snapshot-ca-certificates /etc/ssl/certs/ca-certificates.crt /etc/ssl/certs/ca-certificates.crt COPY package/ubuntu-apt.lock /licenses/ubuntu-apt.lock +COPY package/ubuntu-security-packages.lock /licenses/ubuntu-security-packages.lock +COPY scripts/install-ubuntu-security-updates /usr/local/bin/install-ubuntu-security-updates ARG DAPPER_HOST_ARCH=amd64 ARG DOCKER_VERSION=29.9.2 @@ -39,6 +41,7 @@ RUN set -eux; \ test "$(dpkg-query -W -f='${Version}' ca-certificates)" = '20260816ubuntu0.26.04.1' && \ test ! -e /usr/share/ca-certificates/mozilla/emSign_ECC_Root_CA_-_G3.crt && \ rm -f /opt/pasturestack-ca-certificates.deb && \ + sh /usr/local/bin/install-ubuntu-security-updates /licenses/ubuntu-security-packages.lock /etc/ssl/certs/ca-certificates.crt && \ { \ printf 'snapshot\t%s\n' "${UBUNTU_APT_SNAPSHOT}"; \ dpkg-query -W -f='${binary:Package}\t${Version}\n' | LC_ALL=C sort; \ diff --git a/package/ubuntu-security-packages.lock b/package/ubuntu-security-packages.lock new file mode 100644 index 0000000..b0dfc09 --- /dev/null +++ b/package/ubuntu-security-packages.lock @@ -0,0 +1,34 @@ +# Official Ubuntu 26.04 security/updates snapshot: 20261023T000000Z +# Existing packages only; ABI series and unrelated packages are preserved. +bsdutils=1:2.41.3-3ubuntu2.2 +curl=8.18.0-1ubuntu2.8 +diffutils=1:3.12-1ubuntu0.1 +gnu-coreutils=9.7-3ubuntu2.1 +gpgv=2.4.8-4ubuntu3.1 +libattr1=1:2.5.2-4ubuntu0.1 +libblkid1=2.41.3-3ubuntu2.2 +libbz2-1.0=1.0.8-6ubuntu0.1 +libc-bin=2.43-2ubuntu2.4 +libc-gconv-modules-extra=2.43-2ubuntu2.4 +libc6=2.43-2ubuntu2.4 +libc6-dev=2.43-2ubuntu2.4 +libc-dev-bin=2.43-2ubuntu2.4 +libexpat1=2.7.4-1ubuntu0.2 +libcurl4t64=8.18.0-1ubuntu2.8 +libgcrypt20=1.12.0-2ubuntu1.1 +libmount1=2.41.3-3ubuntu2.2 +libperl5.40=5.40.1-7ubuntu0.3 +libsmartcols1=2.41.3-3ubuntu2.2 +libssh2-1t64=1.11.1-1ubuntu0.26.04.4 +libssl3t64=3.5.5-1ubuntu3.7 +libuuid1=2.41.3-3ubuntu2.2 +linux-libc-dev=7.0.0-38.38 +login=1:4.16.0-2+really2.41.3-3ubuntu2.2 +mount=2.41.3-3ubuntu2.2 +openssl=3.5.5-1ubuntu3.7 +openssl-provider-legacy=3.5.5-1ubuntu3.7 +perl=5.40.1-7ubuntu0.3 +perl-base=5.40.1-7ubuntu0.3 +perl-modules-5.40=5.40.1-7ubuntu0.3 +util-linux=2.41.3-3ubuntu2.2 +zlib1g=1:1.3.dfsg+really1.3.1-1ubuntu3.2 diff --git a/scripts/install-ubuntu-security-updates b/scripts/install-ubuntu-security-updates new file mode 100644 index 0000000..a8630dd --- /dev/null +++ b/scripts/install-ubuntu-security-updates @@ -0,0 +1,54 @@ +#!/bin/sh +# Same-series official micro-updates. Never install a package just for a scan. +set -eu +test "$#" -eq 2 || { echo 'usage: security-updates LOCK TRUSTED_CA_BUNDLE' >&2; exit 2; } +lock=$1 +trusted_ca=$2 +. /etc/os-release +test "$ID:$VERSION_ID" = ubuntu:26.04 +test -s "$lock" +test -s "$trusted_ca" +tmp=$(mktemp -d) +trap 'rm -rf "$tmp"' EXIT HUP INT TERM +dpkg-query -W -f='${binary:Package}\t${db:Status-Status}\n' | LC_ALL=C sort > "$tmp/before" +set -- +while IFS= read -r entry || test -n "$entry"; do + case "$entry" in ''|'#'*) continue;; esac + case "$entry" in *[!a-zA-Z0-9.:+~=_-]*) echo "Invalid lock entry" >&2; exit 1;; esac + package=${entry%%=*} + version=${entry#*=} + test "$package" != "$version" + status=$(dpkg-query -W -f='${db:Status-Status}' "$package" 2>/dev/null || true) + test "$status" = installed || continue + installed=$(dpkg-query -W -f='${Version}' "$package") + # A newer base may already contain the fix; never downgrade it. + dpkg --compare-versions "$installed" ge "$version" && continue + set -- "$@" "$entry" +done < "$lock" +if test "$#" -gt 0; then + mkdir -p "$tmp/lists/partial" + printf 'Types: deb\nURIs: https://snapshot.ubuntu.com/ubuntu/20261023T000000Z\nSuites: resolute-updates resolute-security\nComponents: main\nSigned-By: /usr/share/keyrings/ubuntu-archive-keyring.gpg\nSnapshot: no\n' > "$tmp/security.sources" + apt_security() { + apt-get -o Dir::Etc::sourcelist="$tmp/security.sources" \ + -o Dir::State::lists="$tmp/lists" \ + -o Dir::Cache::pkgcache="$tmp/pkgcache.bin" -o Dir::Cache::srcpkgcache="$tmp/srcpkgcache.bin" \ + -o Dir::Etc::sourceparts=- -o Acquire::https::CaInfo="$trusted_ca" \ + -o Acquire::https::Verify-Peer=true -o Acquire::https::Verify-Host=true \ + -o Acquire::AllowInsecureRepositories=false -o APT::Get::AllowUnauthenticated=false \ + -o Acquire::Retries=5 "$@" + } + apt_security update + DEBIAN_FRONTEND=noninteractive apt_security install -y --only-upgrade --no-install-recommends --no-remove "$@" +fi +while IFS= read -r entry || test -n "$entry"; do + case "$entry" in ''|'#'*) continue;; esac + package=${entry%%=*} + version=${entry#*=} + status=$(dpkg-query -W -f='${db:Status-Status}' "$package" 2>/dev/null || true) + test "$status" = installed || continue + dpkg --compare-versions "$(dpkg-query -W -f='${Version}' "$package")" ge "$version" +done < "$lock" +dpkg-query -W -f='${binary:Package}\t${db:Status-Status}\n' | LC_ALL=C sort > "$tmp/after" +# A security micro-update must not add/remove packages or change installed status. +cmp "$tmp/before" "$tmp/after" +printf 'UBUNTU_SECURITY_MICRO_UPDATES_OK\n'