Skip to content

Commit fd0ad38

Browse files
authored
Merge pull request #5166 from serngawy/versionGate
🐛 ROSA: Fix version gate Ack for rosa hcp y-stream version upgrade
2 parents b25eef6 + ab89ef9 commit fd0ad38

File tree

5 files changed

+97
-3
lines changed

5 files changed

+97
-3
lines changed

config/crd/bases/controlplane.cluster.x-k8s.io_rosacontrolplanes.yaml

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -787,6 +787,19 @@ spec:
787787
version:
788788
description: OpenShift semantic version, for example "4.14.5".
789789
type: string
790+
versionGate:
791+
default: WaitForAcknowledge
792+
description: |-
793+
VersionGate requires acknowledgment when upgrading ROSA-HCP y-stream versions (e.g., from 4.15 to 4.16).
794+
Default is WaitForAcknowledge.
795+
WaitForAcknowledge: If acknowledgment is required, the upgrade will not proceed until VersionGate is set to Acknowledge or AlwaysAcknowledge.
796+
Acknowledge: If acknowledgment is required, apply it for the upgrade. After upgrade is done set the version gate to WaitForAcknowledge.
797+
AlwaysAcknowledge: If acknowledgment is required, apply it and proceed with the upgrade.
798+
enum:
799+
- Acknowledge
800+
- WaitForAcknowledge
801+
- AlwaysAcknowledge
802+
type: string
790803
workerRoleARN:
791804
description: WorkerRoleARN is an AWS IAM role that will be attached
792805
to worker instances.
@@ -801,11 +814,17 @@ spec:
801814
- subnets
802815
- supportRoleARN
803816
- version
817+
- versionGate
804818
- workerRoleARN
805819
type: object
806820
status:
807821
description: RosaControlPlaneStatus defines the observed state of ROSAControlPlane.
808822
properties:
823+
availableUpgrades:
824+
description: Available upgrades for the ROSA hosted control plane.
825+
items:
826+
type: string
827+
type: array
809828
conditions:
810829
description: Conditions specifies the conditions for the managed control
811830
plane

controlplane/rosa/api/v1beta2/rosacontrolplane_types.go

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,20 @@ const (
3838
Private RosaEndpointAccessType = "Private"
3939
)
4040

