DEV Community

Taylor Silva
Taylor Silva

Posted on

Creating Your Own BeforeEach() in Go

I'm developing my own budgeting app using Go and have been using it to learn new things as well. For testing, because I'm TDD'ing the entire project, I decided to just use the built-in Go testing framework. I use Ginkgo at work and enjoy it, but decided to see what vanilla testing in Go is like.

After writing a bunch of tests for a lot of my boilerplate functions, I quickly had a lot of duplicated set-up code that looked like this at the start of all my tests:

g := NewGomegaWithT(t)

db, err := createTestDb()
g.Expect(err).To(BeNil(), ErrorDidNotOccur)

api := NewApi(db, SelectedQueryLang)

I was having trouble figuring out how to pull this out into it's own function. Finally I saw a Stack Overflow answer that provided me with a solution (having trouble finding the link now!).

Here's how you create your own BeforeEach() function when using Go's testing framework.

First, create a struct that will hold the objects your test needs to access. Mine looks like this:

type TestingBasics struct {
    GoMega *GomegaWithT
    Db     *sql.DB
    Api    *api

Then create your BeforeEach() function that will create this struct for your tests.

func BeforeEach(t *testing.T, SelectedQueryLang *QueryLang) (tb TestingBasics) {
    tb.GoMega = NewGomegaWithT(t)

    var err error
    tb.Db, err = createTestDb()
    tb.GoMega.Expect(err).To(BeNil(), ErrorDidNotOccur)

    tb.Api = NewApi(tb.Db, SelectedQueryLang)

    return tb

Now all you need to do is call BeforeEach() at the beginning of your tests. I was able to reduce 4 lines of code down to 1 across all of my tests. Now the start of each of my tests look like this:

t.Run("should add one transaction", func(t *testing.T) {
    tb := BeforeEach(t, SelectedQueryLang)

This can definitely be cleaned up even further, to the point where I wouldn't even need to call BeforeEach() at the start of each test. At that point though, I might as well have gone with Ginkgo. For me and this project, I am fine with this set up.

Top comments (0)