Browse Source

Add unit tests to graph building logic in `dependencies.go`

Signed-off-by: Laura Brehm <[email protected]>
Laura Brehm 3 years ago
parent
commit
4c474fe029
1 changed files with 180 additions and 0 deletions
  1. 180 0
      pkg/compose/dependencies_test.go

+ 180 - 0
pkg/compose/dependencies_test.go

@@ -18,10 +18,12 @@ package compose
 
 import (
 	"context"
+	"fmt"
 	"testing"
 
 	"github.com/compose-spec/compose-go/types"
 	"github.com/stretchr/testify/require"
+	"gotest.tools/assert"
 )
 
 var project = types.Project{
@@ -69,3 +71,181 @@ func TestInDependencyReverseDownCommandOrder(t *testing.T) {
 	require.NoError(t, err, "Error during iteration")
 	require.Equal(t, []string{"test1", "test2", "test3"}, order)
 }
+
+func TestBuildGraph(t *testing.T) {
+	testCases := []struct {
+		desc             string
+		services         types.Services
+		expectedVertices map[string]*Vertex
+	}{
+		{
+			desc: "builds graph with single service",
+			services: types.Services{
+				{
+					Name:      "test",
+					DependsOn: types.DependsOnConfig{},
+				},
+			},
+			expectedVertices: map[string]*Vertex{
+				"test": {
+					Key:      "test",
+					Service:  "test",
+					Status:   ServiceStopped,
+					Children: map[string]*Vertex{},
+					Parents:  map[string]*Vertex{},
+				},
+			},
+		},
+		{
+			desc: "builds graph with two separate services",
+			services: types.Services{
+				{
+					Name:      "test",
+					DependsOn: types.DependsOnConfig{},
+				},
+				{
+					Name:      "another",
+					DependsOn: types.DependsOnConfig{},
+				},
+			},
+			expectedVertices: map[string]*Vertex{
+				"test": {
+					Key:      "test",
+					Service:  "test",
+					Status:   ServiceStopped,
+					Children: map[string]*Vertex{},
+					Parents:  map[string]*Vertex{},
+				},
+				"another": {
+					Key:      "another",
+					Service:  "another",
+					Status:   ServiceStopped,
+					Children: map[string]*Vertex{},
+					Parents:  map[string]*Vertex{},
+				},
+			},
+		},
+		{
+			desc: "builds graph with a service and a dependency",
+			services: types.Services{
+				{
+					Name: "test",
+					DependsOn: types.DependsOnConfig{
+						"another": types.ServiceDependency{},
+					},
+				},
+				{
+					Name:      "another",
+					DependsOn: types.DependsOnConfig{},
+				},
+			},
+			expectedVertices: map[string]*Vertex{
+				"test": {
+					Key:     "test",
+					Service: "test",
+					Status:  ServiceStopped,
+					Children: map[string]*Vertex{
+						"another": {},
+					},
+					Parents: map[string]*Vertex{},
+				},
+				"another": {
+					Key:      "another",
+					Service:  "another",
+					Status:   ServiceStopped,
+					Children: map[string]*Vertex{},
+					Parents: map[string]*Vertex{
+						"test": {},
+					},
+				},
+			},
+		},
+		{
+			desc: "builds graph with multiple dependency levels",
+			services: types.Services{
+				{
+					Name: "test",
+					DependsOn: types.DependsOnConfig{
+						"another": types.ServiceDependency{},
+					},
+				},
+				{
+					Name: "another",
+					DependsOn: types.DependsOnConfig{
+						"another_dep": types.ServiceDependency{},
+					},
+				},
+				{
+					Name:      "another_dep",
+					DependsOn: types.DependsOnConfig{},
+				},
+			},
+			expectedVertices: map[string]*Vertex{
+				"test": {
+					Key:     "test",
+					Service: "test",
+					Status:  ServiceStopped,
+					Children: map[string]*Vertex{
+						"another": {},
+					},
+					Parents: map[string]*Vertex{},
+				},
+				"another": {
+					Key:     "another",
+					Service: "another",
+					Status:  ServiceStopped,
+					Children: map[string]*Vertex{
+						"another_dep": {},
+					},
+					Parents: map[string]*Vertex{
+						"test": {},
+					},
+				},
+				"another_dep": {
+					Key:      "another_dep",
+					Service:  "another_dep",
+					Status:   ServiceStopped,
+					Children: map[string]*Vertex{},
+					Parents: map[string]*Vertex{
+						"another": {},
+					},
+				},
+			},
+		},
+	}
+	for _, tC := range testCases {
+		t.Run(tC.desc, func(t *testing.T) {
+			project := types.Project{
+				Services: tC.services,
+			}
+
+			graph, err := NewGraph(project.Services, ServiceStopped)
+			assert.NilError(t, err, fmt.Sprintf("failed to build graph for: %s", tC.desc))
+
+			for k, vertex := range graph.Vertices {
+				expected, ok := tC.expectedVertices[k]
+				assert.Equal(t, true, ok)
+				assert.Equal(t, true, isVertexEqual(*expected, *vertex))
+			}
+		})
+	}
+}
+
+func isVertexEqual(a, b Vertex) bool {
+	childrenEquality := true
+	for c := range a.Children {
+		if _, ok := b.Children[c]; !ok {
+			childrenEquality = false
+		}
+	}
+	parentEquality := true
+	for p := range a.Parents {
+		if _, ok := b.Parents[p]; !ok {
+			parentEquality = false
+		}
+	}
+	return a.Key == b.Key &&
+		a.Service == b.Service &&
+		childrenEquality &&
+		parentEquality
+}