diff --git a/operator/pkg/config/multiclusterglobalhub_config.go b/operator/pkg/config/multiclusterglobalhub_config.go index 3d7a82223..b48ab44b4 100644 --- a/operator/pkg/config/multiclusterglobalhub_config.go +++ b/operator/pkg/config/multiclusterglobalhub_config.go @@ -38,6 +38,7 @@ import ( "github.com/stolostron/multicluster-global-hub/operator/api/operator/v1alpha4" operatorconstants "github.com/stolostron/multicluster-global-hub/operator/pkg/constants" + "github.com/stolostron/multicluster-global-hub/pkg/constants" "github.com/stolostron/multicluster-global-hub/pkg/logger" ) @@ -131,6 +132,27 @@ var MGHPred = predicate.Funcs{ }, } +// watch globalhub applied services +var GeneralPredicate = predicate.Funcs{ + CreateFunc: func(e event.CreateEvent) bool { + return false + }, + UpdateFunc: func(e event.UpdateEvent) bool { + if !(e.ObjectNew.GetLabels()[constants.GlobalHubOwnerLabelKey] == + constants.GHOperatorOwnerLabelVal) { + return false + } + return e.ObjectNew.GetGeneration() != e.ObjectOld.GetGeneration() + }, + DeleteFunc: func(e event.DeleteEvent) bool { + if e.Object.GetLabels()[constants.GlobalHubOwnerLabelKey] == + constants.GHOperatorOwnerLabelVal { + return true + } + return false + }, +} + // getAnnotation returns the annotation value for a given key, or an empty string if not set func getAnnotation(mgh *v1alpha4.MulticlusterGlobalHub, annotationKey string) string { annotations := mgh.GetAnnotations() diff --git a/operator/pkg/controllers/acm/resources.go b/operator/pkg/controllers/acm/resources.go index 55f0d05e0..bcfff71f3 100644 --- a/operator/pkg/controllers/acm/resources.go +++ b/operator/pkg/controllers/acm/resources.go @@ -90,10 +90,11 @@ func (r *ACMResourceController) readyToWatchACMResources() bool { } func StartController(opts config.ControllerOption) (config.ControllerInterface, error) { - log.Info("start acm controller") if acmResourceController != nil { return acmResourceController, nil } + log.Info("start acm controller") + acmController := &ACMResourceController{ Manager: opts.Manager, Resources: make(map[string]bool), diff --git a/operator/pkg/controllers/agent/addon_manager.go b/operator/pkg/controllers/agent/addon_manager.go index 20396eee9..a534e9c5c 100644 --- a/operator/pkg/controllers/agent/addon_manager.go +++ b/operator/pkg/controllers/agent/addon_manager.go @@ -61,11 +61,11 @@ func ReadyToEnableAddonManager(mgh *v1alpha4.MulticlusterGlobalHub) bool { } func StartAddonManagerController(initOption config.ControllerOption) (config.ControllerInterface, error) { - log.Info("start addon manager controller") - if addonManagerController != nil { return addonManagerController, nil } + log.Info("start addon manager controller") + if !ReadyToEnableAddonManager(initOption.MulticlusterGlobalHub) { return nil, nil } diff --git a/operator/pkg/controllers/agent/default_agent_controller.go b/operator/pkg/controllers/agent/default_agent_controller.go index 3347162fb..b30346133 100644 --- a/operator/pkg/controllers/agent/default_agent_controller.go +++ b/operator/pkg/controllers/agent/default_agent_controller.go @@ -128,10 +128,11 @@ func NewDefaultAgentController(c client.Client) *DefaultAgentController { } func StartDefaultAgentController(initOption config.ControllerOption) (config.ControllerInterface, error) { - log.Info("start default agent controller") if defaultAgentController != nil { return defaultAgentController, nil } + log.Info("start default agent controller") + if !ReadyToEnableAddonManager(initOption.MulticlusterGlobalHub) { return nil, nil } diff --git a/operator/pkg/controllers/agent/hosted_agent_controller.go b/operator/pkg/controllers/agent/hosted_agent_controller.go index a7fd1a8a9..5b6a49a16 100644 --- a/operator/pkg/controllers/agent/hosted_agent_controller.go +++ b/operator/pkg/controllers/agent/hosted_agent_controller.go @@ -56,14 +56,15 @@ var ( ) func StartHostedAgentController(initOption config.ControllerOption) (config.ControllerInterface, error) { - log.Info("start hosted agent controller") - if hostedAgentController != nil { return hostedAgentController, nil } if !config.GetImportClusterInHosted() { return nil, nil } + + log.Info("start hosted agent controller") + if !ReadyToEnableAddonManager(initOption.MulticlusterGlobalHub) { return nil, nil } diff --git a/operator/pkg/controllers/backup/backup_start.go b/operator/pkg/controllers/backup/backup_start.go index 1088346f1..936acca43 100644 --- a/operator/pkg/controllers/backup/backup_start.go +++ b/operator/pkg/controllers/backup/backup_start.go @@ -69,10 +69,11 @@ func GetBackupController() *BackupReconciler { } func StartController(initOption config.ControllerOption) (config.ControllerInterface, error) { - log.Infof("start backup controller") if backupController != nil { return backupController, nil } + log.Infof("start backup controller") + if !config.IsACMResourceReady() { return nil, nil } diff --git a/operator/pkg/controllers/grafana/grafana_reconciler.go b/operator/pkg/controllers/grafana/grafana_reconciler.go index 2a026eda9..263910eab 100644 --- a/operator/pkg/controllers/grafana/grafana_reconciler.go +++ b/operator/pkg/controllers/grafana/grafana_reconciler.go @@ -15,6 +15,7 @@ import ( "gopkg.in/yaml.v2" appsv1 "k8s.io/api/apps/v1" corev1 "k8s.io/api/core/v1" + rbacv1 "k8s.io/api/rbac/v1" "k8s.io/apimachinery/pkg/api/errors" "k8s.io/apimachinery/pkg/api/meta" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" @@ -125,10 +126,11 @@ func (r *GrafanaReconciler) IsResourceRemoved() bool { } func StartController(initOption config.ControllerOption) (config.ControllerInterface, error) { - log.Info("start grafana controller") if grafanaController != nil { return grafanaController, nil } + log.Info("start grafana controller") + if !config.IsACMResourceReady() { return nil, nil } @@ -156,7 +158,17 @@ func (r *GrafanaReconciler) SetupWithManager(mgr ctrl.Manager) error { Watches(&corev1.ConfigMap{}, &handler.EnqueueRequestForObject{}, builder.WithPredicates(configmapPred)). Watches(&appsv1.Deployment{}, - &handler.EnqueueRequestForObject{}, builder.WithPredicates(deplomentPred)) + &handler.EnqueueRequestForObject{}, builder.WithPredicates(deplomentPred)). + Watches(&corev1.Service{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)). + Watches(&corev1.ServiceAccount{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)). + Watches(&rbacv1.ClusterRole{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)). + Watches(&rbacv1.ClusterRoleBinding{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)). + Watches(&routev1.Route{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)) if _, err := mgr.GetRESTMapper().KindFor(schema.GroupVersionResource{ Group: "image.openshift.io", @@ -242,9 +254,17 @@ var secretPred = predicate.Funcs{ return WatchedSecret.Has(e.Object.GetName()) }, UpdateFunc: func(e event.UpdateEvent) bool { + if e.ObjectNew.GetLabels()[constants.GlobalHubOwnerLabelKey] == + constants.GHOperatorOwnerLabelVal { + return true + } return WatchedSecret.Has(e.ObjectNew.GetName()) }, DeleteFunc: func(e event.DeleteEvent) bool { + if e.Object.GetLabels()[constants.GlobalHubOwnerLabelKey] == + constants.GHOperatorOwnerLabelVal { + return true + } return WatchedSecret.Has(e.Object.GetName()) }, } diff --git a/operator/pkg/controllers/inventory/inventory_reconciler.go b/operator/pkg/controllers/inventory/inventory_reconciler.go index f0fd3d985..08c1479ed 100644 --- a/operator/pkg/controllers/inventory/inventory_reconciler.go +++ b/operator/pkg/controllers/inventory/inventory_reconciler.go @@ -68,13 +68,15 @@ func (r *InventoryReconciler) IsResourceRemoved() bool { } func StartController(initOption config.ControllerOption) (config.ControllerInterface, error) { - log.Info("start inventory controller") if inventoryReconciler != nil { return inventoryReconciler, nil } + if !config.WithInventory(initOption.MulticlusterGlobalHub) { return nil, nil } + log.Info("start inventory controller") + if config.GetTransporterConn() == nil { return nil, nil } @@ -100,6 +102,12 @@ func (r *InventoryReconciler) SetupWithManager(mgr ctrl.Manager) error { builder.WithPredicates(config.MGHPred)). Watches(&appsv1.Deployment{}, &handler.EnqueueRequestForObject{}, builder.WithPredicates(deploymentPred)). + Watches(&corev1.Secret{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)). + Watches(&corev1.Service{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)). + Watches(&corev1.ServiceAccount{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)). Complete(r) } diff --git a/operator/pkg/controllers/managedhub/managedhub_controller.go b/operator/pkg/controllers/managedhub/managedhub_controller.go index 85c6c63fc..40284d78a 100644 --- a/operator/pkg/controllers/managedhub/managedhub_controller.go +++ b/operator/pkg/controllers/managedhub/managedhub_controller.go @@ -55,10 +55,11 @@ func (r *ManagedHubController) IsResourceRemoved() bool { } func StartController(initOption config.ControllerOption) (config.ControllerInterface, error) { - log.Info("start managedhub controller") if managedHubController != nil { return managedHubController, nil } + log.Info("start managedhub controller") + if !config.IsACMResourceReady() { return nil, nil } diff --git a/operator/pkg/controllers/manager/manager_reconciler.go b/operator/pkg/controllers/manager/manager_reconciler.go index 631c3a818..3f9a57d01 100644 --- a/operator/pkg/controllers/manager/manager_reconciler.go +++ b/operator/pkg/controllers/manager/manager_reconciler.go @@ -9,9 +9,11 @@ import ( "strconv" "time" + routev1 "github.com/openshift/api/route/v1" promv1 "github.com/prometheus-operator/prometheus-operator/pkg/apis/monitoring/v1" appsv1 "k8s.io/api/apps/v1" corev1 "k8s.io/api/core/v1" + rbacv1 "k8s.io/api/rbac/v1" "k8s.io/apimachinery/pkg/api/equality" "k8s.io/apimachinery/pkg/api/errors" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" @@ -19,6 +21,7 @@ import ( "k8s.io/client-go/discovery/cached/memory" "k8s.io/client-go/kubernetes" "k8s.io/client-go/restmapper" + "open-cluster-management.io/api/addon/v1alpha1" ctrl "sigs.k8s.io/controller-runtime" "sigs.k8s.io/controller-runtime/pkg/builder" "sigs.k8s.io/controller-runtime/pkg/client" @@ -85,11 +88,11 @@ var ( ) func StartController(initOption config.ControllerOption) (config.ControllerInterface, error) { - log.Info("start manager controller") - if managerController != nil { return managerController, nil } + log.Info("start manager controller") + if config.GetTransporterConn() == nil { return nil, nil } @@ -120,6 +123,22 @@ func (r *ManagerReconciler) SetupWithManager(mgr ctrl.Manager) error { builder.WithPredicates(config.MGHPred)). Watches(&appsv1.Deployment{}, &handler.EnqueueRequestForObject{}, builder.WithPredicates(deploymentPred)). + Watches(&v1alpha1.ClusterManagementAddOn{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)). + Watches(&corev1.Service{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)). + Watches(&corev1.ServiceAccount{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)). + Watches(&rbacv1.ClusterRole{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)). + Watches(&rbacv1.ClusterRoleBinding{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)). + Watches(&rbacv1.Role{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)). + Watches(&rbacv1.RoleBinding{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)). + Watches(&routev1.Route{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)). Complete(r) } diff --git a/operator/pkg/controllers/storage/storage_reconciler.go b/operator/pkg/controllers/storage/storage_reconciler.go index 7ade3404e..11f5f2e66 100644 --- a/operator/pkg/controllers/storage/storage_reconciler.go +++ b/operator/pkg/controllers/storage/storage_reconciler.go @@ -12,6 +12,7 @@ import ( "time" "github.com/jackc/pgx/v4" + promv1 "github.com/prometheus-operator/prometheus-operator/pkg/apis/monitoring/v1" appsv1 "k8s.io/api/apps/v1" corev1 "k8s.io/api/core/v1" "k8s.io/apimachinery/pkg/api/errors" @@ -85,11 +86,11 @@ func (r *StorageReconciler) IsResourceRemoved() bool { } func StartController(initOption config.ControllerOption) (config.ControllerInterface, error) { - log.Info("start storage controller") - if storageReconciler != nil { return storageReconciler, nil } + log.Info("start storage controller") + storageReconciler = NewStorageReconciler(initOption.Manager, initOption.OperatorConfig.GlobalResourceEnabled) err := storageReconciler.SetupWithManager(initOption.Manager) @@ -120,6 +121,12 @@ func (r *StorageReconciler) SetupWithManager(mgr ctrl.Manager) error { &handler.EnqueueRequestForObject{}, builder.WithPredicates(configmapPred)). Watches(&appsv1.StatefulSet{}, &handler.EnqueueRequestForObject{}, builder.WithPredicates(statefulSetPred)). + Watches(&corev1.ServiceAccount{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)). + Watches(&promv1.PrometheusRule{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)). + Watches(&promv1.ServiceMonitor{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)). Complete(r) } @@ -143,9 +150,17 @@ var configmapPred = predicate.Funcs{ return WatchedConfigMap.Has(e.Object.GetName()) }, UpdateFunc: func(e event.UpdateEvent) bool { + if e.ObjectNew.GetLabels()[constants.GlobalHubOwnerLabelKey] == + constants.GHOperatorOwnerLabelVal { + return true + } return WatchedConfigMap.Has(e.ObjectNew.GetName()) }, DeleteFunc: func(e event.DeleteEvent) bool { + if e.Object.GetLabels()[constants.GlobalHubOwnerLabelKey] == + constants.GHOperatorOwnerLabelVal { + return true + } return WatchedConfigMap.Has(e.Object.GetName()) }, } @@ -155,9 +170,17 @@ var secretPred = predicate.Funcs{ return WatchedSecret.Has(e.Object.GetName()) }, UpdateFunc: func(e event.UpdateEvent) bool { + if e.ObjectNew.GetLabels()[constants.GlobalHubOwnerLabelKey] == + constants.GHOperatorOwnerLabelVal { + return true + } return WatchedSecret.Has(e.ObjectNew.GetName()) }, DeleteFunc: func(e event.DeleteEvent) bool { + if e.Object.GetLabels()[constants.GlobalHubOwnerLabelKey] == + constants.GHOperatorOwnerLabelVal { + return true + } return WatchedSecret.Has(e.Object.GetName()) }, } diff --git a/operator/pkg/controllers/transporter/protocol/strimzi_kafka_controller.go b/operator/pkg/controllers/transporter/protocol/strimzi_kafka_controller.go index 1030a0059..e69af1afd 100644 --- a/operator/pkg/controllers/transporter/protocol/strimzi_kafka_controller.go +++ b/operator/pkg/controllers/transporter/protocol/strimzi_kafka_controller.go @@ -148,7 +148,7 @@ var kafkaPred = predicate.Funcs{ } func StartKafkaController(ctx context.Context, mgr ctrl.Manager, transporter transport.Transporter) error { - log.Info("start kafka controller") + log.Debug("start kafka controller") if startedKafkaController { return nil } diff --git a/operator/pkg/controllers/transporter/transport_reconciler.go b/operator/pkg/controllers/transporter/transport_reconciler.go index f4019573a..2a25b50a5 100644 --- a/operator/pkg/controllers/transporter/transport_reconciler.go +++ b/operator/pkg/controllers/transporter/transport_reconciler.go @@ -51,10 +51,11 @@ func (c *TransportReconciler) IsResourceRemoved() bool { } func StartController(controllerOption config.ControllerOption) (config.ControllerInterface, error) { - log.Info("start transport controller") if transportReconciler != nil { return transportReconciler, nil } + log.Info("start transport controller") + transportReconciler = NewTransportReconciler(controllerOption.Manager) err := transportReconciler.SetupWithManager(controllerOption.Manager) if err != nil { diff --git a/operator/pkg/controllers/webhook/webhook_controller.go b/operator/pkg/controllers/webhook/webhook_controller.go index bad59a531..00bfd3987 100644 --- a/operator/pkg/controllers/webhook/webhook_controller.go +++ b/operator/pkg/controllers/webhook/webhook_controller.go @@ -12,15 +12,17 @@ import ( "k8s.io/client-go/discovery" "k8s.io/client-go/discovery/cached/memory" "k8s.io/client-go/restmapper" + addonv1alpha1 "open-cluster-management.io/api/addon/v1alpha1" + clusterv1beta1 "open-cluster-management.io/api/cluster/v1beta1" + clusterv1beta2 "open-cluster-management.io/api/cluster/v1beta2" ctrl "sigs.k8s.io/controller-runtime" + "sigs.k8s.io/controller-runtime/pkg/builder" "sigs.k8s.io/controller-runtime/pkg/client" - "sigs.k8s.io/controller-runtime/pkg/controller" "sigs.k8s.io/controller-runtime/pkg/event" "sigs.k8s.io/controller-runtime/pkg/handler" "sigs.k8s.io/controller-runtime/pkg/predicate" - "sigs.k8s.io/controller-runtime/pkg/source" - globalhubv1alpha4 "github.com/stolostron/multicluster-global-hub/operator/api/operator/v1alpha4" + "github.com/stolostron/multicluster-global-hub/operator/api/operator/v1alpha4" "github.com/stolostron/multicluster-global-hub/operator/pkg/config" "github.com/stolostron/multicluster-global-hub/operator/pkg/deployer" "github.com/stolostron/multicluster-global-hub/operator/pkg/renderer" @@ -59,10 +61,11 @@ func NewWebhookReconciler(mgr ctrl.Manager, } func StartController(opts config.ControllerOption) (config.ControllerInterface, error) { - log.Info("start webhook controller") if webhookReconciler != nil { return webhookReconciler, nil } + log.Info("start webhook controller") + webhookReconciler = &WebhookReconciler{ c: opts.Manager.GetClient(), } @@ -131,29 +134,33 @@ type WebhookVariables struct { // SetupWithManager sets up the controller with the Manager. func (r *WebhookReconciler) SetupWithManager(mgr ctrl.Manager) error { - c, err := controller.New("webhook-controller", mgr, controller.Options{ - Reconciler: r, - }) - if err != nil { - return err - } - return c.Watch(source.Kind(mgr.GetCache(), &globalhubv1alpha4.MulticlusterGlobalHub{}, - &handler.TypedEnqueueRequestForObject[*globalhubv1alpha4.MulticlusterGlobalHub]{}, - predicate.TypedFuncs[*globalhubv1alpha4.MulticlusterGlobalHub]{ - CreateFunc: func(e event.TypedCreateEvent[*globalhubv1alpha4.MulticlusterGlobalHub]) bool { - return true - }, - UpdateFunc: func(e event.TypedUpdateEvent[*globalhubv1alpha4.MulticlusterGlobalHub]) bool { - if e.ObjectOld.GetGeneration() != e.ObjectNew.GetGeneration() { - return true - } - return !reflect.DeepEqual(e.ObjectOld.GetAnnotations(), e.ObjectNew.GetAnnotations()) - }, - DeleteFunc: func(e event.TypedDeleteEvent[*globalhubv1alpha4.MulticlusterGlobalHub]) bool { - return false - }, - }, - )) + return ctrl.NewControllerManagedBy(mgr).Named("webhook-controller"). + For(&v1alpha4.MulticlusterGlobalHub{}, + builder.WithPredicates(mghPred)). + Watches(&addonv1alpha1.AddOnDeploymentConfig{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)). + Watches(&clusterv1beta2.ManagedClusterSetBinding{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)). + Watches(&admissionregistrationv1.MutatingWebhookConfiguration{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)). + Watches(&clusterv1beta1.Placement{}, + &handler.EnqueueRequestForObject{}, builder.WithPredicates(config.GeneralPredicate)). + Complete(r) +} + +var mghPred = predicate.Funcs{ + CreateFunc: func(e event.CreateEvent) bool { + return true + }, + UpdateFunc: func(e event.UpdateEvent) bool { + if e.ObjectOld.GetGeneration() != e.ObjectNew.GetGeneration() { + return true + } + return !reflect.DeepEqual(e.ObjectOld.GetAnnotations(), e.ObjectNew.GetAnnotations()) + }, + DeleteFunc: func(e event.DeleteEvent) bool { + return true + }, } func (r *WebhookReconciler) pruneWebhookResources(ctx context.Context) error {