Skip to content

feat: have CVO inject the centralized TLS configuration into the operator's config#1167

Open
ingvagabund wants to merge 1 commit into
openshift:mainfrom
ingvagabund:cvo-injected-tls-configuration
Open

feat: have CVO inject the centralized TLS configuration into the operator's config#1167
ingvagabund wants to merge 1 commit into
openshift:mainfrom
ingvagabund:cvo-injected-tls-configuration

Conversation

@ingvagabund
Copy link
Copy Markdown
Member

@ingvagabund ingvagabund commented May 28, 2026

Also, have the operator restart whenever the config changes.

wip-docs: openshift/enhancements#2020

Analysis / Root cause:

Solution description:

Test setup:

Test cases:

Browser conformance:

  • Chrome
  • Firefox
  • Safari (or Epiphany on Linux)

Additional info:

Reviewers and assignees:

Summary by CodeRabbit

  • Chores
    • Improved TLS certificate management and operator resilience through automatic configuration reload.

…ator's config

Also, have the operator restart whenever the config changes.
@coderabbitai
Copy link
Copy Markdown

coderabbitai Bot commented May 28, 2026

Walkthrough

This PR configures TLS injection and file monitoring for the console-operator. The ConfigMap annotation enables TLS secret injection, while both Deployment manifests are updated with file-watching arguments to gracefully restart the operator when controller config or TLS certificate files change.

Changes

TLS Injection and File Watching Configuration

Layer / File(s) Summary
ConfigMap TLS injection annotation
manifests/05-config.yaml
ConfigMap metadata gains the config.openshift.io/inject-tls: "true" annotation to enable TLS secret injection.
Operator file watching configuration
manifests/07-operator.yaml, manifests/07-operator-ibm-cloud-managed.yaml
Both console-operator Deployment manifests add --terminate-on-files arguments to watch controller config and TLS certificate/key file paths, enabling graceful restart on file changes.

Estimated code review effort

🎯 1 (Trivial) | ⏱️ ~3 minutes

🚥 Pre-merge checks | ✅ 14 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Description check ⚠️ Warning The PR description is largely incomplete. While it mentions the main objective, most required template sections are empty or unfilled. Fill in all required sections: Analysis/Root cause, Solution description, Test setup, Test cases, Browser conformance, and Reviewers/assignees. Ensure the PR title includes a Jira issue prefix.
✅ Passed checks (14 passed)
Check name Status Explanation
Title check ✅ Passed The title accurately describes the main change: enabling CVO to inject centralized TLS configuration into the operator's config, which aligns with all three manifest changes.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
Stable And Deterministic Test Names ✅ Passed PR only modifies YAML manifest files (05-config.yaml, 07-operator*.yaml). No test files are modified; this custom check for Ginkgo test name stability is not applicable.
Test Structure And Quality ✅ Passed PR contains only YAML manifest changes (TLS configuration injection); no Ginkgo test code was added or modified, so the test quality check is not applicable.
Microshift Test Compatibility ✅ Passed The PR contains only YAML manifest changes. No new Ginkgo e2e tests are added in this pull request.
Single Node Openshift (Sno) Test Compatibility ✅ Passed This PR contains no new Ginkgo e2e tests—only YAML manifest changes for operator configuration. The SNO compatibility check is not applicable.
Topology-Aware Scheduling Compatibility ✅ Passed PR introduces no new scheduling constraints—only adds --terminate-on-files args and ConfigMap annotation. Pre-existing master nodeSelector/tolerations were already present.
Ote Binary Stdout Contract ✅ Passed PR modifies only YAML manifests (3 files). No Go code changes made, so OTE stdout contract cannot be violated.
Ipv6 And Disconnected Network Test Compatibility ✅ Passed PR only modifies YAML manifest files; no new Ginkgo e2e tests are added. Check not applicable.
No-Weak-Crypto ✅ Passed No weak crypto algorithms found; uses secure crypto/rand and crypto/sha256; no custom implementations or unsafe secret comparisons detected.
Container-Privileges ✅ Passed No privileged settings, hostPID/Network/IPC, SYS_ADMIN capabilities, root user, or allowPrivilegeEscalation: true found in modified manifests; containers have restrictive security contexts.
No-Sensitive-Data-In-Logs ✅ Passed PR adds terminate-on-files args that log file paths (/var/run/secrets/serving-cert/tls.*) not sensitive data, per library-go logging code.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Comment @coderabbitai help to get the list of available commands and usage tips.

