github.com/kubeshop/testkube@v1.17.23/internal/graphql/services/executors_test.go (about) 1 package services 2 3 import ( 4 "context" 5 "testing" 6 7 "github.com/stretchr/testify/assert" 8 metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" 9 "k8s.io/apimachinery/pkg/runtime" 10 k8sclient "sigs.k8s.io/controller-runtime/pkg/client" 11 "sigs.k8s.io/controller-runtime/pkg/client/fake" 12 13 executorv1 "github.com/kubeshop/testkube-operator/api/executor/v1" 14 executorsclientv1 "github.com/kubeshop/testkube-operator/pkg/client/executors/v1" 15 "github.com/kubeshop/testkube/pkg/api/v1/testkube" 16 ) 17 18 var ( 19 srvMock = NewMockService() 20 k8sObjects = []k8sclient.Object{ 21 &executorv1.Executor{ 22 TypeMeta: metav1.TypeMeta{ 23 Kind: "Executor", 24 APIVersion: "executor.testkube.io/v1", 25 }, 26 ObjectMeta: metav1.ObjectMeta{ 27 Name: "sample", 28 Namespace: "default", 29 Labels: map[string]string{ 30 "label-name": "label-value", 31 }, 32 }, 33 Spec: executorv1.ExecutorSpec{ 34 Types: []string{"curl/test"}, 35 ExecutorType: "job", 36 JobTemplate: "", 37 JobTemplateReference: "", 38 }, 39 Status: executorv1.ExecutorStatus{}, 40 }, 41 } 42 sample = testkube.ExecutorDetails{ 43 Name: "sample", 44 Executor: &testkube.Executor{ 45 ExecutorType: "job", 46 Image: "", 47 ImagePullSecrets: nil, 48 Command: nil, 49 Args: nil, 50 Types: []string{"curl/test"}, 51 Uri: "", 52 ContentTypes: nil, 53 JobTemplate: "", 54 JobTemplateReference: "", 55 Labels: map[string]string{"label-name": "label-value"}, 56 Features: nil, 57 Meta: nil, 58 }, 59 } 60 k8sObjects2 = []k8sclient.Object{ 61 &executorv1.Executor{ 62 TypeMeta: metav1.TypeMeta{ 63 Kind: "Executor", 64 APIVersion: "executor.testkube.io/v1", 65 }, 66 ObjectMeta: metav1.ObjectMeta{ 67 Name: "sample", 68 Namespace: "default", 69 Labels: map[string]string{ 70 "label-name": "label-value", 71 }, 72 }, 73 Spec: executorv1.ExecutorSpec{ 74 Types: []string{"other/test"}, 75 ExecutorType: "job", 76 JobTemplate: "", 77 JobTemplateReference: "", 78 }, 79 Status: executorv1.ExecutorStatus{}, 80 }, 81 } 82 sample2 = testkube.ExecutorDetails{ 83 Name: "sample", 84 Executor: &testkube.Executor{ 85 ExecutorType: "job", 86 Image: "", 87 ImagePullSecrets: nil, 88 Command: nil, 89 Args: nil, 90 Types: []string{"other/test"}, 91 Uri: "", 92 ContentTypes: nil, 93 JobTemplate: "", 94 JobTemplateReference: "", 95 Labels: map[string]string{"label-name": "label-value"}, 96 Features: nil, 97 Meta: nil, 98 }, 99 } 100 ) 101 102 var ( 103 client *executorsclientv1.ExecutorsClient 104 srv ExecutorsService 105 ) 106 107 func ResetMocks() { 108 srvMock.Reset() 109 client = getMockExecutorClient(k8sObjects) 110 srv = NewExecutorsService(srvMock, client) 111 } 112 113 func TestExecutorsService_List(t *testing.T) { 114 t.Run("should list all available executors when no selector passed", func(t *testing.T) { 115 ResetMocks() 116 result, err := srv.List("") 117 assert.NoError(t, err) 118 assert.Equal(t, result, []testkube.ExecutorDetails{sample}) 119 }) 120 121 t.Run("should list none executors when none matches selector", func(t *testing.T) { 122 ResetMocks() 123 result, err := srv.List("xyz=def") 124 assert.NoError(t, err) 125 assert.Equal(t, result, []testkube.ExecutorDetails{}) 126 }) 127 128 t.Run("should list executors matching the selector", func(t *testing.T) { 129 ResetMocks() 130 result, err := srv.List("label-name=label-value") 131 assert.NoError(t, err) 132 assert.Equal(t, result, []testkube.ExecutorDetails{sample}) 133 }) 134 } 135 136 func TestExecutorsService_SubscribeList(t *testing.T) { 137 t.Run("should cancel subscription when the context is canceled", func(t *testing.T) { 138 ResetMocks() 139 ctx, cancel := context.WithCancel(context.Background()) 140 ch, err := srv.SubscribeList(ctx, "") 141 assert.NoError(t, err) 142 <-ch 143 cancel() 144 _, opened := <-ch 145 assert.False(t, opened) 146 assert.Len(t, srvMock.BusMock().ListQueues(), 0) 147 }) 148 149 t.Run("should return initial list of executors", func(t *testing.T) { 150 ResetMocks() 151 ch, err := srv.SubscribeList(context.Background(), "") 152 assert.NoError(t, err) 153 result := <-ch 154 assert.Equal(t, result, []testkube.ExecutorDetails{sample}) 155 }) 156 157 t.Run("should subscribe for new entries", func(t *testing.T) { 158 ResetMocks() 159 ch, err := srv.SubscribeList(context.Background(), "") 160 assert.NoError(t, err) 161 result := <-ch 162 assert.Equal(t, result, []testkube.ExecutorDetails{sample}) 163 assert.Len(t, srvMock.BusMock().ListQueues(), 1) 164 }) 165 166 t.Run("should return new list of executors after events are triggered", func(t *testing.T) { 167 ResetMocks() 168 ch, err := srv.SubscribeList(context.Background(), "") 169 assert.NoError(t, err) 170 <-ch 171 client.Client = getMockExecutorClient(k8sObjects2).Client 172 assert.NoError(t, srvMock.BusMock().PublishTopic("events.executor.create", testkube.Event{ 173 Type_: testkube.EventCreated, 174 Resource: testkube.EventResourceExecutor, 175 })) 176 assert.Equal(t, <-ch, []testkube.ExecutorDetails{sample2}) 177 }) 178 } 179 180 func getMockExecutorClient(initObjects []k8sclient.Object) *executorsclientv1.ExecutorsClient { 181 scheme := runtime.NewScheme() 182 executorv1.AddToScheme(scheme) 183 184 fakeClient := fake.NewClientBuilder(). 185 WithScheme(scheme). 186 WithObjects(initObjects...). 187 Build() 188 return executorsclientv1.NewClient(fakeClient, "") 189 }