diff --git a/internal/controller/aggregates_controller_test.go b/internal/controller/aggregates_controller_test.go index 3996fe0..3c022da 100644 --- a/internal/controller/aggregates_controller_test.go +++ b/internal/controller/aggregates_controller_test.go @@ -18,7 +18,6 @@ limitations under the License. package controller import ( - "context" "fmt" "net/http" @@ -105,7 +104,7 @@ var _ = Describe("AggregatesController", func() { ) // Setup and teardown - BeforeEach(func(ctx context.Context) { + BeforeEach(func(ctx SpecContext) { By("Setting up the OpenStack http mock server") fakeServer = testhelper.SetupHTTP() DeferCleanup(fakeServer.Teardown) @@ -135,19 +134,19 @@ var _ = Describe("AggregatesController", func() { computeClient: client.ServiceClient(fakeServer), } - DeferCleanup(func(ctx context.Context) { + DeferCleanup(func(ctx SpecContext) { Expect(tc.Client.Delete(ctx, hypervisor)).To(Succeed()) }) }) - JustBeforeEach(func(ctx context.Context) { + JustBeforeEach(func(ctx SpecContext) { _, err := tc.Reconcile(ctx, ctrl.Request{NamespacedName: hypervisorName}) Expect(err).NotTo(HaveOccurred()) }) // Tests Context("Adding new Aggregate", func() { - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { By("Setting a missing aggregate") hypervisor := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, hypervisorName, hypervisor)).To(Succeed()) @@ -189,7 +188,7 @@ var _ = Describe("AggregatesController", func() { }) }) - It("should update Aggregates and set status condition as Aggregates differ", func() { + It("should update Aggregates and set status condition as Aggregates differ", func(ctx SpecContext) { updated := &kvmv1.Hypervisor{} Expect(tc.Client.Get(ctx, hypervisorName, updated)).To(Succeed()) Expect(updated.Status.Aggregates).To(ContainElements("test-aggregate1")) @@ -198,7 +197,7 @@ var _ = Describe("AggregatesController", func() { }) Context("Removing Aggregate", func() { - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { hypervisor := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, hypervisorName, hypervisor)).To(Succeed()) // update status to have existing aggregate @@ -233,7 +232,7 @@ var _ = Describe("AggregatesController", func() { fakeServer.Mux.HandleFunc("POST /os-aggregates/99/action", expectRemoveHostFromAggregate) }) - It("should update Aggregates and set status condition when Aggregates differ", func() { + It("should update Aggregates and set status condition when Aggregates differ", func(ctx SpecContext) { updated := &kvmv1.Hypervisor{} Expect(tc.Client.Get(ctx, hypervisorName, updated)).To(Succeed()) Expect(updated.Status.Aggregates).To(BeEmpty()) @@ -242,7 +241,7 @@ var _ = Describe("AggregatesController", func() { }) Context("before onboarding", func() { - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { hypervisor := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, hypervisorName, hypervisor)).To(Succeed()) // Remove the onboarding condition @@ -250,7 +249,7 @@ var _ = Describe("AggregatesController", func() { Expect(k8sClient.Status().Update(ctx, hypervisor)).To(Succeed()) }) - It("should neither update Aggregates and nor set status condition", func() { + It("should neither update Aggregates and nor set status condition", func(ctx SpecContext) { updated := &kvmv1.Hypervisor{} Expect(tc.Client.Get(ctx, hypervisorName, updated)).To(Succeed()) Expect(updated.Status.Aggregates).To(BeEmpty()) @@ -259,7 +258,7 @@ var _ = Describe("AggregatesController", func() { }) Context("when terminating", func() { - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { hypervisor := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, hypervisorName, hypervisor)).To(Succeed()) // Remove the onboarding condition @@ -272,7 +271,7 @@ var _ = Describe("AggregatesController", func() { Expect(k8sClient.Status().Update(ctx, hypervisor)).To(Succeed()) }) - It("should neither update Aggregates and nor set status condition", func() { + It("should neither update Aggregates and nor set status condition", func(ctx SpecContext) { updated := &kvmv1.Hypervisor{} Expect(tc.Client.Get(ctx, hypervisorName, updated)).To(Succeed()) Expect(updated.Status.Aggregates).To(BeEmpty()) diff --git a/internal/controller/decomission_controller.go b/internal/controller/decomission_controller.go index b6367ac..488fb9c 100644 --- a/internal/controller/decomission_controller.go +++ b/internal/controller/decomission_controller.go @@ -28,7 +28,6 @@ import ( "github.com/gophercloud/gophercloud/v2/openstack/compute/v2/aggregates" "github.com/gophercloud/gophercloud/v2/openstack/compute/v2/services" "github.com/gophercloud/gophercloud/v2/openstack/placement/v1/resourceproviders" - corev1 "k8s.io/api/core/v1" "k8s.io/apimachinery/pkg/api/meta" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/apimachinery/pkg/runtime" @@ -44,7 +43,7 @@ import ( const ( decommissionFinalizerName = "cobaltcore.cloud.sap/decommission-hypervisor" - DecommissionControllerName = "nodeDecommission" + DecommissionControllerName = "decommission" ) type NodeDecommissionReconciler struct { @@ -57,8 +56,6 @@ type NodeDecommissionReconciler struct { // The counter-side in gardener is here: // https://github.com/gardener/machine-controller-manager/blob/rel-v0.56/pkg/util/provider/machinecontroller/machine.go#L646 -// +kubebuilder:rbac:groups="",resources=nodes,verbs=get;list;watch;patch;update -// +kubebuilder:rbac:groups="",resources=nodes/finalizers,verbs=update // +kubebuilder:rbac:groups=kvm.cloud.sap,resources=hypervisors,verbs=get;list;watch // +kubebuilder:rbac:groups=kvm.cloud.sap,resources=hypervisors/status,verbs=get;list;watch;update;patch func (r *NodeDecommissionReconciler) Reconcile(ctx context.Context, req ctrl.Request) (ctrl.Result, error) { @@ -66,11 +63,6 @@ func (r *NodeDecommissionReconciler) Reconcile(ctx context.Context, req ctrl.Req log := logger.FromContext(ctx).WithName(req.Name).WithValues("hostname", hostname) ctx = logger.IntoContext(ctx, log) - node := &corev1.Node{} - if err := r.Get(ctx, req.NamespacedName, node); err != nil { - return ctrl.Result{}, k8sclient.IgnoreNotFound(err) - } - // Fetch HV to check if lifecycle management is enabled hv := &kvmv1.Hypervisor{} if err := r.Get(ctx, k8sclient.ObjectKey{Name: hostname}, hv); err != nil { @@ -79,14 +71,14 @@ func (r *NodeDecommissionReconciler) Reconcile(ctx context.Context, req ctrl.Req } if !hv.Spec.LifecycleEnabled { // Get out of the way - return r.removeFinalizer(ctx, node) + return r.removeFinalizer(ctx, hv) } - if !controllerutil.ContainsFinalizer(node, decommissionFinalizerName) { + if !controllerutil.ContainsFinalizer(hv, decommissionFinalizerName) { return ctrl.Result{}, retry.RetryOnConflict(retry.DefaultRetry, func() error { - patch := k8sclient.MergeFrom(node.DeepCopy()) - controllerutil.AddFinalizer(node, decommissionFinalizerName) - if err := r.Patch(ctx, node, patch); err != nil { + patch := k8sclient.MergeFrom(hv.DeepCopy()) + controllerutil.AddFinalizer(hv, decommissionFinalizerName) + if err := r.Patch(ctx, hv, patch); err != nil { return fmt.Errorf("failed to add finalizer due to %w", err) } log.Info("Added finalizer") @@ -95,16 +87,16 @@ func (r *NodeDecommissionReconciler) Reconcile(ctx context.Context, req ctrl.Req } // Not yet deleting hv, nothing more to do - if node.DeletionTimestamp.IsZero() { + if hv.DeletionTimestamp.IsZero() { return ctrl.Result{}, nil } // Someone is just deleting the hv, without going through termination // See: https://github.com/gardener/machine-controller-manager/blob/rel-v0.56/pkg/util/provider/machinecontroller/machine.go#L658-L659 - if !IsNodeConditionTrue(node.Status.Conditions, "Terminating") { + if !meta.IsStatusConditionTrue(hv.Status.Conditions, "Terminating") { log.Info("removing finalizer since not terminating") // So we just get out of the way for now - return r.removeFinalizer(ctx, node) + return r.removeFinalizer(ctx, hv) } if meta.IsStatusConditionTrue(hv.Status.Conditions, kvmv1.ConditionTypeReady) { @@ -116,7 +108,7 @@ func (r *NodeDecommissionReconciler) Reconcile(ctx context.Context, req ctrl.Req hypervisor, err := openstack.GetHypervisorByName(ctx, r.computeClient, hostname, true) if errors.Is(err, openstack.ErrNoHypervisor) { // We are (hopefully) done - return r.removeFinalizer(ctx, node) + return r.removeFinalizer(ctx, hv) } // TODO: remove since RunningVMs is only available until micro-version 2.87, and also is updated asynchronously @@ -141,7 +133,7 @@ func (r *NodeDecommissionReconciler) Reconcile(ctx context.Context, req ctrl.Req return r.setDecommissioningCondition(ctx, hv, fmt.Sprintf("cannot list aggregates due to %v", err)) } - host := node.Name + host := hv.Name for name, aggregate := range aggs { if slices.Contains(aggregate.Hosts, host) { opts := aggregates.RemoveHostOpts{Host: host} @@ -168,17 +160,17 @@ func (r *NodeDecommissionReconciler) Reconcile(ctx context.Context, req ctrl.Req return r.setDecommissioningCondition(ctx, hv, fmt.Sprintf("cannot clean up resource provider: %v", err)) } - return r.removeFinalizer(ctx, node) + return r.removeFinalizer(ctx, hv) } -func (r *NodeDecommissionReconciler) removeFinalizer(ctx context.Context, node *corev1.Node) (ctrl.Result, error) { - if !controllerutil.ContainsFinalizer(node, decommissionFinalizerName) { +func (r *NodeDecommissionReconciler) removeFinalizer(ctx context.Context, hypervisor *kvmv1.Hypervisor) (ctrl.Result, error) { + if !controllerutil.ContainsFinalizer(hypervisor, decommissionFinalizerName) { return ctrl.Result{}, nil } - nodeBase := node.DeepCopy() - controllerutil.RemoveFinalizer(node, decommissionFinalizerName) - err := r.Patch(ctx, node, k8sclient.MergeFromWithOptions(nodeBase, + base := hypervisor.DeepCopy() + controllerutil.RemoveFinalizer(hypervisor, decommissionFinalizerName) + err := r.Patch(ctx, hypervisor, k8sclient.MergeFromWithOptions(base, k8sclient.MergeFromWithOptimisticLock{}), k8sclient.FieldOwner(DecommissionControllerName)) return ctrl.Result{}, err } @@ -195,7 +187,7 @@ func (r *NodeDecommissionReconciler) setDecommissioningCondition(ctx context.Con k8sclient.MergeFromWithOptimisticLock{}), k8sclient.FieldOwner(DecommissionControllerName)); err != nil { return ctrl.Result{}, fmt.Errorf("cannot update hypervisor status due to %w", err) } - return ctrl.Result{RequeueAfter: shortRetryTime}, nil + return ctrl.Result{}, nil } // SetupWithManager sets up the controller with the Manager. @@ -217,6 +209,6 @@ func (r *NodeDecommissionReconciler) SetupWithManager(mgr ctrl.Manager) error { return ctrl.NewControllerManagedBy(mgr). Named(DecommissionControllerName). - For(&corev1.Node{}). + For(&kvmv1.Hypervisor{}). Complete(r) } diff --git a/internal/controller/decomission_controller_test.go b/internal/controller/decomission_controller_test.go index 3eeb4a2..0166225 100644 --- a/internal/controller/decomission_controller_test.go +++ b/internal/controller/decomission_controller_test.go @@ -18,61 +18,82 @@ limitations under the License. package controller import ( - "context" + "fmt" + "net/http" + "os" + "github.com/gophercloud/gophercloud/v2/testhelper" + "github.com/gophercloud/gophercloud/v2/testhelper/client" . "github.com/onsi/ginkgo/v2" . "github.com/onsi/gomega" - corev1 "k8s.io/api/core/v1" + "k8s.io/apimachinery/pkg/api/meta" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/apimachinery/pkg/types" ctrl "sigs.k8s.io/controller-runtime" - "sigs.k8s.io/controller-runtime/pkg/client" + k8sclient "sigs.k8s.io/controller-runtime/pkg/client" kvmv1 "github.com/cobaltcore-dev/openstack-hypervisor-operator/api/v1" ) +const ( + EOF = "EOF" + serviceId = "service-1234" + hypervisorName = "node-test" + namespaceName = "namespace-test" + AggregateListWithHv = ` +{ + "aggregates": [ + { + "name": "test-aggregate2", + "availability_zone": "", + "deleted": false, + "id": 100001, + "hosts": ["note-test"] + } + ] +} +` + AggregateRemoveHostBody = ` +{ + "aggregate": { + "name": "test-aggregate2", + "availability_zone": "", + "deleted": false, + "id": 100001 + } +}` +) + var _ = Describe("Decommission Controller", func() { - const ( - namespaceName = "namespace-test" - ) var ( r *NodeDecommissionReconciler - nodeName = types.NamespacedName{Name: "node-test"} + name = types.NamespacedName{Name: hypervisorName} reconcileReq = ctrl.Request{ - NamespacedName: nodeName, + NamespacedName: name, } + fakeServer testhelper.FakeServer ) BeforeEach(func(ctx SpecContext) { - r = &NodeDecommissionReconciler{ - Client: k8sClient, - Scheme: k8sClient.Scheme(), - } + fakeServer = testhelper.SetupHTTP() + os.Setenv("KVM_HA_SERVICE_URL", fakeServer.Endpoint()+"instance-ha") - By("creating the namespace for the reconciler") - ns := &corev1.Namespace{ObjectMeta: metav1.ObjectMeta{Name: namespaceName}} - Expect(client.IgnoreAlreadyExists(k8sClient.Create(ctx, ns))).To(Succeed()) - - DeferCleanup(func(ctx SpecContext) { - Expect(k8sClient.Delete(ctx, ns)).To(Succeed()) + DeferCleanup(func() { + os.Unsetenv("KVM_HA_SERVICE_URL") + fakeServer.Teardown() }) - By("creating the core resource for the Kind Node") - node := &corev1.Node{ - ObjectMeta: metav1.ObjectMeta{ - Name: nodeName.Name, - Labels: map[string]string{labelEvictionRequired: "true"}, - }, + r = &NodeDecommissionReconciler{ + Client: k8sClient, + Scheme: k8sClient.Scheme(), + computeClient: client.ServiceClient(fakeServer), + placementClient: client.ServiceClient(fakeServer), } - Expect(k8sClient.Create(ctx, node)).To(Succeed()) - DeferCleanup(func(ctx SpecContext) { - Expect(client.IgnoreNotFound(k8sClient.Delete(ctx, node))).To(Succeed()) - }) - By("Create the hypervisor resource with lifecycle enabled") + By("Create the hypervisor to be reconciled with lifecycle enabled") hypervisor := &kvmv1.Hypervisor{ ObjectMeta: metav1.ObjectMeta{ - Name: nodeName.Name, + Name: name.Name, }, Spec: kvmv1.HypervisorSpec{ LifecycleEnabled: true, @@ -80,36 +101,152 @@ var _ = Describe("Decommission Controller", func() { } Expect(k8sClient.Create(ctx, hypervisor)).To(Succeed()) DeferCleanup(func(ctx SpecContext) { - Expect(k8sClient.Delete(ctx, hypervisor)).To(Succeed()) + hypervisor := &kvmv1.Hypervisor{} + Expect(k8sclient.IgnoreNotFound(k8sClient.Get(ctx, name, hypervisor))).To(Succeed()) + if len(hypervisor.Finalizers) > 0 { + hypervisor.Finalizers = make([]string, 0) + Expect(k8sClient.Update(ctx, hypervisor)).To(Succeed()) + } + if hypervisor.Name != "" { + Expect(k8sclient.IgnoreNotFound(k8sClient.Delete(ctx, hypervisor))).To(Succeed()) + } }) }) - AfterEach(func(ctx context.Context) { - node := &corev1.Node{ObjectMeta: metav1.ObjectMeta{Name: nodeName.Name}} - By("Cleanup the specific node and hypervisor resource") - Expect(client.IgnoreNotFound(k8sClient.Delete(ctx, node))).To(Succeed()) - - // Due to the decommissioning finalizer, we need to reconcile once more to delete the node completely - req := ctrl.Request{ - NamespacedName: types.NamespacedName{Name: nodeName.Name}, - } - _, err := r.Reconcile(ctx, req) - Expect(err).NotTo(HaveOccurred()) + Context("When reconciling a hypervisor", func() { + It("should set the finalizer", func(ctx SpecContext) { + By("reconciling the created resource") + _, err := r.Reconcile(ctx, reconcileReq) + Expect(err).NotTo(HaveOccurred()) + hypervisor := &kvmv1.Hypervisor{} - nodelist := &corev1.NodeList{} - Expect(k8sClient.List(ctx, nodelist)).To(Succeed()) - Expect(nodelist.Items).To(BeEmpty()) + Expect(k8sClient.Get(ctx, name, hypervisor)).To(Succeed()) + Expect(hypervisor.Finalizers).To(ContainElement(decommissionFinalizerName)) + }) }) - Context("When reconciling a node", func() { - It("should set the finalizer", func(ctx context.Context) { - By("reconciling the created resource") + Context("When terminating a hypervisor", func() { + JustBeforeEach(func(ctx SpecContext) { + By("reconciling first reconciling the to add the finalizer") _, err := r.Reconcile(ctx, reconcileReq) Expect(err).NotTo(HaveOccurred()) - node := &corev1.Node{} + hypervisor := &kvmv1.Hypervisor{} + + Expect(k8sClient.Get(ctx, name, hypervisor)).To(Succeed()) + Expect(hypervisor.Finalizers).To(ContainElement(decommissionFinalizerName)) + + By("and then terminating then hypervisor") + meta.SetStatusCondition(&hypervisor.Status.Conditions, metav1.Condition{ + Type: "Terminating", + Status: metav1.ConditionTrue, + Reason: "dontcare", + Message: "dontcare", + }) + Expect(k8sClient.Status().Update(ctx, hypervisor)).To(Succeed()) + Expect(k8sClient.Delete(ctx, hypervisor)).To(Succeed()) + hypervisorList := &kvmv1.HypervisorList{} + Expect(k8sClient.List(ctx, hypervisorList)).To(Succeed()) + Expect(hypervisorList.Items).NotTo(BeEmpty()) + }) - Expect(k8sClient.Get(ctx, nodeName, node)).To(Succeed()) - Expect(node.Finalizers).To(ContainElement(decommissionFinalizerName)) + When("the hypervisor was set to ready", func() { + getHypervisorsCalled := 0 + BeforeEach(func(ctx SpecContext) { + hv := &kvmv1.Hypervisor{} + Expect(k8sClient.Get(ctx, name, hv)).To(Succeed()) + meta.SetStatusCondition(&hv.Status.Conditions, + metav1.Condition{ + Type: kvmv1.ConditionTypeReady, + Status: metav1.ConditionTrue, + Reason: "dontcare", + Message: "dontcare", + }, + ) + Expect(k8sClient.Status().Update(ctx, hv)).To(Succeed()) + + fakeServer.Mux.HandleFunc("GET /os-hypervisors/detail", func(w http.ResponseWriter, r *http.Request) { + w.Header().Add("Content-Type", "application/json") + w.WriteHeader(http.StatusOK) + getHypervisorsCalled++ + Expect(fmt.Fprintf(w, HypervisorWithServers, serviceId, "some reason", hypervisorName)).ToNot(BeNil()) + }) + + fakeServer.Mux.HandleFunc("GET /os-aggregates", func(w http.ResponseWriter, r *http.Request) { + w.Header().Add("Content-Type", "application/json") + w.WriteHeader(http.StatusOK) + + _, err := fmt.Fprint(w, AggregateListWithHv) + Expect(err).NotTo(HaveOccurred()) + }) + + fakeServer.Mux.HandleFunc("POST /os-aggregates/100001/action", func(w http.ResponseWriter, r *http.Request) { + // parse request + Expect(r.Header.Get("Content-Type")).To(Equal("application/json")) + expectedBody := `{"remove_host":{"host":"hv-test"}}` + body := make([]byte, r.ContentLength) + _, err := r.Body.Read(body) + Expect(err == nil || err.Error() == EOF).To(BeTrue()) + Expect(string(body)).To(MatchJSON(expectedBody)) + + // send response + w.Header().Add("Content-Type", "application/json") + w.WriteHeader(http.StatusOK) + + _, err = fmt.Fprint(w, AggregateRemoveHostBody) + Expect(err).NotTo(HaveOccurred()) + }) + + // c48f6247-abe4-4a24-824e-ea39e108874f comes from the HypervisorWithServers const + fakeServer.Mux.HandleFunc("GET /resource_providers/c48f6247-abe4-4a24-824e-ea39e108874f", func(w http.ResponseWriter, r *http.Request) { + w.Header().Add("Content-Type", "application/json") + w.WriteHeader(http.StatusOK) + + _, err := fmt.Fprint(w, `{"uuid": "rp-uuid", "name": "hv-test"}`) + Expect(err).NotTo(HaveOccurred()) + }) + + fakeServer.Mux.HandleFunc("GET /resource_providers/rp-uuid/allocations", func(w http.ResponseWriter, r *http.Request) { + w.Header().Add("Content-Type", "application/json") + w.WriteHeader(http.StatusOK) + + _, err := fmt.Fprint(w, `{"allocations": {}}}`) + Expect(err).NotTo(HaveOccurred()) + + }) + fakeServer.Mux.HandleFunc("DELETE /resource_providers/rp-uuid", func(w http.ResponseWriter, r *http.Request) { + w.WriteHeader(http.StatusAccepted) + }) + }) + + It("should set the hypervisor condition", func(ctx SpecContext) { + By("reconciling the created resource") + _, err := r.Reconcile(ctx, reconcileReq) + Expect(err).NotTo(HaveOccurred()) + hypervisor := &kvmv1.Hypervisor{} + Expect(k8sClient.Get(ctx, name, hypervisor)).To(Succeed()) + Expect(hypervisor.Status.Conditions).To(ContainElement( + SatisfyAll( + HaveField("Type", kvmv1.ConditionTypeReady), + HaveField("Status", metav1.ConditionFalse), + HaveField("Reason", "Decommissioning"), + ), + )) + }) + + It("should remove the finalizer", func(ctx SpecContext) { + By("reconciling the created resource") + for range 3 { + _, err := r.Reconcile(ctx, reconcileReq) + Expect(err).NotTo(HaveOccurred()) + } + Expect(getHypervisorsCalled).To(BeNumerically(">", 0)) + + hypervisor := &kvmv1.Hypervisor{} + err := k8sClient.Get(ctx, name, hypervisor) + Expect(err).To(HaveOccurred()) + Expect(k8sclient.IgnoreNotFound(err)).To(Succeed()) + }) }) + }) }) diff --git a/internal/controller/eviction_controller_test.go b/internal/controller/eviction_controller_test.go index d1cf3d7..0affc5e 100644 --- a/internal/controller/eviction_controller_test.go +++ b/internal/controller/eviction_controller_test.go @@ -18,7 +18,6 @@ limitations under the License. package controller import ( - "context" "fmt" "net/http" @@ -97,14 +96,12 @@ var _ = Describe("Eviction Controller", func() { fakeServer testhelper.FakeServer ) - ctx := context.Background() //nolint:govet - BeforeEach(func() { By("Setting up the OpenStack http mock server") fakeServer = testhelper.SetupHTTP() }) - AfterEach(func() { + AfterEach(func(ctx SpecContext) { resource := &kvmv1.Eviction{} err := k8sClient.Get(ctx, typeNamespacedName, resource) if err != nil { @@ -133,7 +130,7 @@ var _ = Describe("Eviction Controller", func() { Describe("API validation", func() { When("creating an eviction without hypervisor", func() { - It("it should fail creating the resource", func() { + It("it should fail creating the resource", func(ctx SpecContext) { resource := &kvmv1.Eviction{ ObjectMeta: metav1.ObjectMeta{ Name: resourceName, @@ -149,7 +146,7 @@ var _ = Describe("Eviction Controller", func() { }) When("creating an eviction without reason", func() { - It("it should fail creating the resource", func() { + It("it should fail creating the resource", func(ctx SpecContext) { resource := &kvmv1.Eviction{ ObjectMeta: metav1.ObjectMeta{ Name: resourceName, @@ -165,7 +162,7 @@ var _ = Describe("Eviction Controller", func() { }) When("creating an eviction with reason and hypervisor", func() { - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { By("creating the hypervisor resource") hypervisor := &kvmv1.Hypervisor{ ObjectMeta: metav1.ObjectMeta{ @@ -174,7 +171,7 @@ var _ = Describe("Eviction Controller", func() { } Expect(ctrlRuntimeClient.IgnoreAlreadyExists(k8sClient.Create(ctx, hypervisor))).To(Succeed()) }) - It("should successfully create the resource", func() { + It("should successfully create the resource", func(ctx SpecContext) { resource := &kvmv1.Eviction{ ObjectMeta: metav1.ObjectMeta{ Name: resourceName, @@ -193,7 +190,7 @@ var _ = Describe("Eviction Controller", func() { Describe("Reconciliation", func() { Describe("an eviction for 'test-hypervisor'", func() { - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { By("Creating the resource") resource := &kvmv1.Eviction{ ObjectMeta: metav1.ObjectMeta{ @@ -224,7 +221,7 @@ var _ = Describe("Eviction Controller", func() { }) }) - It("should fail reconciliation", func() { + It("should fail reconciliation", func(ctx SpecContext) { for range 3 { _, err := controllerReconciler.Reconcile(ctx, reconcileRequest) Expect(err).NotTo(HaveOccurred()) @@ -247,7 +244,7 @@ var _ = Describe("Eviction Controller", func() { }) When("enabled hypervisor has no servers", func() { - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { fakeServer.Mux.HandleFunc("GET /os-hypervisors/detail", func(w http.ResponseWriter, r *http.Request) { w.Header().Add("Content-Type", "application/json") w.WriteHeader(http.StatusOK) @@ -266,7 +263,7 @@ var _ = Describe("Eviction Controller", func() { } Expect(ctrlRuntimeClient.IgnoreAlreadyExists(k8sClient.Create(ctx, hypervisor))).To(Succeed()) }) - It("should succeed the reconciliation", func() { + It("should succeed the reconciliation", func(ctx SpecContext) { runningCond := &metav1.Condition{ Type: kvmv1.ConditionTypeEvicting, Status: metav1.ConditionTrue, @@ -344,7 +341,7 @@ var _ = Describe("Eviction Controller", func() { }) }) When("disabled hypervisor has no servers", func() { - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { fakeServer.Mux.HandleFunc("GET /os-hypervisors/detail", func(w http.ResponseWriter, r *http.Request) { w.Header().Add("Content-Type", "application/json") w.WriteHeader(http.StatusOK) @@ -362,7 +359,7 @@ var _ = Describe("Eviction Controller", func() { } Expect(ctrlRuntimeClient.IgnoreAlreadyExists(k8sClient.Create(ctx, hypervisor))).To(Succeed()) }) - It("should succeed the reconciliation", func() { + It("should succeed the reconciliation", func(ctx SpecContext) { for range 3 { _, err := controllerReconciler.Reconcile(ctx, reconcileRequest) Expect(err).NotTo(HaveOccurred()) diff --git a/internal/controller/gardener_node_lifecycle_controller_test.go b/internal/controller/gardener_node_lifecycle_controller_test.go index fdfafad..1af06de 100644 --- a/internal/controller/gardener_node_lifecycle_controller_test.go +++ b/internal/controller/gardener_node_lifecycle_controller_test.go @@ -31,7 +31,7 @@ var _ = Describe("Gardener Maintenance Controller", func() { const nodeName = "node-test" var controller *GardenerNodeLifecycleController - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { controller = &GardenerNodeLifecycleController{ Client: k8sClient, Scheme: k8sClient.Scheme(), @@ -49,16 +49,13 @@ var _ = Describe("Gardener Maintenance Controller", func() { }, } Expect(k8sClient.Create(ctx, resource)).To(Succeed()) - }) - - AfterEach(func() { - node := &corev1.Node{ObjectMeta: metav1.ObjectMeta{Name: nodeName}} - By("Cleanup the specific node") - Expect(client.IgnoreNotFound(k8sClient.Delete(ctx, node))).To(Succeed()) + DeferCleanup(func(ctx SpecContext) { + Expect(client.IgnoreNotFound(k8sClient.Delete(ctx, resource))).To(Succeed()) + }) }) Context("When reconciling a node", func() { - It("should successfully reconcile the resource", func() { + It("should successfully reconcile the resource", func(ctx SpecContext) { req := ctrl.Request{ NamespacedName: types.NamespacedName{Name: nodeName}, } diff --git a/internal/controller/hypervisor_maintenance_controller_test.go b/internal/controller/hypervisor_maintenance_controller_test.go index 1a56a4b..07cd7e1 100644 --- a/internal/controller/hypervisor_maintenance_controller_test.go +++ b/internal/controller/hypervisor_maintenance_controller_test.go @@ -18,7 +18,6 @@ limitations under the License. package controller import ( - "context" "fmt" "net/http" @@ -79,7 +78,7 @@ var _ = Describe("HypervisorMaintenanceController", func() { } // Setup and teardown - BeforeEach(func(ctx context.Context) { + BeforeEach(func(ctx SpecContext) { By("Setting up the OpenStack http mock server") fakeServer = testhelper.SetupHTTP() DeferCleanup(fakeServer.Teardown) @@ -100,7 +99,7 @@ var _ = Describe("HypervisorMaintenanceController", func() { Spec: kvmv1.HypervisorSpec{}, } Expect(k8sClient.Create(ctx, hypervisor)).To(Succeed()) - DeferCleanup(func(ctx context.Context) { + DeferCleanup(func(ctx SpecContext) { By("Deleting the Hypervisor resource") hypervisor := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, hypervisorName, hypervisor)).To(Succeed()) @@ -109,13 +108,13 @@ var _ = Describe("HypervisorMaintenanceController", func() { }) // After the setup in JustBefore, we want to reconcile - JustBeforeEach(func(ctx context.Context) { + JustBeforeEach(func(ctx SpecContext) { req := ctrl.Request{NamespacedName: hypervisorName} _, err := controller.Reconcile(ctx, req) Expect(err).NotTo(HaveOccurred()) }) - AfterEach(func(ctx context.Context) { + AfterEach(func(ctx SpecContext) { eviction := &kvmv1.Eviction{ ObjectMeta: metav1.ObjectMeta{ Name: hypervisorName.Name, @@ -127,7 +126,7 @@ var _ = Describe("HypervisorMaintenanceController", func() { // Tests Context("Onboarded Hypervisor", func() { - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { hypervisor := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, hypervisorName, hypervisor)).To(Succeed()) hypervisor.Status.ServiceID = "1234" @@ -144,7 +143,7 @@ var _ = Describe("HypervisorMaintenanceController", func() { Describe("Enabling or Disabling the Nova Service", func() { Context("Spec.Maintenance=\"\"", func() { - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { hypervisor := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, hypervisorName, hypervisor)).To(Succeed()) hypervisor.Spec.Maintenance = "" @@ -153,13 +152,13 @@ var _ = Describe("HypervisorMaintenanceController", func() { mockServiceUpdate(expectedBody) }) - It("should set the ConditionTypeHypervisorDisabled to false", func() { + It("should set the ConditionTypeHypervisorDisabled to false", func(ctx SpecContext) { updated := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, hypervisorName, updated)).To(Succeed()) Expect(meta.IsStatusConditionFalse(updated.Status.Conditions, kvmv1.ConditionTypeHypervisorDisabled)).To(BeTrue()) }) - It("should set the ConditionTypeReady to true", func() { + It("should set the ConditionTypeReady to true", func(ctx SpecContext) { updated := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, hypervisorName, updated)).To(Succeed()) Expect(updated.Status.Conditions).To(ContainElement( @@ -173,7 +172,7 @@ var _ = Describe("HypervisorMaintenanceController", func() { for _, mode := range []string{"auto", "manual", "ha"} { Context(fmt.Sprintf("Spec.Maintenance=\"%v\"", mode), func() { - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { hypervisor := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, hypervisorName, hypervisor)).To(Succeed()) hypervisor.Spec.Maintenance = mode @@ -182,13 +181,13 @@ var _ = Describe("HypervisorMaintenanceController", func() { mockServiceUpdate(expectedBody) }) - It("should set the ConditionTypeHypervisorDisabled to true", func() { + It("should set the ConditionTypeHypervisorDisabled to true", func(ctx SpecContext) { updated := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, hypervisorName, updated)).To(Succeed()) Expect(meta.IsStatusConditionTrue(updated.Status.Conditions, kvmv1.ConditionTypeHypervisorDisabled)).To(BeTrue()) }) - It("should set the ConditionTypeReady to false", func() { + It("should set the ConditionTypeReady to false", func(ctx SpecContext) { updated := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, hypervisorName, updated)).To(Succeed()) Expect(updated.Status.Conditions).To(ContainElement( @@ -202,7 +201,7 @@ var _ = Describe("HypervisorMaintenanceController", func() { Describe("Eviction reconciliation", func() { Context("Spec.Maintenance=\"\"", func() { - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { hypervisor := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, hypervisorName, hypervisor)).To(Succeed()) hypervisor.Spec.Maintenance = "" @@ -230,7 +229,7 @@ var _ = Describe("HypervisorMaintenanceController", func() { Expect(k8sClient.Create(ctx, eviction)).To(Succeed()) }) - It("should delete the created eviction", func() { + It("should delete the created eviction", func(ctx SpecContext) { eviction := &kvmv1.Eviction{} err := k8sClient.Get(ctx, hypervisorName, eviction) By(fmt.Sprintf("%+v", *eviction)) @@ -240,7 +239,7 @@ var _ = Describe("HypervisorMaintenanceController", func() { }) // Spec.Maintenance="" Context("Spec.Maintenance=\"ha\"", func() { - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { hypervisor := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, hypervisorName, hypervisor)).To(Succeed()) hypervisor.Spec.Maintenance = "ha" @@ -248,7 +247,7 @@ var _ = Describe("HypervisorMaintenanceController", func() { expectedBody := `{"disabled_reason": "Hypervisor CRD: spec.maintenance=ha", "status": "disabled"}` mockServiceUpdate(expectedBody) }) - It("should not create an eviction resource", func() { + It("should not create an eviction resource", func(ctx SpecContext) { eviction := &kvmv1.Eviction{} err := k8sClient.Get(ctx, hypervisorName, eviction) Expect(err).To(HaveOccurred()) @@ -258,7 +257,7 @@ var _ = Describe("HypervisorMaintenanceController", func() { for _, mode := range []string{"auto", "manual"} { Context(fmt.Sprintf("Spec.Maintenance=\"%v\"", mode), func() { - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { hypervisor := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, hypervisorName, hypervisor)).To(Succeed()) hypervisor.Spec.Maintenance = mode @@ -268,12 +267,12 @@ var _ = Describe("HypervisorMaintenanceController", func() { }) When("there is no eviction yet", func() { - It("should create an eviction resource named as the hypervisor", func() { + It("should create an eviction resource named as the hypervisor", func(ctx SpecContext) { eviction := &kvmv1.Eviction{} Expect(k8sClient.Get(ctx, hypervisorName, eviction)).To(Succeed()) }) - It("should create an evicting condition", func() { + It("should create an evicting condition", func(ctx SpecContext) { hypervisor := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, hypervisorName, hypervisor)).To(Succeed()) Expect(hypervisor.Status.Conditions).To(ContainElement( @@ -285,7 +284,7 @@ var _ = Describe("HypervisorMaintenanceController", func() { )) }) - It("should reflect it in the hypervisor evicted status", func() { + It("should reflect it in the hypervisor evicted status", func(ctx SpecContext) { hypervisor := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, hypervisorName, hypervisor)).To(Succeed()) Expect(hypervisor.Status.Evicted).To(BeFalse()) @@ -293,7 +292,7 @@ var _ = Describe("HypervisorMaintenanceController", func() { }) When("there is a finished eviction", func() { - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { eviction := &kvmv1.Eviction{ ObjectMeta: metav1.ObjectMeta{Name: hypervisorName.Name}, Spec: kvmv1.EvictionSpec{ @@ -316,7 +315,7 @@ var _ = Describe("HypervisorMaintenanceController", func() { Expect(k8sClient.Status().Update(ctx, eviction)).To(Succeed()) }) - It("should reflect it in the hypervisor evicting condition", func() { + It("should reflect it in the hypervisor evicting condition", func(ctx SpecContext) { hypervisor := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, hypervisorName, hypervisor)).To(Succeed()) Expect(hypervisor.Status.Conditions).To(ContainElement( @@ -328,13 +327,13 @@ var _ = Describe("HypervisorMaintenanceController", func() { )) }) - It("should reflect it in the hypervisor evicted status", func() { + It("should reflect it in the hypervisor evicted status", func(ctx SpecContext) { hypervisor := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, hypervisorName, hypervisor)).To(Succeed()) Expect(hypervisor.Status.Evicted).To(BeTrue()) }) - It("should set the ConditionTypeReady to false and reason to evicted", func() { + It("should set the ConditionTypeReady to false and reason to evicted", func(ctx SpecContext) { updated := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, hypervisorName, updated)).To(Succeed()) Expect(updated.Status.Conditions).To(ContainElement( diff --git a/internal/controller/node_certificate_controller_test.go b/internal/controller/node_certificate_controller_test.go index 1e0943d..b704006 100644 --- a/internal/controller/node_certificate_controller_test.go +++ b/internal/controller/node_certificate_controller_test.go @@ -41,7 +41,7 @@ var _ = Describe("Node Certificate Controller", func() { // Setup - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { By("Setting up the test environment") scheme := runtime.NewScheme() Expect(corev1.AddToScheme(scheme)).To(Succeed()) @@ -72,7 +72,7 @@ var _ = Describe("Node Certificate Controller", func() { Expect(fakeClient.Create(ctx, resource)).To(Succeed()) }) - AfterEach(func() { + AfterEach(func(ctx SpecContext) { node := &corev1.Node{ObjectMeta: metav1.ObjectMeta{Name: nodeName}} By("Cleanup the specific node") Expect(client.IgnoreAlreadyExists(fakeClient.Delete(ctx, node))).To(Succeed()) @@ -83,7 +83,7 @@ var _ = Describe("Node Certificate Controller", func() { // Tests Context("When reconciling a node with nova virt label", func() { - It("should successfully create a new certificate", func() { + It("should successfully create a new certificate", func(ctx SpecContext) { By("Reconciling the node") req := ctrl.Request{ NamespacedName: types.NamespacedName{Name: nodeName}, diff --git a/internal/controller/node_eviction_label_controller_test.go b/internal/controller/node_eviction_label_controller_test.go index c7c9769..6866a55 100644 --- a/internal/controller/node_eviction_label_controller_test.go +++ b/internal/controller/node_eviction_label_controller_test.go @@ -18,7 +18,6 @@ limitations under the License. package controller import ( - "context" "os" "github.com/gophercloud/gophercloud/v2/testhelper" @@ -45,7 +44,7 @@ var _ = Describe("Node Eviction Label Controller", func() { reconciler *NodeEvictionLabelReconciler req = ctrl.Request{NamespacedName: types.NamespacedName{Name: nodeName}} fakeServer testhelper.FakeServer - reconcileNodeLoop = func(ctx context.Context, steps int) (res ctrl.Result, err error) { + reconcileNodeLoop = func(ctx SpecContext, steps int) (res ctrl.Result, err error) { for range steps { res, err = reconciler.Reconcile(ctx, req) if err != nil { @@ -56,7 +55,7 @@ var _ = Describe("Node Eviction Label Controller", func() { } ) - BeforeEach(func(ctx context.Context) { + BeforeEach(func(ctx SpecContext) { fakeServer = testhelper.SetupHTTP() Expect(os.Setenv("KVM_HA_SERVICE_URL", fakeServer.Endpoint())).To(Succeed()) @@ -88,7 +87,7 @@ var _ = Describe("Node Eviction Label Controller", func() { } Expect(k8sClient.Create(ctx, resource)).To(Succeed()) - DeferCleanup(func(ctx context.Context) { + DeferCleanup(func(ctx SpecContext) { By("Cleanup the specific node") Expect(k8sClient.Delete(ctx, resource)).To(Succeed()) }) @@ -106,7 +105,7 @@ var _ = Describe("Node Eviction Label Controller", func() { }, } Expect(k8sClient.Create(ctx, hypervisor)).To(Succeed()) - DeferCleanup(func(ctx context.Context) { + DeferCleanup(func(ctx SpecContext) { By("Cleanup the specific hypervisor") Expect(client.IgnoreNotFound(k8sClient.Delete(ctx, hypervisor))).To(Succeed()) }) @@ -114,7 +113,7 @@ var _ = Describe("Node Eviction Label Controller", func() { }) Context("When reconciling a node", func() { - BeforeEach(func(ctx context.Context) { + BeforeEach(func(ctx SpecContext) { hypervisor := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, types.NamespacedName{Name: nodeName}, hypervisor)).To(Succeed()) By("updating the hypervisor status sub-resource") @@ -127,7 +126,7 @@ var _ = Describe("Node Eviction Label Controller", func() { Expect(k8sClient.Status().Update(ctx, hypervisor)).To(Succeed()) }) - It("should successfully reconcile the resource", func(ctx context.Context) { + It("should successfully reconcile the resource", func(ctx SpecContext) { By("ConditionType the created resource") _, err := reconcileNodeLoop(ctx, 5) Expect(err).NotTo(HaveOccurred()) diff --git a/internal/controller/onboarding_controller_test.go b/internal/controller/onboarding_controller_test.go index 2f50d93..7cce58f 100644 --- a/internal/controller/onboarding_controller_test.go +++ b/internal/controller/onboarding_controller_test.go @@ -18,7 +18,6 @@ limitations under the License. package controller import ( - "context" "fmt" "net/http" "os" @@ -213,7 +212,7 @@ var _ = Describe("Onboarding Controller", func() { namespacedName = types.NamespacedName{Name: hypervisorName} fakeServer testhelper.FakeServer reconcileReq = ctrl.Request{NamespacedName: namespacedName} - reconcileLoop = func(ctx context.Context, steps int) (err error) { + reconcileLoop = func(ctx SpecContext, steps int) (err error) { for range steps { _, err = onboardingReconciler.Reconcile(ctx, reconcileReq) if err != nil { @@ -224,7 +223,7 @@ var _ = Describe("Onboarding Controller", func() { } ) - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { By("creating the resource for the Kind Hypervisor") hv := &kvmv1.Hypervisor{ ObjectMeta: metav1.ObjectMeta{ @@ -241,7 +240,7 @@ var _ = Describe("Onboarding Controller", func() { } Expect(k8sClient.Create(ctx, hv)).To(Succeed()) - DeferCleanup(func(ctx context.Context) { + DeferCleanup(func(ctx SpecContext) { By("Cleanup the specific hypervisor CRO") Expect(k8sClient.Delete(ctx, hv)).To(Succeed()) }) @@ -389,7 +388,7 @@ var _ = Describe("Onboarding Controller", func() { }) Context("running tests after initial setup", func() { - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { hv := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, namespacedName, hv)).To(Succeed()) hv.Status.HypervisorID = hypervisorId @@ -497,14 +496,14 @@ var _ = Describe("Onboarding Controller", func() { }) When("SkipTests is set to true", func() { - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { hv := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, namespacedName, hv)).To(Succeed()) hv.Spec.SkipTests = true Expect(k8sClient.Update(ctx, hv)).To(Succeed()) }) - It("should update the conditions", func() { + It("should update the conditions", func(ctx SpecContext) { By("Reconciling the created resource") err := reconcileLoop(ctx, 3) Expect(err).NotTo(HaveOccurred()) @@ -524,14 +523,14 @@ var _ = Describe("Onboarding Controller", func() { }) }) When("SkipTests is set to false", func() { - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { hv := &kvmv1.Hypervisor{} Expect(k8sClient.Get(ctx, namespacedName, hv)).To(Succeed()) hv.Spec.SkipTests = false Expect(k8sClient.Update(ctx, hv)).To(Succeed()) }) - It("should update the conditions", func() { + It("should update the conditions", func(ctx SpecContext) { By("Reconciling the created resource") err := reconcileLoop(ctx, 3) Expect(err).NotTo(HaveOccurred()) diff --git a/internal/controller/suite_test.go b/internal/controller/suite_test.go index fa36940..9e039bf 100644 --- a/internal/controller/suite_test.go +++ b/internal/controller/suite_test.go @@ -18,7 +18,6 @@ limitations under the License. package controller import ( - "context" "fmt" "path/filepath" "runtime" @@ -44,8 +43,6 @@ import ( var cfg *rest.Config var k8sClient client.Client var testEnv *envtest.Environment -var ctx context.Context -var cancel context.CancelFunc func TestControllers(t *testing.T) { RegisterFailHandler(Fail) @@ -56,8 +53,6 @@ func TestControllers(t *testing.T) { var _ = BeforeSuite(func() { logf.SetLogger(zap.New(zap.WriteTo(GinkgoWriter), zap.UseDevMode(true))) - ctx, cancel = context.WithCancel(context.TODO()) - By("bootstrapping test environment") testEnv = &envtest.Environment{ CRDDirectoryPaths: []string{filepath.Join("..", "..", "config", "crd", "bases")}, @@ -91,7 +86,6 @@ var _ = BeforeSuite(func() { var _ = AfterSuite(func() { By("tearing down the test environment") - cancel() err := testEnv.Stop() Expect(err).NotTo(HaveOccurred()) }) diff --git a/internal/controller/traits_controller_test.go b/internal/controller/traits_controller_test.go index 3c14aac..40dd5ca 100644 --- a/internal/controller/traits_controller_test.go +++ b/internal/controller/traits_controller_test.go @@ -18,7 +18,6 @@ limitations under the License. package controller import ( - "context" "fmt" "net/http" @@ -63,7 +62,7 @@ var _ = Describe("TraitsController", func() { // Setup and teardown - BeforeEach(func(ctx context.Context) { + BeforeEach(func(ctx SpecContext) { By("Setting up the OpenStack http mock server") fakeServer = testhelper.SetupHTTP() DeferCleanup(fakeServer.Teardown) @@ -87,7 +86,7 @@ var _ = Describe("TraitsController", func() { } Expect(k8sClient.Create(ctx, hypervisor)).To(Succeed()) - DeferCleanup(func(ctx context.Context) { + DeferCleanup(func(ctx SpecContext) { By("Deleting the Hypervisor resource") hypervisor := &kvmv1.Hypervisor{} Expect(tc.Client.Get(ctx, hypervisorName, hypervisor)).To(Succeed()) @@ -98,7 +97,7 @@ var _ = Describe("TraitsController", func() { // Tests Context("Reconcile after onboarding before decommissioning", func() { - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { // Mock resourceproviders.GetTraits fakeServer.Mux.HandleFunc("GET /resource_providers/1234/traits", func(w http.ResponseWriter, r *http.Request) { w.Header().Add("Content-Type", "application/json") @@ -146,7 +145,7 @@ var _ = Describe("TraitsController", func() { Expect(k8sClient.Status().Update(ctx, hypervisor)).To(Succeed()) }) - It("should update traits and set status condition when traits differ", func() { + It("should update traits and set status condition when traits differ", func(ctx SpecContext) { req := ctrl.Request{NamespacedName: hypervisorName} _, err := tc.Reconcile(ctx, req) Expect(err).NotTo(HaveOccurred()) @@ -159,7 +158,7 @@ var _ = Describe("TraitsController", func() { }) Context("Reconcile before onboarding", func() { - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { // Mock resourceproviders.GetTraits fakeServer.Mux.HandleFunc("GET /resource_providers/1234/traits", func(w http.ResponseWriter, r *http.Request) { defer GinkgoRecover() @@ -178,7 +177,7 @@ var _ = Describe("TraitsController", func() { Expect(k8sClient.Status().Update(ctx, hypervisor)).To(Succeed()) }) - It("should not update traits", func() { + It("should not update traits", func(ctx SpecContext) { req := ctrl.Request{NamespacedName: hypervisorName} _, err := tc.Reconcile(ctx, req) Expect(err).NotTo(HaveOccurred()) @@ -191,7 +190,7 @@ var _ = Describe("TraitsController", func() { }) Context("Reconcile when terminating", func() { - BeforeEach(func() { + BeforeEach(func(ctx SpecContext) { // Mock resourceproviders.GetTraits fakeServer.Mux.HandleFunc("GET /resource_providers/1234/traits", func(w http.ResponseWriter, r *http.Request) { defer GinkgoRecover() @@ -221,7 +220,7 @@ var _ = Describe("TraitsController", func() { }) - It("should not update traits", func() { + It("should not update traits", func(ctx SpecContext) { req := ctrl.Request{NamespacedName: hypervisorName} _, err := tc.Reconcile(ctx, req) Expect(err).NotTo(HaveOccurred())