Search code examples
gokubernetesginkgo

when defer func is executed at ginkgo


I'm rewriting unit test of our k8s controller with ginkgo.

As previous TDD, for each test, we will have something like.

    // Create the Channel  object and expect the Reconcile
    g.Expect(c.Create(context.TODO(), myObj)).NotTo(gomega.HaveOccurred())
    defer c.Delete(context.TODO(),myObj)

What we want is, create an object for a test and delete it from the underline cluster after this test.

Now, on ginkgo, we are running tests within spec of containers. To me the container is the origin process, if that's the case does it mean the defer defined within the It spec will execute before exiting container instead of exiting the It spec.

For example,

var _ = Describe("my desr", func(){
   It("a", func(){
     fmt.Println(100)
     defer func(){fmt.Println("a", 100)}()
   })

   It("b", func(){
     fmt.Println(200)
     defer func(){fmt.Println("b", 200)}()
  })
})

Would the result be:

a

100
a100
200
b200

Or

b

100
200
b200
a100

In my case, I definitely what the first behavior. Or I'm in the wrong direction in terms of getting the defer behavior? I mean, should I look into the BeforeEach and AfterEach approach?


Solution

  • Do you plan to run tests in parallel? If so, then results will be unpredictable. In that case it's recommended to have a separate instance of external resources for each process.

    I would recommend to look at how controller tests are implemented in controller-runtime. I believe, they create new Control Plane with envtest each time BeforeSuit function is called. And as ginkgo docs states:

    when running in parallel, each parallel process will run BeforeSuite and AfterSuite functions