From 603f0ed0f00a16e8116d7c1723cb23b88974a0f0 Mon Sep 17 00:00:00 2001 From: odubajDT Date: Wed, 24 May 2023 11:52:08 +0200 Subject: [PATCH] chore(operator): use List() when fetching KeptnWorkloadInstances for KeptnAppVersion Signed-off-by: odubajDT --- .../controllers/common/fake/fakeclient.go | 6 +-- .../keptnappversion/controller_test.go | 9 ++++- .../reconcile_workloadsstate.go | 39 ++++++++++++------- .../keptnworkloadinstance/controller.go | 6 +++ 4 files changed, 41 insertions(+), 19 deletions(-) diff --git a/operator/controllers/common/fake/fakeclient.go b/operator/controllers/common/fake/fakeclient.go index dd4dc356a1..0039bd514b 100644 --- a/operator/controllers/common/fake/fakeclient.go +++ b/operator/controllers/common/fake/fakeclient.go @@ -15,16 +15,14 @@ import ( // NewClient returns a new controller-runtime fake Client configured with the Operator's scheme, and initialized with objs. func NewClient(objs ...client.Object) client.Client { - setupSchemes() + SetupSchemes() return fake.NewClientBuilder().WithScheme(scheme.Scheme).WithObjects(objs...).Build() } -func setupSchemes() { +func SetupSchemes() { utilruntime.Must(clientgoscheme.AddToScheme(scheme.Scheme)) utilruntime.Must(corev1.AddToScheme(scheme.Scheme)) utilruntime.Must(apiv1.AddToScheme(scheme.Scheme)) - // utilruntime.Must(lfcv1alpha1.AddToScheme(scheme.Scheme)) - // utilruntime.Must(lfcv1alpha2.AddToScheme(scheme.Scheme)) utilruntime.Must(lfcv1alpha3.AddToScheme(scheme.Scheme)) utilruntime.Must(optionsv1alpha1.AddToScheme(scheme.Scheme)) utilruntime.Must(metricsapi.AddToScheme(scheme.Scheme)) diff --git a/operator/controllers/lifecycle/keptnappversion/controller_test.go b/operator/controllers/lifecycle/keptnappversion/controller_test.go index 2b022a25f6..1186dfc5c6 100644 --- a/operator/controllers/lifecycle/keptnappversion/controller_test.go +++ b/operator/controllers/lifecycle/keptnappversion/controller_test.go @@ -19,6 +19,7 @@ import ( "k8s.io/client-go/tools/record" ctrl "sigs.k8s.io/controller-runtime" "sigs.k8s.io/controller-runtime/pkg/client" + k8sfake "sigs.k8s.io/controller-runtime/pkg/client/fake" "sigs.k8s.io/controller-runtime/pkg/log/zap" ) @@ -185,7 +186,13 @@ func setupReconciler() (*KeptnAppVersionReconciler, chan string, *fake.ITracerMo UnbindSpanFunc: func(reconcileObject client.Object, phase string) error { return nil }, } - fakeClient := fake.NewClient() + workloadInstanceIndexer := func(obj client.Object) []string { + workloadInstance, _ := obj.(*lfcv1alpha3.KeptnWorkloadInstance) + return []string{workloadInstance.Spec.AppName} + } + + fake.SetupSchemes() + fakeClient := k8sfake.NewClientBuilder().WithScheme(scheme.Scheme).WithObjects().WithIndex(&lfcv1alpha3.KeptnWorkloadInstance{}, "spec.app", workloadInstanceIndexer).Build() recorder := record.NewFakeRecorder(100) r := &KeptnAppVersionReconciler{ diff --git a/operator/controllers/lifecycle/keptnappversion/reconcile_workloadsstate.go b/operator/controllers/lifecycle/keptnappversion/reconcile_workloadsstate.go index 1ca2a9ca3f..a5253018ba 100644 --- a/operator/controllers/lifecycle/keptnappversion/reconcile_workloadsstate.go +++ b/operator/controllers/lifecycle/keptnappversion/reconcile_workloadsstate.go @@ -6,8 +6,8 @@ import ( klcv1alpha3 "github.com/keptn/lifecycle-toolkit/operator/apis/lifecycle/v1alpha3" apicommon "github.com/keptn/lifecycle-toolkit/operator/apis/lifecycle/v1alpha3/common" controllercommon "github.com/keptn/lifecycle-toolkit/operator/controllers/common" - "k8s.io/apimachinery/pkg/api/errors" "k8s.io/apimachinery/pkg/types" + "sigs.k8s.io/controller-runtime/pkg/client" ) func (r *KeptnAppVersionReconciler) reconcileWorkloads(ctx context.Context, appVersion *klcv1alpha3.KeptnAppVersion) (apicommon.KeptnState, error) { @@ -21,17 +21,26 @@ func (r *KeptnAppVersionReconciler) reconcileWorkloads(ctx context.Context, appV } var newStatus []klcv1alpha3.WorkloadStatus + workloadInstanceList, err := r.getWorkloadInstanceList(ctx, appVersion.Namespace, appVersion.Name) + if err != nil { + r.Log.Error(err, "Could not get workloads") + return apicommon.StatePending, err + } + + if len(workloadInstanceList.Items) == 0 { + r.Log.Info("No WorkloadInstances found") + controllercommon.RecordEvent(r.Recorder, phase, "Warning", appVersion, "NotFound", "workloadInstances not found", appVersion.GetVersion()) + return apicommon.StatePending, nil + } + for _, w := range appVersion.Spec.Workloads { r.Log.Info("Reconciling workload " + w.Name) - workload, err := r.getWorkloadInstance(ctx, getWorkloadInstanceName(appVersion.Namespace, appVersion.Spec.AppName, w.Name, w.Version)) - if err != nil && errors.IsNotFound(err) { - controllercommon.RecordEvent(r.Recorder, phase, "Warning", appVersion, "NotFound", "workloadInstance not found", appVersion.GetVersion()) - workload.Status.Status = apicommon.StatePending - } else if err != nil { - r.Log.Error(err, "Could not get workload") - workload.Status.Status = apicommon.StateUnknown + workloadStatus := apicommon.StatePending + for _, i := range workloadInstanceList.Items { + if w.Name == i.Name && w.Version == i.Spec.Version { + workloadStatus = i.Status.Status + } } - workloadStatus := workload.Status.Status newStatus = append(newStatus, klcv1alpha3.WorkloadStatus{ Workload: w, @@ -48,14 +57,16 @@ func (r *KeptnAppVersionReconciler) reconcileWorkloads(ctx context.Context, appV r.Log.Info("Workload status", "status", appVersion.Status.WorkloadStatus) // Write Status Field - err := r.Client.Status().Update(ctx, appVersion) + err = r.Client.Status().Update(ctx, appVersion) return overallState, err } -func (r *KeptnAppVersionReconciler) getWorkloadInstance(ctx context.Context, workload types.NamespacedName) (klcv1alpha3.KeptnWorkloadInstance, error) { - workloadInstance := &klcv1alpha3.KeptnWorkloadInstance{} - err := r.Get(ctx, workload, workloadInstance) - return *workloadInstance, err +func (r *KeptnAppVersionReconciler) getWorkloadInstanceList(ctx context.Context, namespace string, appName string) (*klcv1alpha3.KeptnWorkloadInstanceList, error) { + workloadInstanceList := &klcv1alpha3.KeptnWorkloadInstanceList{} + err := r.Client.List(ctx, workloadInstanceList, client.InNamespace(namespace), client.MatchingFields{ + "spec.app": appName, + }) + return workloadInstanceList, err } func getWorkloadInstanceName(namespace string, appName string, workloadName string, version string) types.NamespacedName { diff --git a/operator/controllers/lifecycle/keptnworkloadinstance/controller.go b/operator/controllers/lifecycle/keptnworkloadinstance/controller.go index 72dfc0513d..4548caf6fa 100644 --- a/operator/controllers/lifecycle/keptnworkloadinstance/controller.go +++ b/operator/controllers/lifecycle/keptnworkloadinstance/controller.go @@ -212,6 +212,12 @@ func (r *KeptnWorkloadInstanceReconciler) finishKeptnWorkloadInstanceReconcile(c // SetupWithManager sets up the controller with the Manager. func (r *KeptnWorkloadInstanceReconciler) SetupWithManager(mgr ctrl.Manager) error { + if err := mgr.GetFieldIndexer().IndexField(context.Background(), &klcv1alpha3.KeptnWorkloadInstance{}, "spec.app", func(rawObj client.Object) []string { + workloadInstance := rawObj.(*klcv1alpha3.KeptnWorkloadInstance) + return []string{workloadInstance.Spec.AppName} + }); err != nil { + return err + } return ctrl.NewControllerManagedBy(mgr). // predicate disabling the auto reconciliation after updating the object status For(&klcv1alpha3.KeptnWorkloadInstance{}, builder.WithPredicates(predicate.GenerationChangedPredicate{})).