Skip to content

[KFLUXINFRA-3003] Replace DR sleep-pipeline with nightly sanity test pipeline#13074

Open
vsokolen-redhat wants to merge 1 commit into
redhat-appstudio:mainfrom
vsokolen-redhat:dr-sanity-pipeline
Open

[KFLUXINFRA-3003] Replace DR sleep-pipeline with nightly sanity test pipeline#13074
vsokolen-redhat wants to merge 1 commit into
redhat-appstudio:mainfrom
vsokolen-redhat:dr-sanity-pipeline

Conversation

@vsokolen-redhat

@vsokolen-redhat vsokolen-redhat commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

Summary

Replaces the placeholder sleep-pipeline in the konflux-disaster-recovery namespace with a real DR sanity test pipeline that runs the proven manual drill against releng-test-product-tenant on a nightly schedule.

Changes

  • pipeline.yaml — 6 new Tekton Tasks + dr-sanity-pipeline implementing: preflight checks → baseline build/integration/release→ Velero backup → disaster simulation (NetworkPolicy + namespace deletion) → restore → post-restore build/integration/release verification → cleanup (openshift-adp), tenant namespace operations, release pipeline polling (rhtap-releng-tenant), and NetworkPolicy management (image-controller)
  • cronjob.yaml — schedule changed from hourly to daily at 02:00 UTC, added activeDeadlineSeconds: 7200 and startingDeadlineSeconds: 300
  • triggertemplate.yaml — references new pipeline, uses dr-sanity-runner SA, 2h timeout
  • triggerbinding.yaml — removed unused duration param

Context

