package consul import ( "net/rpc" "os" "testing" "github.com/hashicorp/consul/testrpc" "github.com/stretchr/testify/require" ) type testClusterConfig struct { Datacenter string Servers int Clients int ServerConf func(*Config) ClientConf func(*Config) ServerWait func(*testing.T, *Server) ClientWait func(*testing.T, *Client) } type testCluster struct { Servers []*Server ServerCodecs []rpc.ClientCodec Clients []*Client } func newTestCluster(t *testing.T, conf *testClusterConfig) *testCluster { t.Helper() require.NotNil(t, conf) cluster := testCluster{} // create the servers for i := 0; i < conf.Servers; i++ { dir, srv := testServerWithConfig(t, func(c *Config) { if conf.Datacenter != "" { c.Datacenter = conf.Datacenter } c.Bootstrap = false c.BootstrapExpect = conf.Servers if conf.ServerConf != nil { conf.ServerConf(c) } }) t.Cleanup(func() { os.RemoveAll(dir) }) t.Cleanup(func() { srv.Shutdown() }) cluster.Servers = append(cluster.Servers, srv) codec := rpcClient(t, srv) cluster.ServerCodecs = append(cluster.ServerCodecs, codec) t.Cleanup(func() { codec.Close() }) if i > 0 { joinLAN(t, srv, cluster.Servers[0]) } } waitForLeaderEstablishment(t, cluster.Servers...) if conf.ServerWait != nil { for _, srv := range cluster.Servers { conf.ServerWait(t, srv) } } // create the clients for i := 0; i < conf.Clients; i++ { dir, client := testClientWithConfig(t, func(c *Config) { if conf.Datacenter != "" { c.Datacenter = conf.Datacenter } if conf.ClientConf != nil { conf.ClientConf(c) } }) t.Cleanup(func() { os.RemoveAll(dir) }) t.Cleanup(func() { client.Shutdown() }) if len(cluster.Servers) > 0 { joinLAN(t, client, cluster.Servers[0]) } cluster.Clients = append(cluster.Clients, client) } for _, client := range cluster.Clients { if conf.ClientWait != nil { conf.ClientWait(t, client) } else { testrpc.WaitForTestAgent(t, client.RPC, client.config.Datacenter) } } return &cluster }