diff --git a/resource_customizations/operators.coreos.com/Subscription/health.lua b/resource_customizations/operators.coreos.com/Subscription/health.lua index 95cbedd3783c4..76c10b4ecd784 100644 --- a/resource_customizations/operators.coreos.com/Subscription/health.lua +++ b/resource_customizations/operators.coreos.com/Subscription/health.lua @@ -4,14 +4,36 @@ if obj.status ~= nil then local numDegraded = 0 local numPending = 0 local msg = "" + + -- Check if this is a manual approval scenario where InstallPlanPending is expected + -- and the operator is already installed (upgrade pending, not initial install) + local isManualApprovalPending = false + if obj.spec ~= nil and obj.spec.installPlanApproval == "Manual" then + for _, condition in pairs(obj.status.conditions) do + if condition.type == "InstallPlanPending" and condition.status == "True" and condition.reason == "RequiresApproval" then + -- Only treat as expected healthy state if the operator is already installed + -- (installedCSV is present), meaning this is an upgrade pending approval + if obj.status.installedCSV ~= nil then + isManualApprovalPending = true + end + break + end + end + end + for i, condition in pairs(obj.status.conditions) do - msg = msg .. i .. ": " .. condition.type .. " | " .. condition.status .. "\n" - if condition.type == "InstallPlanPending" and condition.status == "True" then - numPending = numPending + 1 - elseif (condition.type == "InstallPlanMissing" and condition.reason ~= "ReferencedInstallPlanNotFound") then - numDegraded = numDegraded + 1 - elseif (condition.type == "CatalogSourcesUnhealthy" or condition.type == "InstallPlanFailed" or condition.type == "ResolutionFailed") and condition.status == "True" then - numDegraded = numDegraded + 1 + -- Skip InstallPlanPending condition when manual approval is pending (expected behavior) + if isManualApprovalPending and condition.type == "InstallPlanPending" then + -- Do not include in message or count as pending + else + msg = msg .. i .. ": " .. condition.type .. " | " .. condition.status .. "\n" + if condition.type == "InstallPlanPending" and condition.status == "True" then + numPending = numPending + 1 + elseif (condition.type == "InstallPlanMissing" and condition.reason ~= "ReferencedInstallPlanNotFound") then + numDegraded = numDegraded + 1 + elseif (condition.type == "CatalogSourcesUnhealthy" or condition.type == "InstallPlanFailed" or condition.type == "ResolutionFailed") and condition.status == "True" then + numDegraded = numDegraded + 1 + end end end @@ -20,9 +42,17 @@ if obj.status ~= nil then if obj.status.state == nil then numPending = numPending + 1 msg = msg .. ".status.state not yet known\n" - elseif obj.status.state == "" or obj.status.state == "UpgradeAvailable" or obj.status.state == "UpgradePending" then + elseif obj.status.state == "" or obj.status.state == "UpgradeAvailable" then numPending = numPending + 1 msg = msg .. ".status.state is '" .. obj.status.state .. "'\n" + elseif obj.status.state == "UpgradePending" then + -- UpgradePending with manual approval is expected behavior, treat as healthy + if isManualApprovalPending then + msg = msg .. ".status.state is 'AtLatestKnown'\n" + else + numPending = numPending + 1 + msg = msg .. ".status.state is '" .. obj.status.state .. "'\n" + end elseif obj.status.state == "UpgradeFailed" then numDegraded = numDegraded + 1 msg = msg .. ".status.state is '" .. obj.status.state .. "'\n" diff --git a/resource_customizations/operators.coreos.com/Subscription/health_test.yaml b/resource_customizations/operators.coreos.com/Subscription/health_test.yaml index 2133b032f0cd4..0a523e5503b92 100644 --- a/resource_customizations/operators.coreos.com/Subscription/health_test.yaml +++ b/resource_customizations/operators.coreos.com/Subscription/health_test.yaml @@ -27,3 +27,11 @@ tests: status: Healthy message: "1: CatalogSourcesUnhealthy | False\n.status.state is 'AtLatestKnown'\n" inputPath: testdata/healthy.yaml +- healthStatus: + status: Healthy + message: "1: CatalogSourcesUnhealthy | False\n.status.state is 'AtLatestKnown'\n" + inputPath: testdata/install_plan_manual_upgrade_pending.yaml +- healthStatus: + status: Progressing + message: "1: CatalogSourcesUnhealthy | False\n2: BundleUnpacking | True\n3: InstallPlanPending | True\n.status.state is 'UpgradePending'\n" + inputPath: testdata/install_plan_manual_upgrade_pending_not_installed_yet.yaml diff --git a/resource_customizations/operators.coreos.com/Subscription/testdata/install_plan_manual_upgrade_pending.yaml b/resource_customizations/operators.coreos.com/Subscription/testdata/install_plan_manual_upgrade_pending.yaml new file mode 100644 index 0000000000000..c489bf4b0711b --- /dev/null +++ b/resource_customizations/operators.coreos.com/Subscription/testdata/install_plan_manual_upgrade_pending.yaml @@ -0,0 +1,87 @@ +apiVersion: operators.coreos.com/v1alpha1 +kind: Subscription +metadata: + annotations: + kubectl.kubernetes.io/last-applied-configuration: | + {"apiVersion":"operators.coreos.com/v1alpha1","kind":"Subscription","metadata":{"annotations":{},"labels":{"app.kubernetes.io/instance":"industrial-edge-datacenter"},"name":"camel-k","namespace":"manuela-data-lake"},"spec":{"channel":"stable-v2","installPlanApproval":"Manual","name":"camel-k","source":"community-operators","sourceNamespace":"openshift-marketplace","startingCSV":"camel-k-operator.v2.5.1"}} + creationTimestamp: "2025-03-05T20:13:35Z" + generation: 1 + labels: + app.kubernetes.io/instance: industrial-edge-datacenter + operators.coreos.com/camel-k.manuela-data-lake: "" + name: camel-k + namespace: manuela-data-lake + resourceVersion: "45944" + uid: eeabc8c9-7a10-4f8d-babd-66e755f804ba +spec: + channel: stable-v2 + installPlanApproval: Manual + name: camel-k + source: community-operators + sourceNamespace: openshift-marketplace + startingCSV: camel-k-operator.v2.5.1 +status: + catalogHealth: + - catalogSourceRef: + apiVersion: operators.coreos.com/v1alpha1 + kind: CatalogSource + name: certified-operators + namespace: openshift-marketplace + resourceVersion: "36041" + uid: 4d85c991-bea0-48d9-adc3-26229bfb3747 + healthy: true + lastUpdated: "2025-03-05T20:14:10Z" + - catalogSourceRef: + apiVersion: operators.coreos.com/v1alpha1 + kind: CatalogSource + name: community-operators + namespace: openshift-marketplace + resourceVersion: "36026" + uid: b578a8f6-63ca-44cf-a35e-0d8e065b0ecc + healthy: true + lastUpdated: "2025-03-05T20:14:10Z" + - catalogSourceRef: + apiVersion: operators.coreos.com/v1alpha1 + kind: CatalogSource + name: redhat-marketplace + namespace: openshift-marketplace + resourceVersion: "36006" + uid: 29e7d910-11b3-43a4-98bb-aa3bf1da0464 + healthy: true + lastUpdated: "2025-03-05T20:14:10Z" + - catalogSourceRef: + apiVersion: operators.coreos.com/v1alpha1 + kind: CatalogSource + name: redhat-operators + namespace: openshift-marketplace + resourceVersion: "36216" + uid: c0a8229a-ceef-4dd5-b362-08bfee1fe64c + healthy: true + lastUpdated: "2025-03-05T20:14:10Z" + conditions: + - lastTransitionTime: "2025-03-05T20:14:13Z" + message: all available catalogsources are healthy + reason: AllCatalogSourcesHealthy + status: "False" + type: CatalogSourcesUnhealthy + - lastTransitionTime: "2025-03-05T20:16:14Z" + reason: RequiresApproval + status: "True" + type: InstallPlanPending + currentCSV: camel-k-operator.v2.6.0 + installPlanGeneration: 2 + installPlanRef: + apiVersion: operators.coreos.com/v1alpha1 + kind: InstallPlan + name: install-sm4qt + namespace: manuela-data-lake + resourceVersion: "45604" + uid: 86a26d57-b292-408b-8cc9-b829d5ecdb15 + installedCSV: camel-k-operator.v2.5.1 + installplan: + apiVersion: operators.coreos.com/v1alpha1 + kind: InstallPlan + name: install-sm4qt + uuid: 86a26d57-b292-408b-8cc9-b829d5ecdb15 + lastUpdated: "2025-03-05T20:16:20Z" + state: UpgradePending diff --git a/resource_customizations/operators.coreos.com/Subscription/testdata/install_plan_manual_upgrade_pending_not_installed_yet.yaml b/resource_customizations/operators.coreos.com/Subscription/testdata/install_plan_manual_upgrade_pending_not_installed_yet.yaml new file mode 100644 index 0000000000000..34faeb6c1581e --- /dev/null +++ b/resource_customizations/operators.coreos.com/Subscription/testdata/install_plan_manual_upgrade_pending_not_installed_yet.yaml @@ -0,0 +1,89 @@ +apiVersion: operators.coreos.com/v1alpha1 +kind: Subscription +metadata: + annotations: + kubectl.kubernetes.io/last-applied-configuration: | + {"apiVersion":"operators.coreos.com/v1alpha1","kind":"Subscription","metadata":{"annotations":{},"labels":{"app.kubernetes.io/instance":"multicloud-gitops-hub"},"name":"advanced-cluster-management","namespace":"open-cluster-management"},"spec":{"channel":"release-2.14","installPlanApproval":"Manual","name":"advanced-cluster-management","source":"redhat-operators","sourceNamespace":"openshift-marketplace","startingCSV":"advanced-cluster-management.v2.14.0"}} + creationTimestamp: "2026-01-09T16:25:42Z" + generation: 1 + labels: + app.kubernetes.io/instance: multicloud-gitops-hub + operators.coreos.com/advanced-cluster-management.open-cluster-management: "" + name: advanced-cluster-management + namespace: open-cluster-management + resourceVersion: "78923" + uid: da1f72d9-901e-4d46-a931-d13eda46501a +spec: + channel: release-2.14 + installPlanApproval: Manual + name: advanced-cluster-management + source: redhat-operators + sourceNamespace: openshift-marketplace + startingCSV: advanced-cluster-management.v2.14.0 +status: + catalogHealth: + - catalogSourceRef: + apiVersion: operators.coreos.com/v1alpha1 + kind: CatalogSource + name: certified-operators + namespace: openshift-marketplace + resourceVersion: "74957" + uid: 8adf5a80-b990-4423-ac2a-95969114c306 + healthy: true + lastUpdated: "2026-01-09T16:25:46Z" + - catalogSourceRef: + apiVersion: operators.coreos.com/v1alpha1 + kind: CatalogSource + name: community-operators + namespace: openshift-marketplace + resourceVersion: "75378" + uid: 8407538e-4739-4e1f-9452-7b487a1e0e9d + healthy: true + lastUpdated: "2026-01-09T16:25:46Z" + - catalogSourceRef: + apiVersion: operators.coreos.com/v1alpha1 + kind: CatalogSource + name: redhat-marketplace + namespace: openshift-marketplace + resourceVersion: "75211" + uid: 1e3ef28b-d483-4722-9b0a-116a94a85339 + healthy: true + lastUpdated: "2026-01-09T16:25:46Z" + - catalogSourceRef: + apiVersion: operators.coreos.com/v1alpha1 + kind: CatalogSource + name: redhat-operators + namespace: openshift-marketplace + resourceVersion: "74904" + uid: 12b22855-3197-4188-bc27-d8e709c2b0c9 + healthy: true + lastUpdated: "2026-01-09T16:25:46Z" + conditions: + - lastTransitionTime: "2026-01-09T16:25:50Z" + message: all available catalogsources are healthy + reason: AllCatalogSourcesHealthy + status: "False" + type: CatalogSourcesUnhealthy + - reason: UnpackingInProgress + status: "True" + type: BundleUnpacking + - lastTransitionTime: "2026-01-09T16:25:58Z" + reason: RequiresApproval + status: "True" + type: InstallPlanPending + currentCSV: advanced-cluster-management.v2.14.0 + installPlanGeneration: 1 + installPlanRef: + apiVersion: operators.coreos.com/v1alpha1 + kind: InstallPlan + name: install-2k2t8 + namespace: open-cluster-management + resourceVersion: "78871" + uid: 8b99223f-0f29-4863-89f6-5e19651f9023 + installplan: + apiVersion: operators.coreos.com/v1alpha1 + kind: InstallPlan + name: install-2k2t8 + uuid: 8b99223f-0f29-4863-89f6-5e19651f9023 + lastUpdated: "2026-01-09T16:25:58Z" + state: UpgradePending