@openshift-ci openshift-ci Bot requested review from TheRealJon and jhadvig May 28, 2026 22:40
@openshift-ci
Copy link
Copy Markdown
Contributor

openshift-ci Bot commented May 28, 2026

[APPROVALNOTIFIER] This PR is NOT APPROVED

This pull-request has been approved by: ingvagabund
Once this PR has been reviewed and has the lgtm label, please assign therealjon for approval. For more information see the Code Review Process.

The full list of commands accepted by this bot can be found here.

Details Needs approval from an approver in each of these files:

Approvers can indicate their approval by writing /approve in a comment
Approvers can cancel approval by writing /approve cancel in a comment

Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

♻️ Duplicate comments (1)
manifests/07-operator-ibm-cloud-managed.yaml (1)

28-30: ⚠️ Potential issue | 🟠 Major | ⚡ Quick win

Verify operator behavior when watching files in optional secret.

Same concern as in manifests/07-operator.yaml: the serving-cert secret is optional (line 105), but file-watching is configured for TLS files within it. Verify the operator gracefully handles watching non-existent files at startup before CVO injects the TLS secret.

🤖 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 `@manifests/07-operator-ibm-cloud-managed.yaml` around lines 28 - 30, The
operator manifest configures file-watching flags (--terminate-on-files) for TLS
files inside the optional "serving-cert" secret (the paths for tls.crt/tls.key)
which may not exist at startup; update the operator startup logic or container
args so the operator handles missing files gracefully by either removing those
--terminate-on-files entries for the serving-cert files when the secret is
optional or adding a startup check that detects absence of the serving-cert
files and skips/defers termination-watching until the secret is present (ensure
the code or entrypoint that parses the --terminate-on-files flags tolerates
non-existent paths and does not exit on startup).
🧹 Nitpick comments (2)
manifests/07-operator.yaml (1)

85-88: ⚡ Quick win

Consider adding resource limits alongside requests.

The container specifies resource requests but no limits. While requests are sufficient for scheduling, adding limits helps prevent resource exhaustion and improves cluster stability. As per coding guidelines, resource limits (cpu, memory) should be present on every container.

📊 Suggested resource limits
         resources:
           requests:
             memory: "100Mi"
             cpu: "10m"
+          limits:
+            memory: "200Mi"
+            cpu: "100m"
🤖 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 `@manifests/07-operator.yaml` around lines 85 - 88, The manifest defines
resource requests under resources.requests (memory: "100Mi", cpu: "10m") but no
resource limits; add a resources.limits block next to requests and set
appropriate cpu and memory caps (e.g., cpu: "100m", memory: "200Mi") to prevent
resource exhaustion and comply with the guideline—update the container spec that
contains the resources key to include limits for both cpu and memory.
manifests/07-operator-ibm-cloud-managed.yaml (1)

63-66: ⚡ Quick win

Consider adding resource limits alongside requests.

The container specifies resource requests but no limits. Adding limits helps prevent resource exhaustion. As per coding guidelines, resource limits (cpu, memory) should be present on every container.

Note: Since this is an auto-generated file (line 1), the change should likely be made in the source template or generator that produces this manifest.

📊 Suggested resource limits
         resources:
           requests:
             cpu: 10m
             memory: 100Mi
+          limits:
+            cpu: 100m
+            memory: 200Mi
🤖 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 `@manifests/07-operator-ibm-cloud-managed.yaml` around lines 63 - 66, The
manifest defines resources.requests (cpu: 10m, memory: 100Mi) but no
resources.limits; update the source Helm/template/generator that produces this
manifest to add resources.limits with appropriate cpu and memory values (e.g.,
limits slightly above requests) so every container has both requests and limits;
modify the template field under resources to include limits (cpu and memory)
alongside the existing requests to ensure the generated manifests include limits
going forward.
🤖 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 `@manifests/07-operator.yaml`:
- Around line 61-63: The args
"--terminate-on-files=/var/run/secrets/serving-cert/tls.crt" and
"--terminate-on-files=/var/run/secrets/serving-cert/tls.key" in the operator
container args cause a terminate() on the first appearance event (e.g. when an
optional serving-cert secret is later created), so either remove these two
"--terminate-on-files=..." entries from the args list in 07-operator.yaml or
make the serving-cert secret mount non-optional (ensure the files exist at
startup); choose the approach you want and update the container args (or the
secret/mount) accordingly to prevent an unintended pod restart when
tls.crt/tls.key appear.

---

