diff --git a/controlplane/rosa/controllers/rosacontrolplane_controller.go b/controlplane/rosa/controllers/rosacontrolplane_controller.go index b079f3fb32..42060c50e9 100644 --- a/controlplane/rosa/controllers/rosacontrolplane_controller.go +++ b/controlplane/rosa/controllers/rosacontrolplane_controller.go @@ -99,7 +99,7 @@ type ROSAControlPlaneReconciler struct { // SetupWithManager is used to setup the controller. func (r *ROSAControlPlaneReconciler) SetupWithManager(ctx context.Context, mgr ctrl.Manager, options controller.Options) error { log := logger.FromContext(ctx) - r.NewOCMClient = rosa.NewOCMClient + r.NewOCMClient = rosa.NewOCMClient2 r.NewStsClient = scope.NewSTSClient rosaControlPlane := &rosacontrolplanev1.ROSAControlPlane{} @@ -210,6 +210,9 @@ func (r *ROSAControlPlaneReconciler) reconcileNormal(ctx context.Context, rosaSc return ctrl.Result{}, err } } + if r.NewOCMClient == nil { + return ctrl.Result{}, fmt.Errorf("failed to create OCM client: NewOCMClient is nil") + } ocmClient, err := r.NewOCMClient(ctx, rosaScope) if err != nil || ocmClient == nil { @@ -432,14 +435,15 @@ func (r *ROSAControlPlaneReconciler) reconcileClusterVersion(rosaScope *scope.RO return nil } - scheduledUpgrade, err := rosa.CheckExistingScheduledUpgrade(ocmClient, cluster) + rosaOCMClient := ocmClient.(*ocm.Client) + scheduledUpgrade, err := rosa.CheckExistingScheduledUpgrade(rosaOCMClient, cluster) if err != nil { return fmt.Errorf("failed to get existing scheduled upgrades: %w", err) } if scheduledUpgrade == nil { ack := (rosaScope.ControlPlane.Spec.VersionGate == rosacontrolplanev1.Acknowledge || rosaScope.ControlPlane.Spec.VersionGate == rosacontrolplanev1.AlwaysAcknowledge) - scheduledUpgrade, err = rosa.ScheduleControlPlaneUpgrade(ocmClient, cluster, version, time.Now(), ack) + scheduledUpgrade, err = rosa.ScheduleControlPlaneUpgrade(rosaOCMClient, cluster, version, time.Now(), ack) if err != nil { condition := &clusterv1.Condition{ Type: rosacontrolplanev1.ROSAControlPlaneUpgradingCondition, @@ -787,8 +791,9 @@ func (r *ROSAControlPlaneReconciler) reconcileKubeconfig(ctx context.Context, ro userName := fmt.Sprintf("%s-capi-admin", clusterName) apiServerURL := cluster.API().URL() + c := ocmClient.(*ocm.Client) // create new user with admin privileges in the ROSA cluster if 'userName' doesn't already exist. - err = rosa.CreateAdminUserIfNotExist(ocmClient, cluster.ID(), userName, password) + err = rosa.CreateAdminUserIfNotExist(c, cluster.ID(), userName, password) if err != nil { return err } diff --git a/exp/controllers/rosamachinepool_controller.go b/exp/controllers/rosamachinepool_controller.go index 374d3b930c..753b167601 100644 --- a/exp/controllers/rosamachinepool_controller.go +++ b/exp/controllers/rosamachinepool_controller.go @@ -58,7 +58,7 @@ type ROSAMachinePoolReconciler struct { // SetupWithManager is used to setup the controller. func (r *ROSAMachinePoolReconciler) SetupWithManager(ctx context.Context, mgr ctrl.Manager, options controller.Options) error { log := logger.FromContext(ctx) - r.NewOCMClient = rosa.NewOCMClient + r.NewOCMClient = rosa.NewOCMClient2 r.NewStsClient = scope.NewSTSClient gvk, err := apiutil.GVKForObject(new(expinfrav1.ROSAMachinePool), mgr.GetScheme()) @@ -193,6 +193,9 @@ func (r *ROSAMachinePoolReconciler) reconcileNormal(ctx context.Context, return ctrl.Result{}, err } } + if r.NewOCMClient == nil { + return ctrl.Result{}, fmt.Errorf("failed to create OCM client: NewOCMClient is nil") + } ocmClient, err := r.NewOCMClient(ctx, rosaControlPlaneScope) if err != nil || ocmClient == nil { @@ -340,7 +343,8 @@ func (r *ROSAMachinePoolReconciler) reconcileMachinePoolVersion(machinePoolScope } if scheduledUpgrade == nil { - scheduledUpgrade, err = rosa.ScheduleNodePoolUpgrade(ocmClient, clusterID, nodePool, version, time.Now()) + rosaOCMClient := ocmClient.(*ocm.Client) + scheduledUpgrade, err = rosa.ScheduleNodePoolUpgrade(rosaOCMClient, clusterID, nodePool, version, time.Now()) if err != nil { return fmt.Errorf("failed to schedule nodePool upgrade to version %s: %w", version, err) } diff --git a/exp/controllers/rosamachinepool_controller_test.go b/exp/controllers/rosamachinepool_controller_test.go index 463d0fbf05..087f5c9c6a 100644 --- a/exp/controllers/rosamachinepool_controller_test.go +++ b/exp/controllers/rosamachinepool_controller_test.go @@ -422,11 +422,12 @@ func TestRosaMachinePoolReconcile(t *testing.T) { mockCtrl := gomock.NewController(t) recorder := record.NewFakeRecorder(10) ctx := context.TODO() + controlPlaneName := "rosa-control-plane-9" mp := &expinfrav1.ROSAMachinePool{ ObjectMeta: metav1.ObjectMeta{ - Name: "rosa-machinepool-9", + Name: controlPlaneName, Namespace: ns.Name, - UID: "rosa-machinepool-9", + UID: types.UID(controlPlaneName), Finalizers: []string{expinfrav1.RosaMachinePoolFinalizer}, }, TypeMeta: metav1.TypeMeta{ @@ -452,19 +453,21 @@ func TestRosaMachinePoolReconcile(t *testing.T) { cpPh, err := patch.NewHelper(cp, testEnv) cp.Status.Ready = true - cp.Status.ID = "rosa-control-plane-9" + cp.Status.ID = controlPlaneName g.Expect(cpPh.Patch(ctx, cp)).To(Succeed()) g.Expect(err).ShouldNot(HaveOccurred()) ocmMock := mocks.NewMockOCMClient(mockCtrl) + nodePoolName := "node-pool-1" expect := func(m *mocks.MockOCMClientMockRecorder) { m.GetNodePool(gomock.Any(), gomock.Any()).DoAndReturn(func(clusterId string, nodePoolID string) (*cmv1.NodePool, bool, error) { nodePoolBuilder := nodePoolBuilder(mp.Spec, omp.Spec) - nodePool, err := nodePoolBuilder.ID("node-pool-1").Build() + nodePool, err := nodePoolBuilder.ID(nodePoolName).Build() g.Expect(err).NotTo(HaveOccurred()) return nodePool, true, nil }).Times(1) - m.DeleteNodePool("rosa-control-plane-9", "node-pool-1").DoAndReturn(func(clusterId string, nodePoolID string) error { + m.DeleteNodePool(controlPlaneName, nodePoolName).DoAndReturn(func(clusterId string, nodePoolID string) error { + testEnv.Delete(ctx, mp) return nil }).Times(1) } @@ -512,11 +515,11 @@ func TestRosaMachinePoolReconcile(t *testing.T) { machinePoolScope.Close() time.Sleep(50 * time.Millisecond) - m := &expinfrav1.ROSAMachinePool{} + rosaMachinePool := &expinfrav1.ROSAMachinePool{} key := client.ObjectKey{Name: mp.Name, Namespace: ns.Name} - err4 := testEnv.Get(ctx, key, m) - g.Expect(err4).ToNot(HaveOccurred()) - g.Expect(m.Finalizers).To(BeNil()) + err4 := testEnv.Get(ctx, key, rosaMachinePool) + g.Expect(err4).To(HaveOccurred()) + g.Expect(rosaMachinePool.Finalizers).To(BeNil()) for _, obj := range objects { cleanupObject(g, obj) diff --git a/pkg/rosa/client.go b/pkg/rosa/client.go index d9b7b37308..ba446f308e 100644 --- a/pkg/rosa/client.go +++ b/pkg/rosa/client.go @@ -21,7 +21,19 @@ const ( ) // NewOCMClient creates a new OCM client. -func NewOCMClient(ctx context.Context, rosaScope *scope.ROSAControlPlaneScope) (OCMClient, error) { +func NewOCMClient(ctx context.Context, rosaScope *scope.ROSAControlPlaneScope) (*ocm.Client, error) { + token, url, err := ocmCredentials(ctx, rosaScope) + if err != nil { + return nil, err + } + return ocm.NewClient().Logger(logrus.New()).Config(&ocmcfg.Config{ + AccessToken: token, + URL: url, + }).Build() +} + +// NewOCMClient2 creates a new OCM client. +func NewOCMClient2(ctx context.Context, rosaScope *scope.ROSAControlPlaneScope) (OCMClient, error) { token, url, err := ocmCredentials(ctx, rosaScope) if err != nil { return nil, err @@ -36,6 +48,7 @@ func NewOCMClient(ctx context.Context, rosaScope *scope.ROSAControlPlaneScope) ( } return &c, err } + func newOCMRawConnection(ctx context.Context, rosaScope *scope.ROSAControlPlaneScope) (*sdk.Connection, error) { logger, err := sdk.NewGoLoggerBuilder(). Debug(false). diff --git a/pkg/rosa/idps.go b/pkg/rosa/idps.go index 0d80bd7d56..61cb21254d 100644 --- a/pkg/rosa/idps.go +++ b/pkg/rosa/idps.go @@ -4,6 +4,7 @@ import ( "fmt" cmv1 "github.com/openshift-online/ocm-sdk-go/clustersmgmt/v1" + "github.com/openshift/rosa/pkg/ocm" ) const ( @@ -13,7 +14,7 @@ const ( // CreateAdminUserIfNotExist creates a new admin user withe username/password in the cluster if username doesn't already exist. // the user is granted admin privileges by being added to a special IDP called `cluster-admin` which will be created if it doesn't already exist. -func CreateAdminUserIfNotExist(client OCMClient, clusterID, username, password string) error { +func CreateAdminUserIfNotExist(client *ocm.Client, clusterID, username, password string) error { existingClusterAdminIDP, userList, err := findExistingClusterAdminIDP(client, clusterID) if err != nil { return fmt.Errorf("failed to find existing cluster admin IDP: %w", err) @@ -74,7 +75,7 @@ func CreateAdminUserIfNotExist(client OCMClient, clusterID, username, password s } // CreateUserIfNotExist creates a new user with `username` and adds it to the group if it doesn't already exist. -func CreateUserIfNotExist(client OCMClient, clusterID string, group, username string) (*cmv1.User, error) { +func CreateUserIfNotExist(client *ocm.Client, clusterID string, group, username string) (*cmv1.User, error) { user, err := client.GetUser(clusterID, group, username) if user != nil || err != nil { return user, err diff --git a/pkg/rosa/versions.go b/pkg/rosa/versions.go index 18706567d0..27136c8772 100644 --- a/pkg/rosa/versions.go +++ b/pkg/rosa/versions.go @@ -13,7 +13,7 @@ import ( var MinSupportedVersion = semver.MustParse("4.14.0") // CheckExistingScheduledUpgrade checks and returns the current upgrade schedule if any. -func CheckExistingScheduledUpgrade(client OCMClient, cluster *cmv1.Cluster) (*cmv1.ControlPlaneUpgradePolicy, error) { +func CheckExistingScheduledUpgrade(client *ocm.Client, cluster *cmv1.Cluster) (*cmv1.ControlPlaneUpgradePolicy, error) { upgradePolicies, err := client.GetControlPlaneUpgradePolicies(cluster.ID()) if err != nil { return nil, err @@ -27,7 +27,7 @@ func CheckExistingScheduledUpgrade(client OCMClient, cluster *cmv1.Cluster) (*cm } // ScheduleControlPlaneUpgrade schedules a new control plane upgrade to the specified version at the specified time. -func ScheduleControlPlaneUpgrade(client OCMClient, cluster *cmv1.Cluster, version string, nextRun time.Time, ack bool) (*cmv1.ControlPlaneUpgradePolicy, error) { +func ScheduleControlPlaneUpgrade(client *ocm.Client, cluster *cmv1.Cluster, version string, nextRun time.Time, ack bool) (*cmv1.ControlPlaneUpgradePolicy, error) { // earliestNextRun is set to at least 5 min from now by the OCM API. // Set our next run request to something slightly longer than 5min to make sure we account for the latency between when we send this // request and when the server processes it. @@ -71,7 +71,7 @@ func ScheduleControlPlaneUpgrade(client OCMClient, cluster *cmv1.Cluster, versio } // ScheduleNodePoolUpgrade schedules a new nodePool upgrade to the specified version at the specified time. -func ScheduleNodePoolUpgrade(client OCMClient, clusterID string, nodePool *cmv1.NodePool, version string, nextRun time.Time) (*cmv1.NodePoolUpgradePolicy, error) { +func ScheduleNodePoolUpgrade(client *ocm.Client, clusterID string, nodePool *cmv1.NodePool, version string, nextRun time.Time) (*cmv1.NodePoolUpgradePolicy, error) { // earliestNextRun is set to at least 5 min from now by the OCM API. // Set our next run request to something slightly longer than 5min to make sure we account for the latency between when we send this // request and when the server processes it.