41+
// VersionGateAckType specifies the version gate acknowledgement.
42+
type VersionGateAckType string
43+
44+
const (
45+
// Acknowledge if acknowledgment is required and proceed with the upgrade.
46+
Acknowledge VersionGateAckType = "Acknowledge"
47+
48+
// WaitForAcknowledge if acknowledgment is required, wait not to proceed with the upgrade.
49+
WaitForAcknowledge VersionGateAckType = "WaitForAcknowledge"
50+
51+
// AlwaysAcknowledge always acknowledg if required and proceed with the upgrade.
52+
AlwaysAcknowledge VersionGateAckType = "AlwaysAcknowledge"
53+
)
54+
4155
// RosaControlPlaneSpec defines the desired state of ROSAControlPlane.
4256
type RosaControlPlaneSpec struct { //nolint: maligned
4357
// Cluster name must be valid DNS-1035 label, so it must consist of lower case alphanumeric
@@ -77,6 +91,16 @@ type RosaControlPlaneSpec struct { //nolint: maligned
7791
// OpenShift semantic version, for example "4.14.5".
7892
Version string `json:"version"`
7993

94+
// VersionGate requires acknowledgment when upgrading ROSA-HCP y-stream versions (e.g., from 4.15 to 4.16).
95+
// Default is WaitForAcknowledge.
96+
// WaitForAcknowledge: If acknowledgment is required, the upgrade will not proceed until VersionGate is set to Acknowledge or AlwaysAcknowledge.
97+
// Acknowledge: If acknowledgment is required, apply it for the upgrade. After upgrade is done set the version gate to WaitForAcknowledge.
98+
// AlwaysAcknowledge: If acknowledgment is required, apply it and proceed with the upgrade.
99+
//
100+
// +kubebuilder:validation:Enum=Acknowledge;WaitForAcknowledge;AlwaysAcknowledge
101+
// +kubebuilder:default=WaitForAcknowledge
102+
VersionGate VersionGateAckType `json:"versionGate"`
103+
80104
// AWS IAM roles used to perform credential requests by the openshift operators.
81105
RolesRef AWSRolesRef `json:"rolesRef"`
82106

@@ -697,6 +721,9 @@ type RosaControlPlaneStatus struct {
697721
ConsoleURL string `json:"consoleURL,omitempty"`
698722
// OIDCEndpointURL is the endpoint url for the managed OIDC provider.
699723
OIDCEndpointURL string `json:"oidcEndpointURL,omitempty"`
724+
725+
// Available upgrades for the ROSA hosted control plane.
726+
AvailableUpgrades []string `json:"availableUpgrades,omitempty"`
700727
}
701728

702729
// +kubebuilder:object:root=true

controlplane/rosa/api/v1beta2/zz_generated.deepcopy.go

Lines changed: 5 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

controlplane/rosa/controllers/rosacontrolplane_controller.go

Lines changed: 22 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -410,6 +410,17 @@ func (r *ROSAControlPlaneReconciler) reconcileClusterVersion(rosaScope *scope.RO
410410
version := rosaScope.ControlPlane.Spec.Version
411411
if version == rosa.RawVersionID(cluster.Version()) {
412412
conditions.MarkFalse(rosaScope.ControlPlane, rosacontrolplanev1.ROSAControlPlaneUpgradingCondition, "upgraded", clusterv1.ConditionSeverityInfo, "")
413+
414+
if cluster.Version() != nil {
415+
rosaScope.ControlPlane.Status.AvailableUpgrades = cluster.Version().AvailableUpgrades()
416+
}
417+
418+
// Set the version gate to WaitForAcknowledge as the previous upgrade is applied.
419+
if rosaScope.ControlPlane.Spec.VersionGate == rosacontrolplanev1.Acknowledge {
420+
rosaScope.ControlPlane.Spec.VersionGate = rosacontrolplanev1.WaitForAcknowledge
421+
}
422+
423+
// return as there is no upgrade to schedule.
413424
return nil
414425
}
415426

@@ -419,9 +430,18 @@ func (r *ROSAControlPlaneReconciler) reconcileClusterVersion(rosaScope *scope.RO
419430
}
420431

421432
if scheduledUpgrade == nil {
422-
scheduledUpgrade, err = rosa.ScheduleControlPlaneUpgrade(ocmClient, cluster, version, time.Now())
433+
ack := (rosaScope.ControlPlane.Spec.VersionGate == rosacontrolplanev1.Acknowledge || rosaScope.ControlPlane.Spec.VersionGate == rosacontrolplanev1.AlwaysAcknowledge)
434+
scheduledUpgrade, err = rosa.ScheduleControlPlaneUpgrade(ocmClient, cluster, version, time.Now(), ack)
423435
if err != nil {
424-
return fmt.Errorf("failed to schedule control plane upgrade to version %s: %w", version, err)
436+
condition := &clusterv1.Condition{
437+
Type: rosacontrolplanev1.ROSAControlPlaneUpgradingCondition,
438+
Status: corev1.ConditionFalse,
439+
Reason: "failed",
440+
Message: fmt.Sprintf("failed to schedule upgrade to version %s: %v", version, err),
441+
}
442+
conditions.Set(rosaScope.ControlPlane, condition)
443+
444+
return err
425445
}
426446
}
427447

pkg/rosa/versions.go

Lines changed: 24 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,7 @@ func CheckExistingScheduledUpgrade(client *ocm.Client, cluster *cmv1.Cluster) (*
2727
}
2828

2929
// ScheduleControlPlaneUpgrade schedules a new control plane upgrade to the specified version at the specified time.
30-
func ScheduleControlPlaneUpgrade(client *ocm.Client, cluster *cmv1.Cluster, version string, nextRun time.Time) (*cmv1.ControlPlaneUpgradePolicy, error) {
30+
func ScheduleControlPlaneUpgrade(client *ocm.Client, cluster *cmv1.Cluster, version string, nextRun time.Time, ack bool) (*cmv1.ControlPlaneUpgradePolicy, error) {
3131
// earliestNextRun is set to at least 5 min from now by the OCM API.
3232
// Set our next run request to something slightly longer than 5min to make sure we account for the latency between when we send this
3333
// request and when the server processes it.
@@ -41,10 +41,32 @@ func ScheduleControlPlaneUpgrade(client *ocm.Client, cluster *cmv1.Cluster, vers
4141
ScheduleType(cmv1.ScheduleTypeManual).
4242
Version(version).
4343
NextRun(nextRun).
44+
EnableMinorVersionUpgrades(true).
4445
Build()
4546
if err != nil {
4647
return nil, err
4748
}
49+
50+
versionGates, err := client.GetMissingGateAgreementsHypershift(cluster.ID(), upgradePolicy)
51+
if err != nil {
52+
return nil, err
53+
}
54+
55+
if !ack && len(versionGates) > 0 {
56+
errMess := "version gate acknowledgement required"
57+
for id := range versionGates {
58+
errMess = fmt.Sprintf(errMess+"\nid:%s\n %s\n %s\n %s\n", versionGates[id].ID(), versionGates[id].Description(), versionGates[id].DocumentationURL(), versionGates[id].WarningMessage())
59+
}
60+
61+
return nil, fmt.Errorf("%s", errMess)
62+
}
63+
64+
for id := range versionGates {
65+
if err = client.AckVersionGate(cluster.ID(), versionGates[id].ID()); err != nil {
66+
return nil, err
67+
}
68+
}
69+
4870
return client.ScheduleHypershiftControlPlaneUpgrade(cluster.ID(), upgradePolicy)
4971
}
5072

@@ -64,6 +86,7 @@ func ScheduleNodePoolUpgrade(client *ocm.Client, clusterID string, nodePool *cmv
6486
ScheduleType(cmv1.ScheduleTypeManual).
6587
Version(version).
6688
NextRun(nextRun).
89+
EnableMinorVersionUpgrades(true).
6790
Build()
6891
if err != nil {
6992
return nil, err

0 commit comments

Comments
 (0)