Duplicate comments:
In `@manifests/07-operator-ibm-cloud-managed.yaml`:
- Around line 28-30: The operator manifest configures file-watching flags
(--terminate-on-files) for TLS files inside the optional "serving-cert" secret
(the paths for tls.crt/tls.key) which may not exist at startup; update the
operator startup logic or container args so the operator handles missing files
gracefully by either removing those --terminate-on-files entries for the
serving-cert files when the secret is optional or adding a startup check that
detects absence of the serving-cert files and skips/defers termination-watching
until the secret is present (ensure the code or entrypoint that parses the
--terminate-on-files flags tolerates non-existent paths and does not exit on
startup).

---

Nitpick comments:
In `@manifests/07-operator-ibm-cloud-managed.yaml`:
- Around line 63-66: The manifest defines resources.requests (cpu: 10m, memory:
100Mi) but no resources.limits; update the source Helm/template/generator that
produces this manifest to add resources.limits with appropriate cpu and memory
values (e.g., limits slightly above requests) so every container has both
requests and limits; modify the template field under resources to include limits
(cpu and memory) alongside the existing requests to ensure the generated
manifests include limits going forward.

In `@manifests/07-operator.yaml`:
- Around line 85-88: The manifest defines resource requests under
resources.requests (memory: "100Mi", cpu: "10m") but no resource limits; add a
resources.limits block next to requests and set appropriate cpu and memory caps
(e.g., cpu: "100m", memory: "200Mi") to prevent resource exhaustion and comply
with the guideline—update the container spec that contains the resources key to
include limits for both cpu and memory.
🪄 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: 28c384d0-ae3d-4587-b0f8-a33acfbf3871

📥 Commits

Reviewing files that changed from the base of the PR and between cba2bb3 and 1b09be0.

📒 Files selected for processing (3)
  • manifests/05-config.yaml
  • manifests/07-operator-ibm-cloud-managed.yaml
  • manifests/07-operator.yaml
📜 Review details
🧰 Additional context used
📓 Path-based instructions (2)
**/*.yaml

⚙️ CodeRabbit configuration file

**/*.yaml: Review YAML manifests based on content and kind.

Refer to /manifest-review when YAML contains:

  • kind: Role or kind: ClusterRole (RBAC review)
  • kind: RoleBinding or kind: ClusterRoleBinding
  • annotations: section (check for cluster profiles)
  • verbs: ["*"] or wildcard permissions
  • apiGroups: ["*"] or overly broad permissions
  • ServiceAccount references in subjects

Check for required annotations in manifests/:

  • include.release.openshift.io/hypershift
  • include.release.openshift.io/ibm-cloud-managed
  • include.release.openshift.io/self-managed-high-availability
  • include.release.openshift.io/single-node-developer
  • capability.openshift.io/name: Console

For quickstarts/, additionally check:

  • QuickStart spec structure
  • Task descriptions and prerequisites
  • See quickstarts/README.md for guidelines

Files:

  • manifests/07-operator.yaml
  • manifests/05-config.yaml
  • manifests/07-operator-ibm-cloud-managed.yaml
**/*.{yaml,yml}

⚙️ CodeRabbit configuration file

**/*.{yaml,yml}: If this is a Kubernetes/OpenShift manifest or Helm template:

  • securityContext: runAsNonRoot, readOnlyRootFilesystem,
    allowPrivilegeEscalation: false
  • Drop ALL capabilities, add only what is required
  • Resource limits (cpu, memory) on every container
  • No hostPID, hostNetwork, hostIPC, privileged: true
  • NetworkPolicy defined for the namespace
  • OpenShift: SCC must be restricted or custom-scoped
  • Liveness + readiness probes defined
  • automountServiceAccountToken: false unless needed
  • RBAC: least privilege; no cluster-admin for workloads
  • Helm: no .Values interpolation in shell commands

Files:

  • manifests/07-operator.yaml
  • manifests/05-config.yaml
  • manifests/07-operator-ibm-cloud-managed.yaml
🔇 Additional comments (1)
manifests/05-config.yaml (1)

12-12: LGTM!

Comment on lines +61 to +63
- "--terminate-on-files=/var/run/configmaps/config/controller-config.yaml"
- "--terminate-on-files=/var/run/secrets/serving-cert/tls.crt"
- "--terminate-on-files=/var/run/secrets/serving-cert/tls.key"
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor | ⚡ Quick win

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
# Description: Search for file-watching implementation and error handling in the operator codebase

# Check for terminate-on-files flag implementation and how it handles missing files
rg -nP --type=go -C5 'terminate-on-files|TerminateOnFiles' 

