使用测试包在golang中导入周期

I am trying to refactor some test code and in two packages I need to do the same thing (connect to a DB). I am getting an import cycle. I get why I can't do it, but am wondering what the best way around it is.

Some specifics, I have three packages: testutils, client, engine.

In engine I define an interface & implementation (both exported).

package engine
type interface QueryEngine {
  // ...
}
type struct MagicEngine {
  // ...
}

And then in the testutils package I will create a MagicEngine and try and return it.

package testutils
func CreateAndConnect() (*engine.MagicEngine, error) {
  // ....
}

Now in the test code (using a TestMain) I need to do something like

package engine
func TestMain(m *testing.M) {
  e, err := testutils.CreateAndConnect()
  // ....
  os.Exit(m.Run())
}

This is of course a cycle. I want to do this so that I can in the client package also use this testutils.CreateAndConnect() method. I don't want to repeat the code in both packages. I don't want it in the main code of the engine package, it is very specific to the tests.

I tried adding it as an exported method on the engine test class (engine/engine_test.go) and using it in the client/client_test.go. No dice. :/

I feel I have done this in other languages, but could be crazy. What is the best way to structure this code for reusability?

You could use black-box style testing because the components of engine are exported. Change your tests to be in package engine_test:

package engine_test
import "engine"
import "testutils"
func TestMain(m *testing.M) {
  e, err := testutils.CreateAndConnect()
  // ....
  os.Exit(m.Run())
}