The full-chain DR drill was validated manually on 2026-07-15 (KFLUXINFRA-3914). This PR automates the same procedure. The Go e2e test suite (Meirav/Manish) will complement this from CI when ready ([Option C, confirmed in KFLUXINFRA-3003 comments](https://redhat.atlassian.net/browse/KFLUXINFRA-3003?focusedCommentId=17616945)).

Test plan

  • Kustomize build passes locally (kustomize build components/disaster-recovery/staging/stone-stg-rh01/)
  • ArgoCD syncs successfully after merge
  • First nightly run completes (monitor oc get pipelineruns -n konflux-disaster-recovery)
  • All 5 pipeline tasks pass: preflight, baseline-run, backup, disaster-and-restore, post-restore-verify
  • Cleanup task removes test Backup/Restore/Release CRs

Jira
https://redhat.atlassian.net/browse/KFLUXINFRA-3003

@openshift-ci

openshift-ci Bot commented Jul 16, 2026

Copy link
Copy Markdown

[APPROVALNOTIFIER] This PR is APPROVED

This pull-request has been approved by: vsokolen-redhat

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

The pull request process is described 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

@openshift-ci
openshift-ci Bot requested review from celeztyne and gbenhaim July 16, 2026 13:44
@github-actions

github-actions Bot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

Kustomize Render Diff

Comparing 550fb1211f9102e317

Component Environment Changes
components/disaster-recovery/development development +869 -23
components/disaster-recovery/staging/stone-stage-p01 staging +869 -23
components/disaster-recovery/staging/stone-stg-rh01 staging +869 -23

Total: 3 components, +2607 -69 lines

📋 Full diff available in the workflow summary and as a downloadable artifact.

@qodo-for-redhat-appstudio

Copy link
Copy Markdown

PR Summary by Qodo

Replace DR sleep pipeline with nightly DR sanity test Tekton pipeline

✨ Enhancement ⚙️ Configuration changes 🕐 40+ Minutes

Grey Divider

AI Description

• Replace placeholder DR sleep pipeline with an end-to-end nightly DR sanity drill.
• Automate Velero backup, disaster simulation, restore, and post-restore build/release verification.
• Update scheduling, triggers, and RBAC to run safely with a dedicated service account.
Diagram

graph TD
  CJ(["CronJob: nightly trigger"]) --> TT(["Tekton Triggers"]) --> PR(["PipelineRun"]) --> PL(["Pipeline: dr-sanity-pipeline"]) 
  PL --> API{{"OpenShift API (oc)"}}
  PL --> VEL[("Velero (openshift-adp)")]
  PL --> TNS(["Tenant ns: releng-test-product-tenant"]) 
  PL --> MNS(["Managed ns: rhtap-releng-tenant"]) 

  subgraph Legend
    direction LR
    _k8s(["K8s object"]) ~~~ _ext{{"External/system API"}} ~~~ _db[("Backup/restore system")]
  end
Loading
High-Level Assessment

The following are alternative approaches to this PR:

1. Use existing ClusterTasks / shared scripts instead of inline bash
  • ➕ Reduces YAML size and duplication (poll loops, release creation, velero waits).
  • ➕ Centralizes retry/timeouts and error handling.
  • ➕ Easier to unit-test logic outside Tekton YAML.
  • ➖ Requires additional packaging/distribution process for shared tasks/scripts.
  • ➖ May slow down delivery if those shared components don't exist yet.
2. Implement DR drill as a Go e2e test suite (CI-driven) and keep Tekton minimal
  • ➕ Better structure, richer assertions, and easier maintenance than shell.
  • ➕ Can run in CI with consistent reporting and flake management.
  • ➕ Encapsulates cluster interactions behind typed clients.
  • ➖ Longer lead time; requires test harness, creds, and execution environment readiness.
  • ➖ Still needs an operational scheduler for nightly runs (Tekton/CronJob or CI scheduler).

Recommendation: The PR’s approach is appropriate for quickly operationalizing a proven manual DR drill as a nightly cluster-side check. Given the amount of imperative logic, consider a follow-up to extract the repeated polling/CR-creation routines into reusable tasks or scripts, and progressively migrate the workflow to the planned Go e2e suite when it is ready.

Files changed (5) +776 / -27

Enhancement (1) +683 / -6
pipeline.yamlReplace sleep-pipeline with full DR sanity Tekton pipeline and tasks +683/-6

Replace sleep-pipeline with full DR sanity Tekton pipeline and tasks

• Replaces the placeholder Task/Pipeline with a multi-step DR sanity workflow: preflight checks, baseline build/integration/release, Velero backup, disaster simulation (network policy + namespace deletion) and restore, and post-restore build/integration/release verification, plus final cleanup. Introduces pipeline parameters (tenant/app/component/release plan/managed namespace) and wires task outputs (backup name) into downstream steps.

components/disaster-recovery/development/pipeline.yaml

Other (4) +93 / -21
cronjob.yamlRun DR trigger nightly with execution deadlines +3/-3

Run DR trigger nightly with execution deadlines

• Updates the CronJob schedule from hourly to daily at 02:00 UTC. Adds starting and active deadlines to prevent missed/overlapping or runaway executions while keeping concurrency forbidden.

components/disaster-recovery/development/cronjob.yaml

rbac.yamlAdd runner service account and cluster-scoped permissions for DR drill +82/-2

Add runner service account and cluster-scoped permissions for DR drill

• Fixes the TriggerBinding subject namespace to 'konflux-disaster-recovery'. Adds a dedicated 'dr-sanity-runner' ServiceAccount with a ClusterRole/Binding covering Velero backup/restore, Tekton polling/patching, namespace deletion, network policy manipulation, and Konflux resource reads/patches needed for the drill and cleanup.

components/disaster-recovery/development/rbac.yaml

triggerbinding.yamlRemove unused trigger parameters +1/-5

Remove unused trigger parameters

• Drops the previous 'duration' parameter and replaces the TriggerBinding spec with an empty object, since the pipeline no longer sleeps and no binding params are required.

components/disaster-recovery/development/triggerbinding.yaml

triggertemplate.yamlTrigger the new dr-sanity pipeline with runner SA and 2h timeout +7/-11

Trigger the new dr-sanity pipeline with runner SA and 2h timeout

• Switches the TriggerTemplate to create a v1 PipelineRun for 'dr-sanity-pipeline' with a 'dr-sanity-pipeline-run-' generateName. Configures PipelineRun execution to use the 'dr-sanity-runner' service account and enforces a 2-hour pipeline timeout.

components/disaster-recovery/development/triggertemplate.yaml

@qodo-for-redhat-appstudio

Copy link
Copy Markdown

Code Review by Qodo

🐞 Bugs (4) 📘 Rule violations (0) 📜 Skill insights (0)

Context used
⚠️ Tickets: not configured — ticket URL found in PR but could not be fetched — check ticket provider credentials

Grey Divider


Action required

1. 2h deadline too short 🐞 Bug ☼ Reliability
Description
The CronJob activeDeadlineSeconds: 7200 and PipelineRun timeouts.pipeline: 2h are shorter than
the pipeline’s own worst-case sequential polling loops, so runs can be terminated mid-drill and may
not reach cleanup. This can cause frequent false failures and leave disruptive resources behind
(e.g., the image-controller NetworkPolicy).
Code

components/disaster-recovery/development/triggertemplate.yaml[R15-18]

+      taskRunTemplate:
+        serviceAccountName: dr-sanity-runner
+      timeouts:
+        pipeline: 2h
Relevance

⭐⭐ Medium

Team accepted adding Job deadlines/timeouts elsewhere (PR #12769), but no precedent about increasing
2h Tekton pipeline timeout.

PR-#12769

ⓘ Recommendations generated based on similar findings in past PRs

Evidence
The Job and PipelineRun are both capped at 2h, but the pipeline contains multiple sequential polling
loops (build appearance + completion + integration + release; backup completion; restore completion;
post-restore repeat) whose allowed durations sum to well over 2h, so the run can be killed before
completing and before cleanup executes.

components/disaster-recovery/development/cronjob.yaml[8-15]
components/disaster-recovery/development/triggertemplate.yaml[12-18]
components/disaster-recovery/development/pipeline.yaml[97-200]
components/disaster-recovery/development/pipeline.yaml[258-401]
components/disaster-recovery/development/pipeline.yaml[466-552]
components/disaster-recovery/development/pipeline.yaml[630-701]

Agent prompt
The issue below was found during a code review. Follow the provided context and guidance below and implement a solution

### Issue description
CronJob and PipelineRun timeouts are set to 2 hours, but the pipeline tasks contain polling loops and run sequentially with a worst-case duration significantly greater than 2 hours. This can terminate the run before completion and skip/interrupt cleanup.

### Issue Context
- CronJob caps the Job runtime to 7200s.
- TriggerTemplate caps the PipelineRun pipeline timeout to 2h.
- Baseline + backup + restore + post-restore verification loops can exceed 2h in aggregate.

### Fix Focus Areas
- components/disaster-recovery/development/cronjob.yaml[8-15]
- components/disaster-recovery/development/triggertemplate.yaml[12-18]
- components/disaster-recovery/development/pipeline.yaml[97-200]
- components/disaster-recovery/development/pipeline.yaml[258-401]
- components/disaster-recovery/development/pipeline.yaml[466-552]

### What to change
- Either (A) increase `spec.jobTemplate.spec.activeDeadlineSeconds` and `PipelineRun.spec.timeouts.pipeline` to cover the worst-case sequential duration with headroom (e.g., 5–6h), or (B) reduce the polling limits so the total worst-case fits within 2h.
- If keeping a strict overall cap, ensure cleanup is handled out-of-band (or guaranteed to run before termination) so the NetworkPolicy and Velero objects aren’t left behind.

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools



Remediation recommended

2. NetworkPolicy RBAC too narrow 🐞 Bug ≡ Correctness
Description
The pipeline uses oc apply on a fixed NetworkPolicy name in the image-controller namespace, but
the dr-sanity-runner ClusterRole does not grant patch/update on networkpolicies. If the policy
already exists (e.g., leftover from a prior interrupted run), oc apply will fail and abort the
drill.
Code

components/disaster-recovery/development/rbac.yaml[R91-94]

+# NetworkPolicies — create/delete in image-controller namespace
+- apiGroups: ["networking.k8s.io"]
+  resources: ["networkpolicies"]
+  verbs: ["create", "delete", "get"]
Relevance

⭐⭐ Medium

No direct historical RBAC-for-oc-apply precedent found in DR; RBAC issues sometimes addressed, but
evidence is sparse.

PR-#10686

ⓘ Recommendations generated based on similar findings in past PRs

Evidence
The task applies a NetworkPolicy via oc apply, while RBAC grants only create/delete/get for
NetworkPolicies, which is insufficient when the object already exists and needs to be updated.

components/disaster-recovery/development/pipeline.yaml[301-316]
components/disaster-recovery/development/rbac.yaml[91-95]

Agent prompt
The issue below was found during a code review. Follow the provided context and guidance below and implement a solution

### Issue description
`dr-disaster-and-restore` creates the `dr-block-image-controller` NetworkPolicy using `oc apply`, which requires update-style permissions when the object already exists. The ClusterRole currently grants only create/delete/get for NetworkPolicies.

### Issue Context
A previous run may leave the NetworkPolicy behind (especially under timeout/deadline termination), making reruns hit the existing-object path.

### Fix Focus Areas
- components/disaster-recovery/development/pipeline.yaml[301-316]
- components/disaster-recovery/development/rbac.yaml[91-95]

### What to change
- Add `patch` (and/or `update`) to the `networkpolicies` rule for the `dr-sanity-runner` ClusterRole.
- Alternatively, change the script to handle existing policies explicitly (e.g., `oc delete ... --ignore-not-found` then `oc create -f -`) if you want to avoid patch/update permissions.

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools


3. Backup cleanup can be skipped 🐞 Bug ☼ Reliability
Description
Cleanup only deletes the Velero Backup when BACKUP_NAME is non-empty, but BACKUP_NAME is sourced
from tasks.backup.results.backup-name, which won’t be available if the run fails before the result
is written or if backup never ran. This can leak Backup CRs and their stored backups over time.
Code

components/disaster-recovery/development/pipeline.yaml[R692-701]

+  finally:
+  - name: cleanup
    taskRef:
      kind: Task
-      name: sleep
+      name: dr-cleanup
+    params:
+    - name: TENANT_NAMESPACE
+      value: $(params.TENANT_NAMESPACE)
+    - name: BACKUP_NAME
+      value: $(tasks.backup.results.backup-name)
Relevance

⭐⭐ Medium

No close historical precedent; team cares about cleanup reliability but no evidence on finally-task
result availability.

PR-#12880

ⓘ Recommendations generated based on similar findings in past PRs

Evidence
The pipeline passes BACKUP_NAME to the finally task from the backup task’s result, while the cleanup
script only deletes the backup when BACKUP_NAME is non-empty, so missing/unavailable results lead to
skipped backup deletion.

components/disaster-recovery/development/pipeline.yaml[558-595]
components/disaster-recovery/development/pipeline.yaml[658-701]

Agent prompt
The issue below was found during a code review. Follow the provided context and guidance below and implement a solution

### Issue description
The finally cleanup deletes the Backup only if it receives `BACKUP_NAME`, but the pipeline passes this from a task result. If the result isn’t available (task not executed, or failed before writing results), cleanup won’t delete the Backup.

### Issue Context
Cleanup script explicitly skips backup deletion on empty BACKUP_NAME.

### Fix Focus Areas
- components/disaster-recovery/development/pipeline.yaml[558-595]
- components/disaster-recovery/development/pipeline.yaml[658-701]

### What to change
- Remove the dependency on a task result for identifying the Backup.
- Option A (recommended): define a deterministic backup name in the Pipeline (e.g., `dr-sanity-backup-$(context.pipelineRun.uid)`), pass it as a param to both the `backup` and `disaster-and-restore` tasks, and pass the same value to `cleanup`.
- Option B: have cleanup discover and delete backups/restores created by this run via labels/annotations (add labels when creating Backup/Restore), instead of relying on a result.

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools



Informational

4. Wrong PipelineRun selected 🐞 Bug ≡ Correctness
Description
dr-baseline-run and dr-post-restore-verify select the newest PipelineRun in a namespace (and in
the managed namespace for release) without filtering to the build/release they triggered, so they
can wait on and report the status of unrelated PipelineRuns. This can create false
positives/negatives for the DR drill in shared namespaces.
Code

components/disaster-recovery/development/pipeline.yaml[R97-112]

+      # Record PipelineRun count before triggering
+      BEFORE_COUNT=$(oc get pipelineruns -n "$NS" --no-headers 2>/dev/null | wc -l)
+
+      echo "Triggering build on $COMP..."
+      oc annotate component/"$COMP" -n "$NS" \
+        build.appstudio.openshift.io/request=trigger-pac-build --overwrite
+
+      echo "Waiting for new build PipelineRun..."
+      for i in $(seq 1 120); do
+        CURRENT_COUNT=$(oc get pipelineruns -n "$NS" --no-headers 2>/dev/null | wc -l)
+        if [ "$CURRENT_COUNT" -gt "$BEFORE_COUNT" ]; then
+          BUILD_PR=$(oc get pipelineruns -n "$NS" \
+            --sort-by=.metadata.creationTimestamp -o jsonpath='{.items[-1].metadata.name}')
+          echo "Found build PipelineRun: $BUILD_PR"
+          break
+        fi
Relevance

⭐ Low

Similar PipelineRun-selection robustness suggestion was rejected in PR #10815; no contrary accepted
precedent found.

PR-#10815

ⓘ Recommendations generated based on similar findings in past PRs

Evidence
The scripts pick BUILD_PR and REL_PR using only namespace-wide counts and
--sort-by=.metadata.creationTimestamp with no label/owner filtering, so the chosen PipelineRun can
be unrelated to the build/release the task initiated.

components/disaster-recovery/development/pipeline.yaml[97-114]
components/disaster-recovery/development/pipeline.yaml[181-200]
components/disaster-recovery/development/pipeline.yaml[458-477]
components/disaster-recovery/development/pipeline.yaml[535-552]

Agent prompt
The issue below was found during a code review. Follow the provided context and guidance below and implement a solution

### Issue description
The pipeline determines which build/release PipelineRun to watch by counting all PipelineRuns and then reading the most recently created PipelineRun. In shared namespaces, unrelated PipelineRuns can be created concurrently (or already be the newest), causing the DR pipeline to validate the wrong run.

### Issue Context
This affects:
- Build PipelineRun selection after triggering a component build.
- Release PipelineRun selection in the managed namespace after creating a Release CR.

### Fix Focus Areas
- components/disaster-recovery/development/pipeline.yaml[97-114]
- components/disaster-recovery/development/pipeline.yaml[181-200]
- components/disaster-recovery/development/pipeline.yaml[458-477]
- components/disaster-recovery/development/pipeline.yaml[535-552]

### What to change
- When triggering the build, poll only PipelineRuns associated with the specific component/app (use stable labels used by your build pipelines), and also restrict to PipelineRuns created after a recorded start timestamp.
- After creating the Release CR, find the PipelineRun owned by that Release (e.g., query PipelineRuns and match `.metadata.ownerReferences[].name == $RELEASE_NAME`) or filter by release-specific labels/annotations, rather than taking the newest PipelineRun in the managed namespace.
- Avoid using namespace-wide counts as the identity mechanism; use labels/ownerRefs/UIDs.

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools


Grey Divider

Qodo Logo

Comment on lines +15 to +18
taskRunTemplate:
serviceAccountName: dr-sanity-runner
timeouts:
pipeline: 2h

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Action required

1. 2h deadline too short 🐞 Bug ☼ Reliability

The CronJob activeDeadlineSeconds: 7200 and PipelineRun timeouts.pipeline: 2h are shorter than
the pipeline’s own worst-case sequential polling loops, so runs can be terminated mid-drill and may
not reach cleanup. This can cause frequent false failures and leave disruptive resources behind
(e.g., the image-controller NetworkPolicy).
Agent Prompt
### Issue description
CronJob and PipelineRun timeouts are set to 2 hours, but the pipeline tasks contain polling loops and run sequentially with a worst-case duration significantly greater than 2 hours. This can terminate the run before completion and skip/interrupt cleanup.

### Issue Context
- CronJob caps the Job runtime to 7200s.
- TriggerTemplate caps the PipelineRun pipeline timeout to 2h.
- Baseline + backup + restore + post-restore verification loops can exceed 2h in aggregate.

### Fix Focus Areas
- components/disaster-recovery/development/cronjob.yaml[8-15]
- components/disaster-recovery/development/triggertemplate.yaml[12-18]
- components/disaster-recovery/development/pipeline.yaml[97-200]
- components/disaster-recovery/development/pipeline.yaml[258-401]
- components/disaster-recovery/development/pipeline.yaml[466-552]

### What to change
- Either (A) increase `spec.jobTemplate.spec.activeDeadlineSeconds` and `PipelineRun.spec.timeouts.pipeline` to cover the worst-case sequential duration with headroom (e.g., 5–6h), or (B) reduce the polling limits so the total worst-case fits within 2h.
- If keeping a strict overall cap, ensure cleanup is handled out-of-band (or guaranteed to run before termination) so the NetworkPolicy and Velero objects aren’t left behind.

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

The e2e tests also set the timeout at 3h, so this is a valid point

Comment on lines +91 to +94
# NetworkPolicies — create/delete in image-controller namespace
- apiGroups: ["networking.k8s.io"]
resources: ["networkpolicies"]
verbs: ["create", "delete", "get"]

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Remediation recommended

3. Networkpolicy rbac too narrow 🐞 Bug ≡ Correctness

The pipeline uses oc apply on a fixed NetworkPolicy name in the image-controller namespace, but
the dr-sanity-runner ClusterRole does not grant patch/update on networkpolicies. If the policy
already exists (e.g., leftover from a prior interrupted run), oc apply will fail and abort the
drill.
Agent Prompt
### Issue description
`dr-disaster-and-restore` creates the `dr-block-image-controller` NetworkPolicy using `oc apply`, which requires update-style permissions when the object already exists. The ClusterRole currently grants only create/delete/get for NetworkPolicies.

### Issue Context
A previous run may leave the NetworkPolicy behind (especially under timeout/deadline termination), making reruns hit the existing-object path.

### Fix Focus Areas
- components/disaster-recovery/development/pipeline.yaml[301-316]
- components/disaster-recovery/development/rbac.yaml[91-95]

### What to change
- Add `patch` (and/or `update`) to the `networkpolicies` rule for the `dr-sanity-runner` ClusterRole.
- Alternatively, change the script to handle existing policies explicitly (e.g., `oc delete ... --ignore-not-found` then `oc create -f -`) if you want to avoid patch/update permissions.

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools

Comment on lines +692 to +701
finally:
- name: cleanup
taskRef:
kind: Task
name: sleep
name: dr-cleanup
params:
- name: TENANT_NAMESPACE
value: $(params.TENANT_NAMESPACE)
- name: BACKUP_NAME
value: $(tasks.backup.results.backup-name)

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Remediation recommended

4. Backup cleanup can be skipped 🐞 Bug ☼ Reliability

Cleanup only deletes the Velero Backup when BACKUP_NAME is non-empty, but BACKUP_NAME is sourced
from tasks.backup.results.backup-name, which won’t be available if the run fails before the result
is written or if backup never ran. This can leak Backup CRs and their stored backups over time.
Agent Prompt
### Issue description
The finally cleanup deletes the Backup only if it receives `BACKUP_NAME`, but the pipeline passes this from a task result. If the result isn’t available (task not executed, or failed before writing results), cleanup won’t delete the Backup.

### Issue Context
Cleanup script explicitly skips backup deletion on empty BACKUP_NAME.

### Fix Focus Areas
- components/disaster-recovery/development/pipeline.yaml[558-595]
- components/disaster-recovery/development/pipeline.yaml[658-701]

### What to change
- Remove the dependency on a task result for identifying the Backup.
- Option A (recommended): define a deterministic backup name in the Pipeline (e.g., `dr-sanity-backup-$(context.pipelineRun.uid)`), pass it as a param to both the `backup` and `disaster-and-restore` tasks, and pass the same value to `cleanup`.
- Option B: have cleanup discover and delete backups/restores created by this run via labels/annotations (add labels when creating Backup/Restore), instead of relying on a result.

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

A good point

@konflux-ci-qe-bot

konflux-ci-qe-bot commented Jul 16, 2026

Copy link
Copy Markdown

🤖 Pipeline Failure Analysis

Category: Infrastructure

The pipeline failed due to a timeout when deploying Konflux ArgoCD applications, primarily caused by missing Kubernetes resources and a degraded redhat-oadp-operator subscription.

📋 Technical Details

Immediate Cause

Multiple critical Konflux ArgoCD applications (backup-in-cluster-local, kueue-in-cluster-local, policies-in-cluster-local, squid-in-cluster-local) failed to synchronize and achieve a healthy state within 45 minutes, resulting in an ARGOCD_SYNC_TIMEOUT.

Contributing Factors

The widespread failure of these applications to deploy was due to numerous missing Kubernetes resources required for their operation. A key contributing factor was the Subscription/redhat-oadp-operator being in a Degraded state, specifically reporting CatalogSourcesUnhealthy and ResolutionFailed, which likely hindered the deployment of dependent components.

Impact

This failure prevented the successful bootstrapping of the cluster for disaster recovery tests, blocking the pipeline from proceeding and leading to the overall job failure.

🔍 Evidence

appstudio-konflux-disaster-recovery/redhat-appstudio-konflux-disaster-recovery

Category: infrastructure
Root Cause: The root cause is an infrastructure issue where multiple critical Konflux ArgoCD applications failed to deploy or become healthy due to missing and degraded Kubernetes resources, most notably stemming from a degraded redhat-oadp-operator subscription indicating unhealthy catalog sources or resolution failures within the OpenShift cluster's operator management system.

Logs:

artifacts/step-name/build-log.txt
[2026-07-20 13:32:43] [ERROR] TIMEOUT: Applications failed to sync within 45 minutes
artifacts/step-name/build-log.txt
[2026-07-20 13:32:43] [ERROR] Failure Reason: ARGOCD_SYNC_TIMEOUT: 4 apps failed to sync
artifacts/step-name/build-log.txt
[2026-07-20 13:32:43] [ERROR] Failed Applications: backup-in-cluster-local
kueue-in-cluster-local
policies-in-cluster-local
squid-in-cluster-local
artifacts/step-name/build-log.txt
Application: backup-in-cluster-local
-----------------------------------------------------------------------------
  Sync Status: OutOfSync
  Health Status: Degraded
  Unhealthy Resources:
    - ConfigMap/image-repository-resource-modifier-config: Missing - no message
    - Secret/minio-storage-configuration: Missing - no message
    - Job/create-velero-bucket: Missing - no message
    - Tenant/oadp-minio-storage: Missing - no message
    - DataProtectionApplication/velero-aws: Missing - no message
    - Subscription/redhat-oadp-operator: Degraded - 1: CatalogSourcesUnhealthy | False
2: ResolutionFailed | True
    - Schedule/backup-tenants: Missing - no message
  Operation Message: one or more synchronization tasks completed unsuccessfully. Retrying attempt #17 at 1:33PM.
artifacts/step-name/build-log.txt
Application: kueue-in-cluster-local
-----------------------------------------------------------------------------
  Sync Status: OutOfSync
  Health Status: Degraded
  Unhealthy Resources:
    - ConfigMap/tekton-kueue-config: Missing - no message
    - Namespace/tekton-kueue: Missing - no message
    - Secret/metrics-reader: Missing - no message
    - Service/tekton-kueue-controller-manager-metrics-service: Missing - no message
    - Service/tekton-kueue-webhook-service: Missing - no message
    - ServiceAccount/metrics-reader: Missing - no message
    - ServiceAccount/tekton-kueue-controller-manager: Missing - no message
    - ServiceAccount/tekton-kueue-webhook: Missing - no message
    - MutatingWebhookConfiguration/tekton-kueue-mutating-webhook-configuration: Missing - no message
    - Deployment/tekton-kueue-controller-manager: Missing - no message
  Operation Message: one or more synchronization tasks completed unsuccessfully. Retrying attempt #17 at 1:34PM.
artifacts/step-name/build-log.txt
Application: policies-in-cluster-local
-----------------------------------------------------------------------------
  Sync Status: OutOfSync
  Health Status: Healthy
  Unhealthy Resources:
    - ValidatingAdmissionPolicy/deny-on-validation-error.kueue.konflux-ci.dev: Missing - no message
    - ValidatingAdmissionPolicy/deny-serviceaccount-token-secrets.konflux-ci.dev: Missing - no message
    - ValidatingAdmissionPolicy/konflux-rbac-restrict-bindings-serviceaccounts-create.konflux-ci.dev: Missing - no message
  Operation Message: waiting for completion of hook batch/Job/kueue-crd-check
artifacts/step-name/build-log.txt
E0720 13:33:00.196988   18029 magefile.go:1347] failed to bootstrap cluster for disaster recovery tests: exit status 1

Analysis powered by prow-failure-analysis | Build: 2079171507761713152

@gbenhaim

Copy link
Copy Markdown
Member

@flacatus @enkeefe00 @p8r-the-gr8 do you think this test pipeline should be integrated with ring deployments?

…h, add patch verb to NetworkPolicy RBAC for oc apply idempotency, make cleanup discover backups by prefix pattern instead of relying on task result
@enkeefe00

Copy link
Copy Markdown
Contributor

@flacatus @enkeefe00 @p8r-the-gr8 do you think this test pipeline should be integrated with ring deployments?

In the next fixVersion, yes. This is out of scope for our current one.

@vsokolen-redhat

Copy link
Copy Markdown
Contributor Author

/retest pull-ci-redhat-appstudio-infra-deployments-main-appstudio-konflux-disaster-recovery

@vsokolen-redhat

Copy link
Copy Markdown
Contributor Author

/test appstudio-konflux-disaster-recovery

@qodo-for-redhat-appstudio

qodo-for-redhat-appstudio Bot commented Jul 20, 2026

Copy link
Copy Markdown

Unsupported PR languages

@vsokolen-redhat

Copy link
Copy Markdown
Contributor Author

/retest

@openshift-ci

openshift-ci Bot commented Jul 20, 2026

Copy link
Copy Markdown

@vsokolen-redhat: The following tests 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/appstudio-e2e-tests cbc1443 link true /test appstudio-e2e-tests
ci/prow/appstudio-konflux-disaster-recovery cbc1443 link false /test appstudio-konflux-disaster-recovery

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

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants