Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 6 additions & 1 deletion config/golden-image-container-integration.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ schema_version: 1

image:
type: container
alias: nddev-u24-amd64-ctr-docker-runner-2.336.0-r20260801-b13
alias: nddev-u24-amd64-ctr-docker-runner-2.336.0-r20260801-b14
current_alias: nddev-ubuntu-24.04-amd64-container-docker-current
previous_alias: nddev-ubuntu-24.04-amd64-container-docker-previous
source_alias: nddev-source-ubuntu-24.04-amd64-container-r20260801
Expand Down Expand Up @@ -53,6 +53,11 @@ toolchains:
archive: bun-linux-x64.zip
download_url: https://github.com/oven-sh/bun/releases/download/bun-v1.3.14/bun-linux-x64.zip
archive_sha256: 951ee2aee855f08595aeec6225226a298d3fea83a3dcd6465c09cbccdf7e848f
- name: codeql
version: 2.26.4
archive: codeql-bundle-linux64.tar.gz
download_url: https://github.com/github/codeql-action/releases/download/codeql-bundle-v2.26.4/codeql-bundle-linux64.tar.gz
archive_sha256: 48e1ab8b874d57bd6fd7c90fefee75addc5a45e9bd063982df9beb45a62dd5d3
- name: go
version: 1.26.6
archive: go1.26.6.linux-amd64.tar.gz
Expand Down
7 changes: 6 additions & 1 deletion config/golden-image-container.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ schema_version: 1

image:
type: container
alias: nddev-ubuntu-24.04-amd64-container-runner-2.336.0-r20260801-b20
alias: nddev-ubuntu-24.04-amd64-container-runner-2.336.0-r20260801-b21
current_alias: nddev-ubuntu-24.04-amd64-container-current
previous_alias: nddev-ubuntu-24.04-amd64-container-previous
source_alias: nddev-source-ubuntu-24.04-amd64-container-r20260801
Expand Down Expand Up @@ -53,6 +53,11 @@ toolchains:
archive: bun-linux-x64.zip
download_url: https://github.com/oven-sh/bun/releases/download/bun-v1.3.14/bun-linux-x64.zip
archive_sha256: 951ee2aee855f08595aeec6225226a298d3fea83a3dcd6465c09cbccdf7e848f
- name: codeql
version: 2.26.4
archive: codeql-bundle-linux64.tar.gz
download_url: https://github.com/github/codeql-action/releases/download/codeql-bundle-v2.26.4/codeql-bundle-linux64.tar.gz
archive_sha256: 48e1ab8b874d57bd6fd7c90fefee75addc5a45e9bd063982df9beb45a62dd5d3
- name: go
version: 1.26.6
archive: go1.26.6.linux-amd64.tar.gz
Expand Down
7 changes: 6 additions & 1 deletion config/golden-image-integration.yaml
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
schema_version: 1

image:
alias: nddev-ubuntu-24.04-amd64-docker-runner-2.336.0-r20260801-b16
alias: nddev-ubuntu-24.04-amd64-docker-runner-2.336.0-r20260801-b17
current_alias: nddev-ubuntu-24.04-amd64-docker-current
previous_alias: nddev-ubuntu-24.04-amd64-docker-previous
source_alias: nddev-source-ubuntu-24.04-amd64-r20260801
Expand Down Expand Up @@ -52,6 +52,11 @@ toolchains:
archive: bun-linux-x64.zip
download_url: https://github.com/oven-sh/bun/releases/download/bun-v1.3.14/bun-linux-x64.zip
archive_sha256: 951ee2aee855f08595aeec6225226a298d3fea83a3dcd6465c09cbccdf7e848f
- name: codeql
version: 2.26.4
archive: codeql-bundle-linux64.tar.gz
download_url: https://github.com/github/codeql-action/releases/download/codeql-bundle-v2.26.4/codeql-bundle-linux64.tar.gz
archive_sha256: 48e1ab8b874d57bd6fd7c90fefee75addc5a45e9bd063982df9beb45a62dd5d3
- name: go
version: 1.26.6
archive: go1.26.6.linux-amd64.tar.gz
Expand Down
7 changes: 6 additions & 1 deletion config/golden-image.yaml
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
schema_version: 1

