CONSOLE-5293: Update Dockerfile.downloads for 4.22 and add RHEL 8/9 oc binaries#16455
CONSOLE-5293: Update Dockerfile.downloads for 4.22 and add RHEL 8/9 oc binaries#16455jhadvig wants to merge 1 commit into
Conversation
…c binaries Update base images from 4.18 to 4.22 so the console-downloads image builds in CI against the current release. Add oc.rhel8 and oc.rhel9 binary entries for all Linux architectures (amd64, arm64, ppc64le, s390x) to match the console-operator change (OCPBUGS-57468). Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
|
@jhadvig: This pull request references CONSOLE-5293 which is a valid jira issue. Warning: The referenced jira issue has an invalid target version for the target branch this PR targets: expected the story to target the "5.0.0" version, but no target version was set. DetailsIn response to this:
Instructions for interacting with me using PR comments are available here. If you have questions or suggestions related to my behavior, please file an issue against the openshift-eng/jira-lifecycle-plugin repository. |
|
[APPROVALNOTIFIER] This PR is APPROVED This pull-request has been approved by: jhadvig The full list of commands accepted by this bot can be found here. The pull request process is described here DetailsNeeds approval from an approver in each of these files:
Approvers can indicate their approval by writing |
📝 WalkthroughWalkthroughThis PR refactors the OpenShift Console downloads server to generate binary archives asynchronously. It extends the artifact configuration to include RHEL 8 and RHEL 9 variants across multiple architectures (amd64, arm64, ppc64le, s390x), upgrades container base images to newer versions, and introduces a synchronization mechanism that allows non-archive HTTP requests to be served immediately while blocking archive requests until tar/zip files are ready. The implementation uses concurrent goroutines to create archives in the background, a coordination channel to signal completion, and an HTTP handler wrapper that enforces request-level synchronization. 🚥 Pre-merge checks | ✅ 11 | ❌ 1❌ Failed checks (1 warning)
✅ Passed checks (11 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. ✨ Finishing Touches🧪 Generate unit tests (beta)
Comment |
There was a problem hiding this comment.
Actionable comments posted: 3
🧹 Nitpick comments (1)
cmd/downloads/config/downloads_config_test.go (1)
109-126: ⚡ Quick winAvoid order-coupled assertions in generated entries.
Asserting
content[1]/content[2]makes this test fragile to harmless ordering changes. Assert by URL key instead.Suggested refactor
- linux := content[1] - if linux.URL != "amd64/linux/oc" { - t.Errorf("expected URL %q, got %q", "amd64/linux/oc", linux.URL) - } - if linux.TarURL != "amd64/linux/oc.tar" { - t.Errorf("expected TarURL %q, got %q", "amd64/linux/oc.tar", linux.TarURL) - } - - win := content[2] - if win.URL != "amd64/windows/oc.exe" { - t.Errorf("expected URL %q, got %q", "amd64/windows/oc.exe", win.URL) - } - if win.TarURL != "amd64/windows/oc.tar" { - t.Errorf("expected TarURL %q, got %q", "amd64/windows/oc.tar", win.TarURL) - } - if win.ZipURL != "amd64/windows/oc.zip" { - t.Errorf("expected ZipURL %q, got %q", "amd64/windows/oc.zip", win.ZipURL) - } + byURL := map[string]ListItemLink{} + for _, item := range content { + byURL[item.URL] = item + } + + linux, ok := byURL["amd64/linux/oc"] + if !ok { + t.Fatalf("missing linux entry") + } + if linux.TarURL != "amd64/linux/oc.tar" { + t.Errorf("expected TarURL %q, got %q", "amd64/linux/oc.tar", linux.TarURL) + } + + win, ok := byURL["amd64/windows/oc.exe"] + if !ok { + t.Fatalf("missing windows entry") + } + if win.TarURL != "amd64/windows/oc.tar" { + t.Errorf("expected TarURL %q, got %q", "amd64/windows/oc.tar", win.TarURL) + } + if win.ZipURL != "amd64/windows/oc.zip" { + t.Errorf("expected ZipURL %q, got %q", "amd64/windows/oc.zip", win.ZipURL) + }🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@cmd/downloads/config/downloads_config_test.go` around lines 109 - 126, The test currently relies on fixed indices (content[1], content[2]) for entries (variables linux, win) which makes it fragile; instead, build a lookup from the content slice keyed by the entry.URL (or find entries by matching URL) and then assert TarURL/ZipURL values from that map/lookup for the keys "amd64/linux/oc" and "amd64/windows/oc.exe"; update assertions that reference linux.URL/linux.TarURL and win.URL/win.TarURL/win.ZipURL to use the mapped entries so the test no longer depends on ordering of the content slice.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@cmd/downloads/config/downloads_config_test.go`:
- Around line 158-161: The test currently ignores errors from os.Open and from
Close calls and should mirror production error handling: change the os.Open call
used before tar.NewReader to capture and check the error (e.g., handle the
returned error and fail the test on open failure), defer closing the opened file
and check the error returned by Close (or capture Close error from the deferred
call), and ensure the tar reader's tr.Next() error (the err after hdr, err :=
tr.Next()) is checked and handled; likewise move the zip reader Close
(zr.Close()) into a defer and check its returned error. Update the code around
os.Open, tar.NewReader/tr.Next, and zr.Close to perform proper error checks and
use defer for cleanup.
In `@cmd/downloads/config/downloads_config.go`:
- Around line 383-387: The final goroutine currently always logs "All archives
created successfully" after wg.Wait() and closing c.archivesReady; change it to
track whether any createArchive call failed (e.g., set a shared failure flag via
an atomic.Bool or send errors to an errs channel read before logging) and only
emit the success message when no failures were recorded; otherwise log a
distinct error/warning indicating that one or more archive creations failed.
Update the goroutine that calls wg.Wait() and close(c.archivesReady) to inspect
that failure indicator (or aggregated errors) and choose the appropriate log
message, referencing createArchive, c.archivesReady, and the wg.Wait()
goroutine.
In `@Dockerfile.downloads`:
- Around line 1-3: Replace the mutable UBI image tag used in the Dockerfile by
updating the image reference
"registry.access.redhat.com/ubi9/ubi-minimal:latest" to a stable versioned tag
(for example "registry.access.redhat.com/ubi9/ubi-minimal:9.7") so builds are
reproducible and consistent with the other versioned images like
"quay.io/openshift/origin-cli-artifacts:4.22" and
"registry.ci.openshift.org/ocp/builder:rhel-9-golang-1.25-openshift-4.22";
locate the line containing the
"registry.access.redhat.com/ubi9/ubi-minimal:latest" image and replace ":latest"
with the chosen stable version.
---
Nitpick comments:
In `@cmd/downloads/config/downloads_config_test.go`:
- Around line 109-126: The test currently relies on fixed indices (content[1],
content[2]) for entries (variables linux, win) which makes it fragile; instead,
build a lookup from the content slice keyed by the entry.URL (or find entries by
matching URL) and then assert TarURL/ZipURL values from that map/lookup for the
keys "amd64/linux/oc" and "amd64/windows/oc.exe"; update assertions that
reference linux.URL/linux.TarURL and win.URL/win.TarURL/win.ZipURL to use the
mapped entries so the test no longer depends on ordering of the content slice.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Repository YAML (base), Central YAML (inherited)
Review profile: CHILL
Plan: Enterprise
Run ID: c6874bf1-9a63-4e2c-aa91-08a658853e0d
📒 Files selected for processing (5)
Dockerfile.downloadscmd/downloads/config/defaultArtifactsConfig.yamlcmd/downloads/config/downloads_config.gocmd/downloads/config/downloads_config_test.gocmd/downloads/main.go
📜 Review details
🧰 Additional context used
📓 Path-based instructions (2)
**/*.{yaml,yml,go}
📄 CodeRabbit inference engine (Custom checks)
When deployment manifests, operator code, or controllers are added/modified, check for scheduling constraints assuming standard HA topology (3+ CP nodes, dedicated workers). Flag: required pod anti-affinity with hostname topology key, pod topology spread with DoNotSchedule and hostname key, replica counts derived from node count, nodeSelector/affinity targeting control-plane nodes, broad tolerations that could schedule to resource-constrained arbiter nodes, assuming dedicated worker nodes exist, or PodDisruptionBudgets designed for 3+ nodes. Consider SNO (1 node), DualReplica (2 CP nodes), HighlyAvailableArbiter (2 CP + 1 arbiter), and External (HyperShift) topologies
Files:
cmd/downloads/main.gocmd/downloads/config/downloads_config_test.gocmd/downloads/config/downloads_config.gocmd/downloads/config/defaultArtifactsConfig.yaml
**/*_test.go
📄 CodeRabbit inference engine (Custom checks)
**/*_test.go: When new Ginkgo e2e tests are added, check for IPv4 assumptions: hardcoded IPv4 addresses (10.0.0.1, 192.168.1.1, 172.16.0.0/12), IPv4 localhost (127.0.0.1 without ::1), IPv4-only IP parsing, hardcoded IPv4 CIDRs in Service/Endpoint objects, hardcoded net.ParseIP/ParseCIDR values, IPv4-only pod/node IP assumptions, IPv4-only network policies, and URLs built without brackets for IPv6 (use net.JoinHostPort instead)
When new Ginkgo e2e tests are added, check for external connectivity requirements: connections to public internet hosts, pulling images from public registries without mirrors, downloading from external URLs, DNS resolution of public hostnames, and connections to external APIs/services outside the cluster. If requiring external connectivity that cannot be adapted, add [Skipped:Disconnected] to test name
When new Ginkgo e2e tests are added, check for usage of unavailable MicroShift APIs: Project/ProjectRequest, Build/BuildConfig, DeploymentConfig, ClusterOperator, ClusterVersion, Etcd operator, CSV/OLM resources, MachineSet/Machine/MachineHealthCheck, ClusterAutoscaler, Console, Monitoring stack, ImageRegistry operator, Samples operator, OperatorHub/CatalogSource, CloudCredential, Storage operator, Network operator CRDs, and any OpenShift API except Route and SecurityContextConstraints. Also flag references to namespaces openshift-kube-apiserver, openshift-kube-controller-manager, openshift-kube-scheduler. If flagged and test is intentional, use [Skipped:MicroShift] label or [apigroup:...] tag or guard with exutil.IsMicroShiftCluster() check
OpenShift Tests Extension (OTE) binaries must output valid JSON to stdout at process level. Flag any non-JSON stdout writes in main(), init(), TestMain(), BeforeSuite(), AfterSuite(), SynchronizedBeforeSuite(), RunSpecs() setup, or top-level var/const initializers. Common violations: klog writing to stdout (use klog.SetOutput(os.Stderr) or klog.LogToStderr(true)), fmt.Print/Println/Printf to stdout in main...
Files:
cmd/downloads/config/downloads_config_test.go
🪛 golangci-lint (2.12.2)
cmd/downloads/config/downloads_config_test.go
[error] 161-161: Error return value of f.Close is not checked
(errcheck)
[error] 205-205: net/http/httptest.NewRequest must not be called. use net/http/httptest.NewRequestWithContext
(noctx)
[error] 216-216: net/http/httptest.NewRequest must not be called. use net/http/httptest.NewRequestWithContext
(noctx)
[error] 258-258: net/http/httptest.NewRequest must not be called. use net/http/httptest.NewRequestWithContext
(noctx)
🔀 Multi-repo context openshift/console-operator
Findings for openshift/console-operator:
-
pkg/console/controllers/clidownloads/controller.go: entries adding RHEL variants (display name, path, archive name):
- lines with {"Linux for x86_64 - RHEL 8", "amd64/linux", "oc.rhel8.tar"} and {"Linux for x86_64 - RHEL 9", "amd64/linux", "oc.rhel9.tar"}; likewise for arm64, ppc64le, s390x. [::openshift/console-operator::pkg/console/controllers/clidownloads/controller.go]
-
pkg/console/controllers/clidownloads/controller_test.go: tests expecting Href links to oc.rhel8.tar and oc.rhel9.tar for amd64/arm64/ppc64le/s390x. [::openshift/console-operator::pkg/console/controllers/clidownloads/controller_test.go]
-
bindata/assets/deployments/downloads-deployment.yaml: deployment asset includes file paths for oc.rhel8 and oc.rhel9 under /usr/share/openshift/... for amd64, arm64, ppc64le, s390x and comment about stripping .exe vs keeping oc.rhel8. [::openshift/console-operator::bindata/assets/deployments/downloads-deployment.yaml]
-
test/e2e/downloads_test.go and other tests reference the clidownloads controller and downloads deployment; e2e tests may exercise the new RHEL variants. [::openshift/console-operator::test/e2e/downloads_test.go]
Implication: The console-operator repo already contains support and tests for oc.rhel8/oc.rhel9 artifacts and controller logic; the PR’s changes to console downloads (adding RHEL 8/9 artifacts and display/handler behavior) align with existing consumers and deployment assets in this repo. [::openshift/console-operator::]
🔇 Additional comments (11)
cmd/downloads/config/defaultArtifactsConfig.yaml (1)
5-10: LGTM!Also applies to: 20-25, 32-46
cmd/downloads/config/downloads_config.go (5)
8-12: LGTM!
61-62: LGTM!
218-228: LGTM!
343-351: LGTM!
390-401: LGTM!cmd/downloads/main.go (2)
33-34: LGTM!Also applies to: 41-41
19-19: 💤 Low valueThe premise is inaccurate.
cmd/downloads/main.gois a new file added in this PR (status: Added), not a modification of an existing file. There was no prior port value to change from. The port 8080 is the initial default and aligns correctly with the console-operator's existing deployment expectations (confirmed in console-operator's downloads-deployment.yaml).No coordination issue exists—the operator already expects port 8080.
> Likely an incorrect or invalid review comment.Dockerfile.downloads (1)
33-33: LGTM!cmd/downloads/config/downloads_config_test.go (2)
17-107: LGTM!Also applies to: 129-157, 168-204, 241-257, 262-269
205-205: ⚡ Quick winThis review comment does not apply to this project.
The openshift/console project does not enforce the
noctxlinting rule. No.golangci.ymlor Go linting configuration exists in the repository, and the STYLEGUIDE.md (which documents Go best practices) makes no mention of requiring context withhttptest.NewRequest. The pattern of usinghttptest.NewRequestwithout context is consistent throughout the codebase—includingpkg/olm/handler_test.go,pkg/server/robots_test.go, and other test files—establishing it as the project's standard convention.While using
httptest.NewRequestWithContext(context.Background(), ...)is a general Go best practice, it is not a linting requirement in this project and would not "fail lint gates."> Likely an incorrect or invalid review comment.
| f, _ := os.Open(tarPath) | ||
| tr := tar.NewReader(f) | ||
| hdr, err := tr.Next() | ||
| f.Close() |
There was a problem hiding this comment.
🧩 Analysis chain
🏁 Script executed:
#!/bin/bash
# Verify remaining unchecked open/close patterns in this test file
rg -n 'os\.Open\(|\.Close\(\)' --type go cmd/downloads/config/downloads_config_test.goRepository: openshift/console
Length of output: 126
🏁 Script executed:
#!/bin/bash
# Read the test file to see the full context around lines 158-180
sed -n '150,185p' cmd/downloads/config/downloads_config_test.go | cat -nRepository: openshift/console
Length of output: 1335
🏁 Script executed:
#!/bin/bash
# Check for errcheck or golangci-lint config
find . -maxdepth 2 -type f \( -name ".golangci.yml" -o -name "golangci.yaml" -o -name ".golangci.yaml" -o -name ".errcheck*" -o -name "Makefile" -o -name "go.mod" \) | head -20Repository: openshift/console
Length of output: 70
🏁 Script executed:
#!/bin/bash
# Check if errcheck or linting is mentioned in the repo
rg -l "errcheck|golangci" --type go --type yaml . | head -10Repository: openshift/console
Length of output: 605
🏁 Script executed:
#!/bin/bash
# Check for linting config at project root
ls -la | grep -E "^\.|Makefile|golangci|lint"Repository: openshift/console
Length of output: 43
🏁 Script executed:
#!/bin/bash
# Check if there's a Makefile with lint/test targets
head -100 Makefile 2>/dev/null | grep -E "lint|errcheck|vet|test" || echo "No Makefile or matches found"Repository: openshift/console
Length of output: 90
🏁 Script executed:
#!/bin/bash
# Check for CI configuration (GitHub Actions, etc.) that might run linting
find .github -type f -name "*.yml" -o -name "*.yaml" 2>/dev/null | head -5Repository: openshift/console
Length of output: 43
🏁 Script executed:
#!/bin/bash
# Check if there are other test files in the same directory with error handling patterns
ls -la cmd/downloads/config/ | grep testRepository: openshift/console
Length of output: 136
🏁 Script executed:
#!/bin/bash
# Look at error handling patterns in other test files in this project
rg -l 'os\.Open|\.Close\(\)' --type go cmd/downloads/ | head -5Repository: openshift/console
Length of output: 148
🏁 Script executed:
#!/bin/bash
# Check the non-test file for error handling patterns with file operations
rg -n 'os\.Open|\.Close\(\)' --type go cmd/downloads/config/downloads_config.go -A 2Repository: openshift/console
Length of output: 743
🏁 Script executed:
#!/bin/bash
# Check the full context of the tar and zip handling in the test to understand the complete picture
sed -n '155,185p' cmd/downloads/config/downloads_config_test.goRepository: openshift/console
Length of output: 890
Handle os.Open and Close errors in tar/zip verification.
The test ignores the error from os.Open() (line 158) and unchecked Close() calls (lines 161, 180), which violates error handling best practices and will fail errcheck. The production code properly checks errors after file operations; apply the same rigor here. Consider using defer for cleanup instead, matching the production pattern.
Suggested fix
- f, _ := os.Open(tarPath)
+ f, err := os.Open(tarPath)
+ if err != nil {
+ t.Errorf("failed to open tar %s: %v", tarPath, err)
+ continue
+ }
+ defer f.Close()
tr := tar.NewReader(f)
hdr, err := tr.Next()
- f.Close()
if err != nil {
t.Errorf("failed to read tar %s: %v", tarPath, err)
} else if hdr.Name != basename {Also check zr.Close() at line 180 (zip reader) — move it into a defer or check the error.
🧰 Tools
🪛 golangci-lint (2.12.2)
[error] 161-161: Error return value of f.Close is not checked
(errcheck)
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In `@cmd/downloads/config/downloads_config_test.go` around lines 158 - 161, The
test currently ignores errors from os.Open and from Close calls and should
mirror production error handling: change the os.Open call used before
tar.NewReader to capture and check the error (e.g., handle the returned error
and fail the test on open failure), defer closing the opened file and check the
error returned by Close (or capture Close error from the deferred call), and
ensure the tar reader's tr.Next() error (the err after hdr, err := tr.Next()) is
checked and handled; likewise move the zip reader Close (zr.Close()) into a
defer and check its returned error. Update the code around os.Open,
tar.NewReader/tr.Next, and zr.Close to perform proper error checks and use defer
for cleanup.
| go func() { | ||
| wg.Wait() | ||
| close(c.archivesReady) | ||
| klog.Info("All archives created successfully") | ||
| }() |
There was a problem hiding this comment.
Success message logged unconditionally, even when archive creation fails.
If any createArchive call fails, the error is logged but archivesReady is still closed and the "All archives created successfully" message is emitted. This can mask failures during incident investigation.
Consider tracking failure state and adjusting the final log accordingly.
🛠️ Proposed fix
func (c *DownloadsServerConfig) CreateArchivesInBackground() {
c.archivesReady = make(chan struct{})
var wg sync.WaitGroup
+ var errCount int32
+ var errMu sync.Mutex
for _, spec := range c.Spec {
basename := filepath.Base(spec.Path)
artifactPath := filepath.Join(c.TempDir, spec.Arch, spec.OperatingSystem, basename)
wg.Add(2)
go func(p string) {
defer wg.Done()
if err := createArchive(p, ".tar"); err != nil {
klog.Errorf("Failed to create tar archive for %s: %v", p, err)
+ errMu.Lock()
+ errCount++
+ errMu.Unlock()
}
}(artifactPath)
go func(p string) {
defer wg.Done()
if err := createArchive(p, ".zip"); err != nil {
klog.Errorf("Failed to create zip archive for %s: %v", p, err)
+ errMu.Lock()
+ errCount++
+ errMu.Unlock()
}
}(artifactPath)
}
go func() {
wg.Wait()
close(c.archivesReady)
- klog.Info("All archives created successfully")
+ if errCount > 0 {
+ klog.Warningf("Archive creation completed with %d failures", errCount)
+ } else {
+ klog.Info("All archives created successfully")
+ }
}()
}🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In `@cmd/downloads/config/downloads_config.go` around lines 383 - 387, The final
goroutine currently always logs "All archives created successfully" after
wg.Wait() and closing c.archivesReady; change it to track whether any
createArchive call failed (e.g., set a shared failure flag via an atomic.Bool or
send errors to an errs channel read before logging) and only emit the success
message when no failures were recorded; otherwise log a distinct error/warning
indicating that one or more archive creations failed. Update the goroutine that
calls wg.Wait() and close(c.archivesReady) to inspect that failure indicator (or
aggregated errors) and choose the appropriate log message, referencing
createArchive, c.archivesReady, and the wg.Wait() goroutine.
| FROM quay.io/openshift/origin-cli-artifacts:4.22 AS origincli | ||
|
|
||
| FROM registry.ci.openshift.org/ocp/builder:rhel-9-golang-1.22-openshift-4.18 AS gobuilder | ||
| FROM registry.ci.openshift.org/ocp/builder:rhel-9-golang-1.25-openshift-4.22 AS gobuilder |
There was a problem hiding this comment.
🧩 Analysis chain
🏁 Script executed:
#!/bin/bash
set -euo pipefail
FILE="$(fd '^Dockerfile\.downloads$' | head -n1)"
echo "== FROM lines =="
awk '/^FROM / { print NR ":" $0 }' "$FILE"
echo
echo "== Unpinned FROM lines (missing `@sha256`) =="
awk '/^FROM / && $2 !~ /@sha256:/ { print NR ":" $0 }' "$FILE"
echo
echo "== Mutable latest tags =="
awk '/^FROM / && $2 ~ /:latest($|[[:space:]])/ { print NR ":" $0 }' "$FILE"Repository: openshift/console
Length of output: 639
🏁 Script executed:
#!/bin/bash
# Find all Dockerfiles and check their FROM line patterns
find . -name "Dockerfile*" -type f | head -20Repository: openshift/console
Length of output: 439
🏁 Script executed:
#!/bin/bash
# Check other Dockerfiles for digest pinning patterns
find . -name "Dockerfile*" -type f -exec grep -H "^FROM" {} + | head -30Repository: openshift/console
Length of output: 2300
🏁 Script executed:
#!/bin/bash
# Check console-operator Dockerfiles for digest pinning patterns
find . -name "Dockerfile*" -type f -exec grep -H "^FROM" {} + | head -30Repository: openshift/console-operator
Length of output: 767
🏁 Script executed:
#!/bin/bash
# Check context around the Dockerfile.downloads file to understand the UBI choice
cat -n Dockerfile.downloads | head -25Repository: openshift/console
Length of output: 997
🌐 Web query:
registry.access.redhat.com/ubi9/ubi-minimal latest stable versions tags
💡 Result:
As of May 15, 2026, the latest stable version of the Red Hat Universal Base Image 9 Minimal (ubi9-minimal) is 9.7 [1][2]. The Red Hat Container Registry uses a tagging system that includes both major/minor version tags and specific build-based tags [1]. You can access the image using the following primary tags: - latest: Always points to the most recent stable release of the image [1]. - 9.7: Points to the current stable minor release [1]. - 9.7-: Points to a specific, immutable build of the 9.7 release (e.g., 9.7-1778562320) [1]. Additionally, Red Hat provides corresponding source images for these tags, which can be accessed by appending -source to the tag (e.g., 9.7-source) [1][2]. To view the most up-to-date list of available tags, you can check the Red Hat Ecosystem Catalog [2] or the official Red Hat repository on Docker Hub [1][3]. For programmatic access or to mirror images, it is recommended to use the skopeo tool to list tags directly from the registry [2][4].
Citations:
- 1: https://hub.docker.com/r/redhat/ubi9-minimal/tags
- 2: https://catalog.redhat.com/en/software/containers/ubi9/ubi-minimal/615bd9b4075b022acc111bf5
- 3: https://hub.docker.com/r/redhat/ubi9-minimal
- 4: https://dev.to/lyraalishaikh/stop-pulling-containers-just-to-mirror-them-practical-skopeo-for-safer-image-promotion-1kf3
Replace mutable :latest tag on Line 17 with a stable version tag.
Line 17 uses registry.access.redhat.com/ubi9/ubi-minimal:latest, which is mutable and inconsistent with the versioned approach elsewhere in the Dockerfile. Replace with a stable version tag like 9.7 to ensure reproducible builds and align with the versioned tags used on lines 1 and 3.
Suggested change
-FROM registry.access.redhat.com/ubi9/ubi-minimal:latest
+FROM registry.access.redhat.com/ubi9/ubi-minimal:9.7🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In `@Dockerfile.downloads` around lines 1 - 3, Replace the mutable UBI image tag
used in the Dockerfile by updating the image reference
"registry.access.redhat.com/ubi9/ubi-minimal:latest" to a stable versioned tag
(for example "registry.access.redhat.com/ubi9/ubi-minimal:9.7") so builds are
reproducible and consistent with the other versioned images like
"quay.io/openshift/origin-cli-artifacts:4.22" and
"registry.ci.openshift.org/ocp/builder:rhel-9-golang-1.25-openshift-4.22";
locate the line containing the
"registry.access.redhat.com/ubi9/ubi-minimal:latest" image and replace ":latest"
with the chosen stable version.
|
/retest |
|
@jhadvig: all tests passed! Full PR test history. Your PR dashboard. DetailsInstructions for interacting with me using PR comments are available here. If you have questions or suggestions related to my behavior, please file an issue against the kubernetes-sigs/prow repository. I understand the commands that are listed here. |
Analysis / Root cause:
The
Dockerfile.downloadsstill references OCP 4.18 base images, preventing the console-downloads image from building against the current 4.22 release in CI. Additionally, the downloads server does not serve theRHEL 8 and RHEL 9 specific
ocbinaries that were recently added to the cli-artifacts image (console-operator#1102, OCPBUGS-57468).This is a follow-up to CONSOLE-3340 to wire the console-downloads image into CI so it is built and promoted to the release payload.
Solution description:
Dockerfile.downloads— Updated all threeFROMdirectives from 4.18 to 4.22:quay.io/openshift/origin-cli-artifacts:4.22registry.ci.openshift.org/ocp/builder:rhel-9-golang-1.25-openshift-4.22registry.ci.openshift.org/ocp/4.22:base-rhel9defaultArtifactsConfig.yaml— Added 8 new entries foroc.rhel8andoc.rhel9binaries across all Linux architectures (amd64, arm64, ppc64le, s390x), matching the paths served by the console-operator.downloads_config.go— Added adisplayName()helper that derives a human-readable label from the binary basename (e.g.oc.rhel8→"amd64 linux - RHEL 8"), so the HTML index page distinguishesRHEL-specific variants from the generic binary.
downloads_config_test.go— Added unit tests fordisplayNameandconfigureArchivePathcovering generic, RHEL 8, RHEL 9, and.exeinputs.Screenshots / screen recording:
Test setup:
No special setup required. The downloads server can be tested locally:
go build ./cmd/downloads/...
go test ./cmd/downloads/config/...
Test cases:
go test ./cmd/downloads/config/...go build ./cmd/downloads/...Dockerfile.downloadsbuilds successfully locallyoc.rhel8.tar,oc.rhel8.zip,oc.rhel9.tar,oc.rhel9.zipAdditional info:
Summary by CodeRabbit
New Features
Chores