From eb2d0437560ce7ffb8ffe1792ea1b624bf80fed6 Mon Sep 17 00:00:00 2001 From: meggm Date: Fri, 7 Jun 2024 19:24:18 +0530 Subject: [PATCH 1/6] Remove role/rolebindings for csm objects --- controllers/acc_controller.go | 21 +++++++ pkg/utils/utils.go | 104 +++++++++++++++++++++++++++++++++- 2 files changed, 124 insertions(+), 1 deletion(-) diff --git a/controllers/acc_controller.go b/controllers/acc_controller.go index fd0e64f08..c441c3d5b 100644 --- a/controllers/acc_controller.go +++ b/controllers/acc_controller.go @@ -438,6 +438,7 @@ func applyAccConfigVersionAnnotations(ctx context.Context, instance *csmv1.ApexC // DeployApexConnectivityClient - perform deployment func DeployApexConnectivityClient(ctx context.Context, isDeleting bool, operatorConfig utils.OperatorConfig, cr csmv1.ApexConnectivityClient, ctrlClient crclient.Client) error { + log := logger.GetLogger(ctx) YamlString := "" ModifiedYamlString := "" deploymentPath := fmt.Sprintf("%s/clientconfig/%s/%s/%s", operatorConfig.ConfigDirectory, csmv1.DreadnoughtClient, cr.Spec.Client.ConfigVersion, AccManifest) @@ -465,6 +466,26 @@ func DeployApexConnectivityClient(ctx context.Context, isDeleting bool, operator } } + //If existing csm-installations are found, proceed to get those namespaces and create roles/rolebindings + csmList := &csmv1.ContainerStorageModuleList{} + err = ctrlClient.List(ctx, csmList) + if err == nil && len(csmList.Items) > 0 { + log.Info("Found existing csm installations. Proceeding to onboard them to Apex Navigator for Kubernetes") + BrownfieldCR := "brownfield-onboard.yaml" + + brownfieldManifestFilePath := fmt.Sprintf("%s/clientconfig/%s/%s/%s", operatorConfig.ConfigDirectory, csmv1.DreadnoughtClient, cr.Spec.Client.ConfigVersion, BrownfieldCR) + if isDeleting { + if err = utils.BrownfieldOnboard(ctx, brownfieldManifestFilePath, cr, ctrlClient, true); err != nil { + log.Error(err, "brownfield cluster onboarding failed") + } + } else { + if err = utils.BrownfieldOnboard(ctx, brownfieldManifestFilePath, cr, ctrlClient, false); err != nil { + log.Error(err, "brownfield cluster onboarding failed") + } + } + } + + log.Info("No existing csm installations found") return nil } diff --git a/pkg/utils/utils.go b/pkg/utils/utils.go index 1cfbeb70e..0dad22d7c 100644 --- a/pkg/utils/utils.go +++ b/pkg/utils/utils.go @@ -42,6 +42,7 @@ import ( t1 "k8s.io/apimachinery/pkg/types" confv1 "k8s.io/client-go/applyconfigurations/apps/v1" acorev1 "k8s.io/client-go/applyconfigurations/core/v1" + "sigs.k8s.io/controller-runtime/pkg/log" "sigs.k8s.io/controller-runtime/pkg/reconcile" "sigs.k8s.io/yaml" @@ -139,6 +140,9 @@ const ( PodmonNodeComponent = "podmon-node" // ApplicationMobilityNamespace - application-mobility ApplicationMobilityNamespace = "application-mobility" + // BrownfieldNamespace + ExistingNamespace = "" + ClientNamespace = "" ) // SplitYaml divides a big bytes of yaml files in individual yaml files. @@ -1202,7 +1206,7 @@ func getUpgradeInfo[T csmv1.CSMComponentType](ctx context.Context, operatorConfi return upgradePath.MinUpgradePath, nil } -func getNamespaces(ctx context.Context, ctrlClient crclient.Client) ([]string, error) { +func GetNamespaces(ctx context.Context, ctrlClient crclient.Client) ([]string, error) { // Set to store unique namespaces namespaceMap := make(map[string]struct{}) @@ -1223,3 +1227,101 @@ func getNamespaces(ctx context.Context, ctrlClient crclient.Client) ([]string, e return namespaces, nil } + +func BrownfieldOnboard(ctx context.Context, path string, cr csmv1.ApexConnectivityClient, ctrlClient crclient.Client, isDeleting bool) error { + log := logger.GetLogger(ctx) + + namespace, err := GetNamespaces(ctx, ctrlClient) + if err != nil { + log.Error(err, "Failed to get namespaces") + return err + } + + buf, err := os.ReadFile(filepath.Clean(path)) + if err != nil { + log.Error(err, "Failed to read manifest file") + return err + } + + yamlFile := string(buf) + + for _, ns := range namespace { + + yamlFile := strings.ReplaceAll(yamlFile, ExistingNamespace, ns) + yamlFile = strings.ReplaceAll(yamlFile, ClientNamespace, cr.Namespace) + if isDeleting { + err := DeleteObjects(ctx, yamlFile, ctrlClient) + if err != nil { + return err + } + } else { + err := CreateObjects(ctx, yamlFile, ctrlClient) + if err != nil { + return err + } + } + } + return nil +} + +func CreateObjects(ctx context.Context, yamlFile string, ctrlClient crclient.Client) error { + deployObjects, err := GetModuleComponentObj([]byte(yamlFile)) + if err != nil { + return err + } + + for _, obj := range deployObjects { + log.FromContext(ctx).Info("namespace of parsed object is", "object", obj.GetNamespace()) + + found := obj.DeepCopyObject().(crclient.Object) + err := ctrlClient.Get(ctx, crclient.ObjectKey{Namespace: obj.GetNamespace(), Name: obj.GetName()}, found) + if err != nil && k8serror.IsNotFound(err) { + log.FromContext(ctx).Info("Creating a new object", "object", obj.GetObjectKind().GroupVersionKind().String()) + err := ctrlClient.Create(ctx, obj) + if err != nil { + return err + } + } else if err != nil { + log.FromContext(ctx).Info("Unknown error trying to retrieve the object.", "Error", err.Error()) + return err + } else { + log.FromContext(ctx).Info("Creating a new Object", "object", obj.GetObjectKind().GroupVersionKind().String()) + err = ctrlClient.Update(ctx, obj) + if err != nil { + return err + } + } + } + return nil +} + +func DeleteObjects(ctx context.Context, yamlFile string, ctrlClient crclient.Client) error { + deployObjects, err := GetModuleComponentObj([]byte(yamlFile)) + if err != nil { + return err + } + + for _, obj := range deployObjects { + log.FromContext(ctx).Info("namespace of parsed object is", "object", obj.GetNamespace()) + + found := obj.DeepCopyObject().(crclient.Object) + err := ctrlClient.Get(ctx, crclient.ObjectKey{Namespace: obj.GetNamespace(), Name: obj.GetName()}, found) + if err != nil && k8serror.IsNotFound(err) { + log.FromContext(ctx).Info("Deleting an object", "object", obj.GetObjectKind().GroupVersionKind().String()) + err := ctrlClient.Create(ctx, obj) + if err != nil { + return err + } + } else if err != nil { + log.FromContext(ctx).Info("Unknown error trying to retrieve the object.", "Error", err.Error()) + return err + } else { + log.FromContext(ctx).Info("Deleting an Object", "object", obj.GetObjectKind().GroupVersionKind().String()) + err = ctrlClient.Update(ctx, obj) + if err != nil { + return err + } + } + } + return nil +} From 918e4dc3435a1a63eb5365e1f7dc0f405883d0fc Mon Sep 17 00:00:00 2001 From: meggm Date: Fri, 7 Jun 2024 22:27:58 +0530 Subject: [PATCH 2/6] Remove role/rolebindings for csm objects --- pkg/utils/utils.go | 45 +++++++++++---------------------------------- 1 file changed, 11 insertions(+), 34 deletions(-) diff --git a/pkg/utils/utils.go b/pkg/utils/utils.go index 0dad22d7c..ff08c01c1 100644 --- a/pkg/utils/utils.go +++ b/pkg/utils/utils.go @@ -1249,10 +1249,18 @@ func BrownfieldOnboard(ctx context.Context, path string, cr csmv1.ApexConnectivi yamlFile := strings.ReplaceAll(yamlFile, ExistingNamespace, ns) yamlFile = strings.ReplaceAll(yamlFile, ClientNamespace, cr.Namespace) + + deployObjects, err := GetModuleComponentObj([]byte(yamlFile)) + if err != nil { + return err + } + if isDeleting { - err := DeleteObjects(ctx, yamlFile, ctrlClient) - if err != nil { - return err + for _, ctrlObj := range deployObjects { + err := DeleteObject(ctx, ctrlObj, ctrlClient) + if err != nil { + return err + } } } else { err := CreateObjects(ctx, yamlFile, ctrlClient) @@ -1294,34 +1302,3 @@ func CreateObjects(ctx context.Context, yamlFile string, ctrlClient crclient.Cli } return nil } - -func DeleteObjects(ctx context.Context, yamlFile string, ctrlClient crclient.Client) error { - deployObjects, err := GetModuleComponentObj([]byte(yamlFile)) - if err != nil { - return err - } - - for _, obj := range deployObjects { - log.FromContext(ctx).Info("namespace of parsed object is", "object", obj.GetNamespace()) - - found := obj.DeepCopyObject().(crclient.Object) - err := ctrlClient.Get(ctx, crclient.ObjectKey{Namespace: obj.GetNamespace(), Name: obj.GetName()}, found) - if err != nil && k8serror.IsNotFound(err) { - log.FromContext(ctx).Info("Deleting an object", "object", obj.GetObjectKind().GroupVersionKind().String()) - err := ctrlClient.Create(ctx, obj) - if err != nil { - return err - } - } else if err != nil { - log.FromContext(ctx).Info("Unknown error trying to retrieve the object.", "Error", err.Error()) - return err - } else { - log.FromContext(ctx).Info("Deleting an Object", "object", obj.GetObjectKind().GroupVersionKind().String()) - err = ctrlClient.Update(ctx, obj) - if err != nil { - return err - } - } - } - return nil -} From 85d9e33bf15f6f4355bae10e15421191cb0e24cb Mon Sep 17 00:00:00 2001 From: meggm Date: Fri, 7 Jun 2024 22:33:51 +0530 Subject: [PATCH 3/6] Remove role/rolebindings for csm objects --- controllers/csm_controller.go | 53 +++++++++++++++++++++++++++++++++++ 1 file changed, 53 insertions(+) diff --git a/controllers/csm_controller.go b/controllers/csm_controller.go index dd2f76010..7755b8dad 100644 --- a/controllers/csm_controller.go +++ b/controllers/csm_controller.go @@ -272,6 +272,14 @@ func (r *ContainerStorageModuleReconciler) Reconcile(ctx context.Context, req ct if csm.IsBeingDeleted() { log.Infow("Delete request", "csm", req.Namespace, "Name", req.Name) + //remove role/rolebinding from the csm object namespace + err := r.SyncRbac(ctx, *csm, *operatorConfig, r.Client) + if err != nil { + r.EventRecorder.Event(csm, corev1.EventTypeWarning, csmv1.EventDeleted, fmt.Sprintf("Failed to sync rbac: %s", err)) + log.Errorw("sync rbac", "error", err.Error()) + return ctrl.Result{}, fmt.Errorf("error when syncing rbac: %v", err) + } + // check for force cleanup if csm.Spec.Driver.ForceRemoveDriver { // remove all resources deployed from CR by operator @@ -879,6 +887,26 @@ func (r *ContainerStorageModuleReconciler) SyncCSM(ctx context.Context, cr csmv1 } } + //If dell connectivity client is deployed, create role/rolebindings in the csm namespaces + list := &csmv1.ApexConnectivityClientList{} + if err := ctrlClient.List(ctx, list); err != nil { + log.Info("dell connectivity client not found") + return nil + } else if len(list.Items) <= 0 { + log.Info("dell connectivity client not found") + return nil + } else { + log.Info("dell connectivity client found") + cr := new(csmv1.ApexConnectivityClient) + BrownfieldCR := "brownfield-onboard.yaml" + configVersion1 := list.Items[0].Spec.Client.ConfigVersion + brownfieldManifestFilePath := fmt.Sprintf("%s/clientconfig/%s/%s/%s", operatorConfig.ConfigDirectory, csmv1.DreadnoughtClient, configVersion1, BrownfieldCR) + + if err = utils.BrownfieldOnboard(ctx, brownfieldManifestFilePath, *cr, ctrlClient, false); err != nil { + log.Error(err, "error creating role/rolebindings to newly discovered csm namespace") + return err + } + } return nil } @@ -1419,6 +1447,31 @@ func applyConfigVersionAnnotations(ctx context.Context, instance *csmv1.Containe return false } +func (r *ContainerStorageModuleReconciler) SyncRbac(ctx context.Context, cr csmv1.ContainerStorageModule, operatorConfig utils.OperatorConfig, ctrlClient client.Client) error { + log := logger.GetLogger(ctx) + //If dell connectivity client is deployed, create role/rolebindings in the csm namespaces + list := &csmv1.ApexConnectivityClientList{} + if err := ctrlClient.List(ctx, list); err != nil { + log.Info("dell connectivity client not found") + return nil + } else if len(list.Items) <= 0 { + log.Info("dell connectivity client not found") + return nil + } else { + log.Info("dell connectivity client found") + cr := new(csmv1.ApexConnectivityClient) + BrownfieldCR := "brownfield-onboard.yaml" + configVersion1 := list.Items[0].Spec.Client.ConfigVersion + brownfieldManifestFilePath := fmt.Sprintf("%s/clientconfig/%s/%s/%s", operatorConfig.ConfigDirectory, csmv1.DreadnoughtClient, configVersion1, BrownfieldCR) + + if err = utils.BrownfieldOnboard(ctx, brownfieldManifestFilePath, *cr, ctrlClient, true); err != nil { + log.Error(err, "error deleting role/rolebindings to newly discovered csm namespace") + return err + } + } + return nil +} + // GetClient - returns the split client func (r *ContainerStorageModuleReconciler) GetClient() client.Client { return r.Client From d957c217703d7e2aa65ffa4b15e43ebe752793a6 Mon Sep 17 00:00:00 2001 From: meggm Date: Fri, 7 Jun 2024 22:49:43 +0530 Subject: [PATCH 4/6] Remove role/rolebindings for csm objects --- controllers/csm_controller.go | 1 + pkg/utils/utils.go | 8 ++++++-- 2 files changed, 7 insertions(+), 2 deletions(-) diff --git a/controllers/csm_controller.go b/controllers/csm_controller.go index 7755b8dad..8b8628a1d 100644 --- a/controllers/csm_controller.go +++ b/controllers/csm_controller.go @@ -1447,6 +1447,7 @@ func applyConfigVersionAnnotations(ctx context.Context, instance *csmv1.Containe return false } +// SyncRbac - Delete the role/rolebindings in the csm namespaces func (r *ContainerStorageModuleReconciler) SyncRbac(ctx context.Context, cr csmv1.ContainerStorageModule, operatorConfig utils.OperatorConfig, ctrlClient client.Client) error { log := logger.GetLogger(ctx) //If dell connectivity client is deployed, create role/rolebindings in the csm namespaces diff --git a/pkg/utils/utils.go b/pkg/utils/utils.go index ff08c01c1..f206060d1 100644 --- a/pkg/utils/utils.go +++ b/pkg/utils/utils.go @@ -140,9 +140,10 @@ const ( PodmonNodeComponent = "podmon-node" // ApplicationMobilityNamespace - application-mobility ApplicationMobilityNamespace = "application-mobility" - // BrownfieldNamespace + // ExistingNamespace - BrownfieldNamespace ExistingNamespace = "" - ClientNamespace = "" + // ClientNamespace - acc-client-namespace + ClientNamespace = "" ) // SplitYaml divides a big bytes of yaml files in individual yaml files. @@ -1206,6 +1207,7 @@ func getUpgradeInfo[T csmv1.CSMComponentType](ctx context.Context, operatorConfi return upgradePath.MinUpgradePath, nil } +// GetNamespaces - get all namespaces func GetNamespaces(ctx context.Context, ctrlClient crclient.Client) ([]string, error) { // Set to store unique namespaces namespaceMap := make(map[string]struct{}) @@ -1228,6 +1230,7 @@ func GetNamespaces(ctx context.Context, ctrlClient crclient.Client) ([]string, e return namespaces, nil } +// BrownfieldOnboard - brownfield onboarding func BrownfieldOnboard(ctx context.Context, path string, cr csmv1.ApexConnectivityClient, ctrlClient crclient.Client, isDeleting bool) error { log := logger.GetLogger(ctx) @@ -1272,6 +1275,7 @@ func BrownfieldOnboard(ctx context.Context, path string, cr csmv1.ApexConnectivi return nil } +// CreateObjects - create objects func CreateObjects(ctx context.Context, yamlFile string, ctrlClient crclient.Client) error { deployObjects, err := GetModuleComponentObj([]byte(yamlFile)) if err != nil { From 6c74f09f7b76ad8bf5fa8b50a4a5e9dae84511d2 Mon Sep 17 00:00:00 2001 From: meggm Date: Mon, 10 Jun 2024 12:20:49 +0530 Subject: [PATCH 5/6] Remove role/rolebindings for csm objects --- controllers/acc_controller.go | 2 -- pkg/utils/utils.go | 48 ++++++----------------------------- 2 files changed, 8 insertions(+), 42 deletions(-) diff --git a/controllers/acc_controller.go b/controllers/acc_controller.go index c441c3d5b..9afccf874 100644 --- a/controllers/acc_controller.go +++ b/controllers/acc_controller.go @@ -484,8 +484,6 @@ func DeployApexConnectivityClient(ctx context.Context, isDeleting bool, operator } } } - - log.Info("No existing csm installations found") return nil } diff --git a/pkg/utils/utils.go b/pkg/utils/utils.go index f206060d1..1457c6637 100644 --- a/pkg/utils/utils.go +++ b/pkg/utils/utils.go @@ -1258,51 +1258,19 @@ func BrownfieldOnboard(ctx context.Context, path string, cr csmv1.ApexConnectivi return err } - if isDeleting { - for _, ctrlObj := range deployObjects { + for _, ctrlObj := range deployObjects { + if isDeleting { err := DeleteObject(ctx, ctrlObj, ctrlClient) if err != nil { return err } - } - } else { - err := CreateObjects(ctx, yamlFile, ctrlClient) - if err != nil { - return err - } - } - } - return nil -} - -// CreateObjects - create objects -func CreateObjects(ctx context.Context, yamlFile string, ctrlClient crclient.Client) error { - deployObjects, err := GetModuleComponentObj([]byte(yamlFile)) - if err != nil { - return err - } - - for _, obj := range deployObjects { - log.FromContext(ctx).Info("namespace of parsed object is", "object", obj.GetNamespace()) - - found := obj.DeepCopyObject().(crclient.Object) - err := ctrlClient.Get(ctx, crclient.ObjectKey{Namespace: obj.GetNamespace(), Name: obj.GetName()}, found) - if err != nil && k8serror.IsNotFound(err) { - log.FromContext(ctx).Info("Creating a new object", "object", obj.GetObjectKind().GroupVersionKind().String()) - err := ctrlClient.Create(ctx, obj) - if err != nil { - return err - } - } else if err != nil { - log.FromContext(ctx).Info("Unknown error trying to retrieve the object.", "Error", err.Error()) - return err - } else { - log.FromContext(ctx).Info("Creating a new Object", "object", obj.GetObjectKind().GroupVersionKind().String()) - err = ctrlClient.Update(ctx, obj) - if err != nil { - return err + } else { + err := ApplyObject(ctx, ctrlObj, ctrlClient) + if err != nil { + return err + } } } } return nil -} +} \ No newline at end of file From ba066e05b999d1a1f010f1e8eadc1b84830a2240 Mon Sep 17 00:00:00 2001 From: meggm Date: Mon, 10 Jun 2024 12:28:40 +0530 Subject: [PATCH 6/6] Remove role/rolebindings for csm objects --- pkg/utils/utils.go | 1 - 1 file changed, 1 deletion(-) diff --git a/pkg/utils/utils.go b/pkg/utils/utils.go index 1457c6637..fdfe0ae43 100644 --- a/pkg/utils/utils.go +++ b/pkg/utils/utils.go @@ -42,7 +42,6 @@ import ( t1 "k8s.io/apimachinery/pkg/types" confv1 "k8s.io/client-go/applyconfigurations/apps/v1" acorev1 "k8s.io/client-go/applyconfigurations/core/v1" - "sigs.k8s.io/controller-runtime/pkg/log" "sigs.k8s.io/controller-runtime/pkg/reconcile" "sigs.k8s.io/yaml"