image:
alias: nddev-ubuntu-24.04-amd64-runner-2.336.0-r20260801-b17
alias: nddev-ubuntu-24.04-amd64-runner-2.336.0-r20260801-b18
current_alias: nddev-ubuntu-24.04-amd64-current
previous_alias: nddev-ubuntu-24.04-amd64-previous
source_alias: nddev-source-ubuntu-24.04-amd64-r20260801
Expand Down Expand Up @@ -52,6 +52,11 @@ toolchains:
archive: bun-linux-x64.zip
download_url: https://github.com/oven-sh/bun/releases/download/bun-v1.3.14/bun-linux-x64.zip
archive_sha256: 951ee2aee855f08595aeec6225226a298d3fea83a3dcd6465c09cbccdf7e848f
- name: codeql
version: 2.26.4
archive: codeql-bundle-linux64.tar.gz
download_url: https://github.com/github/codeql-action/releases/download/codeql-bundle-v2.26.4/codeql-bundle-linux64.tar.gz
archive_sha256: 48e1ab8b874d57bd6fd7c90fefee75addc5a45e9bd063982df9beb45a62dd5d3
- name: go
version: 1.26.6
archive: go1.26.6.linux-amd64.tar.gz
Expand Down
1 change: 1 addition & 0 deletions internal/imagebuild/assets/docker-provision.sh
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,7 @@ jq -n --arg storage_driver "${GHA_DOCKER_STORAGE_DRIVER}" '({
"default-address-pools":[{"base":"172.30.0.0/16","size":24}],
"exec-opts":["native.cgroupdriver=systemd"],
"features":{"buildkit":true},
"registry-mirrors":["https://192.0.2.1:5001"],
"live-restore":false,
"log-driver":"local",
"log-opts":{"max-file":"3","max-size":"10m"},
Expand Down
20 changes: 17 additions & 3 deletions internal/imagebuild/assets/provision.sh
Original file line number Diff line number Diff line change
Expand Up @@ -237,9 +237,9 @@ toolchain_manifest="$(printf '%s' "${GHA_TOOLCHAINS_B64}" | base64 --decode)"
jq -e 'type == "array"' <<<"${toolchain_manifest}" >/dev/null
mapfile -t toolchain_names < <(jq -r '.[].name' <<<"${toolchain_manifest}")
toolchain_set="$(printf '%s\n' "${toolchain_names[@]}" | LC_ALL=C sort | paste -sd, -)"
if [[ "${toolchain_set}" != bun,gh,go,rustup,uv \
&& "${toolchain_set}" != bun,gh,go,node22,node24,node25,pnpm,rustup,uv,yarn \
&& "${toolchain_set}" != bun,flutter,gh,go,node22,node24,node25,pnpm,rustup,uv,yarn ]]; then
if [[ "${toolchain_set}" != bun,codeql,gh,go,rustup,uv \
&& "${toolchain_set}" != bun,codeql,gh,go,node22,node24,node25,pnpm,rustup,uv,yarn \
&& "${toolchain_set}" != bun,codeql,flutter,gh,go,node22,node24,node25,pnpm,rustup,uv,yarn ]]; then
echo "toolchain manifest does not pin the exact baked set" >&2
exit 1
fi
Expand All @@ -254,6 +254,20 @@ for toolchain_name in "${toolchain_names[@]}"; do
echo "${toolchain_sha256} ${toolchain_archive}" | sha256sum --check --strict
toolchain_scratch="$(mktemp -d /var/tmp/gha-toolchain.XXXXXXXXXX)"
case "${toolchain_name}" in
codeql)
# The action resolves ${runner_tool_cache}/CodeQL/0.0.0-codeql-bundle-v<ver>
# with an x64.complete marker beside x64/, and prefers it over the 800 MB
# network download an ephemeral runner would otherwise repeat every
# analyze job.
codeql_root="${runner_tool_cache}/CodeQL/0.0.0-codeql-bundle-v${toolchain_version}"
install -d -o runner -g runner -m 0755 "${runner_tool_cache}/CodeQL" \
"${codeql_root}" "${codeql_root}/x64"
tar --extract --gzip --file "${toolchain_archive}" \
--directory "${codeql_root}/x64" --no-same-owner --no-same-permissions
chown -R runner:runner "${codeql_root}"
install -o runner -g runner -m 0644 /dev/null "${codeql_root}/x64.complete"
[[ "$(runuser -u runner -- "${codeql_root}/x64/codeql/codeql" version --format=terse)" == "${toolchain_version}" ]]
;;
bun)
unzip -q "${toolchain_archive}" -d "${toolchain_scratch}"
install -o root -g root -m 0755 \
Expand Down
8 changes: 7 additions & 1 deletion internal/imagebuild/assets/smoke-integration.sh
Original file line number Diff line number Diff line change
Expand Up @@ -88,14 +88,20 @@ runner_tool_cache="$(jq -er .runner_tool_cache /etc/nddev/image-build.json)"
[[ "${runner_tool_cache}" == /home/runner/actions-runner/_work/_tool ]]
smoke_toolchains="$(printf '%s' "${GHA_TOOLCHAINS_B64}" | base64 --decode)"
mapfile -t smoke_toolchain_names < <(jq -r '.[].name' <<<"${smoke_toolchains}")
[[ "$(printf '%s\n' "${smoke_toolchain_names[@]}" | LC_ALL=C sort | paste -sd, -)" == bun,gh,go,node22,node24,node25,pnpm,rustup,uv,yarn ]]
[[ "$(printf '%s\n' "${smoke_toolchain_names[@]}" | LC_ALL=C sort | paste -sd, -)" == bun,codeql,gh,go,node22,node24,node25,pnpm,rustup,uv,yarn ]]
for smoke_toolchain in "${smoke_toolchain_names[@]}"; do
entry="$(jq -ce --arg name "${smoke_toolchain}" '.[] | select(.name == $name)' <<<"${smoke_toolchains}")"
expected_version="$(jq -er .version <<<"${entry}")"
expected_sha256="$(jq -er .archive_sha256 <<<"${entry}")"
[[ "$(jq -er --arg name "${smoke_toolchain}" '.toolchains[$name].version' /etc/nddev/image-build.json)" == "${expected_version}" ]]
[[ "$(jq -er --arg name "${smoke_toolchain}" '.toolchains[$name].archive_sha256' /etc/nddev/image-build.json)" == "${expected_sha256}" ]]
case "${smoke_toolchain}" in
codeql)
codeql_root="${runner_tool_cache}/CodeQL/0.0.0-codeql-bundle-v${expected_version}"
test -f "${codeql_root}/x64.complete"
[[ "$(stat --format='%U' -- "${codeql_root}/x64/codeql/codeql")" == runner ]]
[[ "$(runuser -u runner -- "${codeql_root}/x64/codeql/codeql" version --format=terse)" == "${expected_version}" ]]
;;
bun)
[[ "$(bun --version)" == "${expected_version}" ]]
# The path oven-sh/setup-bun probes before deciding to download.
Expand Down
12 changes: 9 additions & 3 deletions internal/imagebuild/assets/smoke.sh
Original file line number Diff line number Diff line change
Expand Up @@ -64,16 +64,22 @@ runner_tool_cache="$(jq -er .runner_tool_cache /etc/nddev/image-build.json)"
smoke_toolchains="$(printf '%s' "${GHA_TOOLCHAINS_B64}" | base64 --decode)"
mapfile -t smoke_toolchain_names < <(jq -r '.[].name' <<<"${smoke_toolchains}")
smoke_toolchain_set="$(printf '%s\n' "${smoke_toolchain_names[@]}" | LC_ALL=C sort | paste -sd, -)"
[[ "${smoke_toolchain_set}" == bun,gh,go,rustup,uv \
|| "${smoke_toolchain_set}" == bun,gh,go,node22,node24,node25,pnpm,rustup,uv,yarn \
|| "${smoke_toolchain_set}" == bun,flutter,gh,go,node22,node24,node25,pnpm,rustup,uv,yarn ]]
[[ "${smoke_toolchain_set}" == bun,codeql,gh,go,rustup,uv \
|| "${smoke_toolchain_set}" == bun,codeql,gh,go,node22,node24,node25,pnpm,rustup,uv,yarn \
|| "${smoke_toolchain_set}" == bun,codeql,flutter,gh,go,node22,node24,node25,pnpm,rustup,uv,yarn ]]
for smoke_toolchain in "${smoke_toolchain_names[@]}"; do
entry="$(jq -ce --arg name "${smoke_toolchain}" '.[] | select(.name == $name)' <<<"${smoke_toolchains}")"
expected_version="$(jq -er .version <<<"${entry}")"
expected_sha256="$(jq -er .archive_sha256 <<<"${entry}")"
[[ "$(jq -er --arg name "${smoke_toolchain}" '.toolchains[$name].version' /etc/nddev/image-build.json)" == "${expected_version}" ]]
[[ "$(jq -er --arg name "${smoke_toolchain}" '.toolchains[$name].archive_sha256' /etc/nddev/image-build.json)" == "${expected_sha256}" ]]
case "${smoke_toolchain}" in
codeql)
codeql_root="${runner_tool_cache}/CodeQL/0.0.0-codeql-bundle-v${expected_version}"
test -f "${codeql_root}/x64.complete"
[[ "$(stat --format='%U' -- "${codeql_root}/x64/codeql/codeql")" == runner ]]
[[ "$(runuser -u runner -- "${codeql_root}/x64/codeql/codeql" version --format=terse)" == "${expected_version}" ]]
;;
bun)
[[ "$(bun --version)" == "${expected_version}" ]]
# The path oven-sh/setup-bun probes before deciding to download.
Expand Down
2 changes: 1 addition & 1 deletion internal/imagebuild/orchestrator_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -164,7 +164,7 @@ func TestRecipeFingerprintIsDeterministic(t *testing.T) {
// alias is part of the recipe, so a manifest whose contents changed under an
// unchanged alias would otherwise ask the builder to produce different bytes
// for a name that is already promoted.
if first != "sha256:4cc00e2ee72d7ed4646f84229f3b6a2d5c6d4aeeb05aae29f15f4e1bd381eeb1" {
if first != "sha256:ba41e9cfcebc856bfa3ee0b75f12d4e3f7a9b85598308491ea70f72b2fe2baff" {
t.Fatalf("deployed standard recipe fingerprint drifted: %q", first)
}
smoke, err := SmokeFingerprint(plan)
Expand Down
3 changes: 2 additions & 1 deletion internal/imagemanifest/manifest_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ func TestRepositoryManifestIsValidAndPinned(t *testing.T) {
if !strings.HasPrefix(fingerprint, "sha256:") || len(fingerprint) != len("sha256:")+64 {
t.Fatalf("unexpected fingerprint %q", fingerprint)
}
if fingerprint != "sha256:4c76a6c764a529923aa4dcd0327863aa43a4700b3a5e5d99aa30426a7db96217" {
if fingerprint != "sha256:47a1569f94fa824b69de51d5ee917a5e8b72cc4a4c9b727c214019f891615a56" {
t.Fatalf("standard manifest fingerprint drifted: %q", fingerprint)
}
}
Expand Down Expand Up @@ -71,6 +71,7 @@ func assertBakedToolchains(t *testing.T, manifest Manifest) {
t.Helper()
wanted := map[string]struct{ version, archiveSHA256 string }{
"bun": {"1.3.14", "951ee2aee855f08595aeec6225226a298d3fea83a3dcd6465c09cbccdf7e848f"},
"codeql": {"2.26.4", "48e1ab8b874d57bd6fd7c90fefee75addc5a45e9bd063982df9beb45a62dd5d3"},
"gh": {"2.97.0", "a2c9b8497e1f85b1ad0dfcb78b5a622e098801b8e461e459e88e1ee12f018112"},
"go": {"1.26.6", "708effb774be8237570d0add163225abbdfaf4fca28b2611df167beba4feef89"},
"node22": {"22.23.2", "d60acfe00a2932254bb0ad20e01b0d74397a0875595de719654b214f4b03f307"},
Expand Down
2 changes: 1 addition & 1 deletion internal/imagemanifest/types.go
Original file line number Diff line number Diff line change
Expand Up @@ -122,7 +122,7 @@ func BakedToolchains() []string {
// was unreachable in the shipped image. The default channel serves jobs
// that call cargo directly, and actions-rust-lang/setup-rust-toolchain
// resolves rust-toolchain.toml channels through rustup either way.
return []string{"bun", "gh", "go", "node22", "node24", "node25", "pnpm", "rustup", "uv", "yarn"}
return []string{"bun", "codeql", "gh", "go", "node22", "node24", "node25", "pnpm", "rustup", "uv", "yarn"}
}

// OptionalToolchains may be pinned by an image that needs them and omitted by
Expand Down
10 changes: 10 additions & 0 deletions internal/imagemanifest/validate.go
Original file line number Diff line number Diff line change
Expand Up @@ -112,6 +112,16 @@ var toolchainAssets = map[string]struct {
return "/rustup/archive/" + version + "/x86_64-unknown-linux-gnu/rustup-init"
},
},
// The CodeQL bundle the action would otherwise download on every analyze
// job of an ephemeral runner: 800 MB per run, resolved from the runner
// tool cache when present.
"codeql": {
Host: "github.com",
Archive: func(string) string { return "codeql-bundle-linux64.tar.gz" },
Path: func(version string) string {
return "/github/codeql-action/releases/download/codeql-bundle-v" + version + "/codeql-bundle-linux64.tar.gz"
},
},
"uv": {
Host: "github.com",
Archive: func(string) string { return "uv-x86_64-unknown-linux-gnu.tar.gz" },
Expand Down
2 changes: 1 addition & 1 deletion internal/imageplan/plan_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -82,7 +82,7 @@ func TestBuildProducesDeterministicBoundedPlan(t *testing.T) {
}
// The baked set plus the optional Flutter SDK this manifest pins, still
// sorted: the plan's ordering is what makes the recipe fingerprint stable.
if !slices.Equal(names, []string{"bun", "flutter", "gh", "go", "node22", "node24", "node25", "pnpm", "rustup", "uv", "yarn"}) {
if !slices.Equal(names, []string{"bun", "codeql", "flutter", "gh", "go", "node22", "node24", "node25", "pnpm", "rustup", "uv", "yarn"}) {
t.Fatalf("plan toolchains are not the canonical sorted set: %v", names)
}
if first.CompilerCache.Name != "sccache" || first.CompilerCache.Version != "v0.17.0" ||
Expand Down
1 change: 1 addition & 0 deletions internal/repositorycontract/external_downloads_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ func TestEveryNetworkBootstrapSurfaceIsClassified(t *testing.T) {
"internal/garmproviderincus/provider/incus.go",
"internal/garmproviderincus/provider/specs.go",
"internal/imagebuild/assets/container-provision.sh",
"internal/imagebuild/assets/docker-provision.sh",
"internal/imagebuild/assets/provision.sh",
"internal/imagebuild/assets/smoke-integration.sh",
"internal/imagebuild/assets/smoke.sh",
Expand Down