# Look for file watching logic and error handling
rg -nP --type=go -C3 'fsnotify|file.*watch|inotify' 

# Check if there's logic to handle optional files or graceful degradation
rg -nP --type=go -C3 'optional.*file|file.*optional|skip.*missing'

Repository: openshift/console-operator

Length of output: 50383


🏁 Script executed:

#!/bin/bash
set -euo pipefail

echo "== Find fileobserver implementation =="
rg -n "package fileobserver" -S vendor openshift || true
rg -n "fileobserver\.NewObserver|NewObserver\(" -S vendor | head -n 50 || true
rg -n "AddReactor\(" -S vendor | head -n 50 || true
rg -n "TerminateOnFiles" -S . | head -n 50 || true

echo
echo "== Show relevant manifest sections =="
# Print a manageable chunk around the mentioned lines
sed -n '40,140p' manifests/07-operator.yaml | cat -n

Repository: openshift/console-operator

Length of output: 6690


🏁 Script executed:

#!/bin/bash
set -euo pipefail

echo "== observer.go (fileobserver) =="
nl -ba vendor/github.com/openshift/library-go/pkg/controller/fileobserver/observer.go | sed -n '1,220p'

echo
echo "== observer_polling.go (fileobserver) =="
nl -ba vendor/github.com/openshift/library-go/pkg/controller/fileobserver/observer_polling.go | sed -n '1,240p'

echo
echo "== Any helper types in observer.go beyond 220 (if small) =="
nl -ba vendor/github.com/openshift/library-go/pkg/controller/fileobserver/observer.go | sed -n '220,420p'

Repository: openshift/console-operator

Length of output: 164


🏁 Script executed:

#!/bin/bash
set -euo pipefail

echo "== observer.go (fileobserver) =="
sed -n '1,260p' vendor/github.com/openshift/library-go/pkg/controller/fileobserver/observer.go | cat -n

echo
echo "== observer_polling.go (fileobserver) =="
sed -n '1,320p' vendor/github.com/openshift/library-go/pkg/controller/fileobserver/observer_polling.go | cat -n

echo
echo "== observer.go tail (if larger) =="
sed -n '260,520p' vendor/github.com/openshift/library-go/pkg/controller/fileobserver/observer.go | cat -n

Repository: openshift/console-operator

Length of output: 10870


🏁 Script executed:

sed -n '130,210p' vendor/github.com/openshift/library-go/pkg/controller/controllercmd/cmd.go | cat -n

Repository: openshift/console-operator

Length of output: 3301


Clarify --terminate-on-files behavior with optional serving-cert

The below args still terminate the operator when the watched files change:

- "--terminate-on-files=/var/run/secrets/serving-cert/tls.crt"
- "--terminate-on-files=/var/run/secrets/serving-cert/tls.key"
  • The file observer is polling-based and treats missing files as exists=false; it will not crash or exit just because tls.crt/tls.key don’t exist at startup.
  • However, the terminate reactor calls terminate() on the first observed file event, so when the optional serving-cert secret is later created and the tls.* files appear, the operator will terminate (causing a pod restart).
  • If a restart on secret injection/creation is not intended, adjust terminate-on-files for these optional TLS paths (or make the secret non-optional).
🤖 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 `@manifests/07-operator.yaml` around lines 61 - 63, The args
"--terminate-on-files=/var/run/secrets/serving-cert/tls.crt" and
"--terminate-on-files=/var/run/secrets/serving-cert/tls.key" in the operator
container args cause a terminate() on the first appearance event (e.g. when an
optional serving-cert secret is later created), so either remove these two
"--terminate-on-files=..." entries from the args list in 07-operator.yaml or
make the serving-cert secret mount non-optional (ensure the files exist at
startup); choose the approach you want and update the container args (or the
secret/mount) accordingly to prevent an unintended pod restart when
tls.crt/tls.key appear.

@ingvagabund
Copy link
Copy Markdown
Member Author

/retest-required

@openshift-ci
Copy link
Copy Markdown
Contributor

openshift-ci Bot commented May 29, 2026

@ingvagabund: The following test failed, say /retest to rerun all failed tests or /retest-required to rerun all mandatory failed tests:

Test name Commit Details Required Rerun command
ci/prow/e2e-aws-console 1b09be0 link true /test e2e-aws-console

Full PR test history. Your PR dashboard.

Details

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 kubernetes-sigs/prow repository. I understand the commands that are listed here.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant