1
16
17 package apiclient
18
19 import (
20 "context"
21 "os"
22 "testing"
23 "time"
24
25 "github.com/google/go-cmp/cmp"
26 "github.com/pkg/errors"
27
28 apps "k8s.io/api/apps/v1"
29 v1 "k8s.io/api/core/v1"
30 rbac "k8s.io/api/rbac/v1"
31 apierrors "k8s.io/apimachinery/pkg/api/errors"
32 metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
33 "k8s.io/apimachinery/pkg/runtime"
34 "k8s.io/apimachinery/pkg/runtime/schema"
35 clientsetfake "k8s.io/client-go/kubernetes/fake"
36 clientgotesting "k8s.io/client-go/testing"
37
38 kubeadmapi "k8s.io/kubernetes/cmd/kubeadm/app/apis/kubeadm"
39 )
40
41 func TestMain(m *testing.M) {
42
43 defaultRetryInterval := apiCallRetryInterval
44 apiCallRetryInterval = time.Millisecond * 50
45
46 defaultTimeouts := kubeadmapi.GetActiveTimeouts()
47 defaultAPICallTimeout := defaultTimeouts.KubernetesAPICall
48 defaultTimeouts.KubernetesAPICall = &metav1.Duration{Duration: apiCallRetryInterval}
49
50 exitVal := m.Run()
51
52
53 apiCallRetryInterval = defaultRetryInterval
54 defaultTimeouts.KubernetesAPICall = defaultAPICallTimeout
55
56 os.Exit(exitVal)
57 }
58
59 func TestCreateOrUpdateConfigMap(t *testing.T) {
60 tests := []struct {
61 name string
62 setupClient func(*clientsetfake.Clientset)
63 expectedError bool
64 }{
65 {
66 name: "create configmap success",
67 setupClient: func(client *clientsetfake.Clientset) {
68 client.PrependReactor("create", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
69 return true, nil, nil
70 })
71 },
72 expectedError: false,
73 },
74 {
75 name: "create configmap returns error",
76 setupClient: func(client *clientsetfake.Clientset) {
77 client.PrependReactor("create", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
78 return true, nil, errors.New("unknown error")
79 })
80 },
81 expectedError: true,
82 },
83 {
84 name: "configmap exists, update it",
85 setupClient: func(client *clientsetfake.Clientset) {
86 client.PrependReactor("create", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
87 return true, nil, apierrors.NewAlreadyExists(schema.GroupResource{}, "name")
88 })
89 client.PrependReactor("update", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
90 return true, nil, nil
91 })
92 },
93 expectedError: false,
94 },
95 {
96 name: "configmap exists, update error",
97 setupClient: func(client *clientsetfake.Clientset) {
98 client.PrependReactor("create", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
99 return true, nil, apierrors.NewAlreadyExists(schema.GroupResource{}, "name")
100 })
101 client.PrependReactor("update", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
102 return true, nil, errors.New("")
103 })
104 },
105 expectedError: true,
106 },
107 }
108
109 for _, tc := range tests {
110 t.Run(tc.name, func(t *testing.T) {
111 client := clientsetfake.NewSimpleClientset()
112 tc.setupClient(client)
113 err := CreateOrUpdateConfigMap(client, &v1.ConfigMap{})
114 if (err != nil) != tc.expectedError {
115 t.Fatalf("expected error: %v, got %v, error: %v", tc.expectedError, err != nil, err)
116 }
117 })
118 }
119 }
120
121 func TestCreateOrMutateConfigMap(t *testing.T) {
122 tests := []struct {
123 name string
124 setupClient func(*clientsetfake.Clientset)
125 mutator func(*v1.ConfigMap) error
126 expectedError bool
127 }{
128 {
129 name: "create configmap",
130 setupClient: func(client *clientsetfake.Clientset) {
131 client.PrependReactor("create", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
132 return true, nil, nil
133 })
134 client.PrependReactor("get", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
135 return true, nil, nil
136 })
137 client.PrependReactor("update", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
138 return true, nil, nil
139 })
140 },
141 expectedError: false,
142 },
143 {
144 name: "create configmap error",
145 setupClient: func(client *clientsetfake.Clientset) {
146 client.PrependReactor("create", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
147 return true, nil, errors.New("")
148 })
149 },
150 expectedError: true,
151 },
152 {
153 name: "configmap exists, mutate returns error",
154 setupClient: func(client *clientsetfake.Clientset) {
155 client.PrependReactor("create", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
156 return true, nil, apierrors.NewAlreadyExists(schema.GroupResource{}, "name")
157 })
158 client.PrependReactor("get", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
159 return true, &v1.ConfigMap{}, nil
160 })
161 },
162 mutator: func(*v1.ConfigMap) error { return errors.New("") },
163 expectedError: true,
164 },
165 {
166 name: "configmap exists, get returns error",
167 setupClient: func(client *clientsetfake.Clientset) {
168 client.PrependReactor("create", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
169 return true, nil, apierrors.NewAlreadyExists(schema.GroupResource{}, "name")
170 })
171 client.PrependReactor("get", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
172 return true, nil, errors.New("")
173 })
174 },
175 expectedError: true,
176 },
177 {
178 name: "configmap exists, mutate returns error",
179 setupClient: func(client *clientsetfake.Clientset) {
180 client.PrependReactor("create", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
181 return true, nil, apierrors.NewAlreadyExists(schema.GroupResource{}, "name")
182 })
183 client.PrependReactor("get", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
184 return true, &v1.ConfigMap{}, nil
185 })
186 client.PrependReactor("update", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
187 return true, nil, errors.New("")
188 })
189 },
190 mutator: func(*v1.ConfigMap) error { return nil },
191 expectedError: true,
192 },
193 }
194
195 for _, tc := range tests {
196 t.Run(tc.name, func(t *testing.T) {
197 client := clientsetfake.NewSimpleClientset()
198 tc.setupClient(client)
199 err := CreateOrMutateConfigMap(client, &v1.ConfigMap{}, tc.mutator)
200 if (err != nil) != tc.expectedError {
201 t.Fatalf("expected error: %v, got %v, error: %v", tc.expectedError, err != nil, err)
202 }
203 })
204 }
205 }
206
207 func TestCreateOrRetainConfigMap(t *testing.T) {
208 tests := []struct {
209 name string
210 setupClient func(*clientsetfake.Clientset)
211 expectedError bool
212 }{
213 {
214 name: "configmap exists",
215 setupClient: func(client *clientsetfake.Clientset) {
216 client.PrependReactor("get", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
217 return true, &v1.ConfigMap{}, nil
218 })
219 },
220 expectedError: false,
221 },
222 {
223 name: "configmap get returns an error",
224 setupClient: func(client *clientsetfake.Clientset) {
225 client.PrependReactor("get", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
226 return true, nil, errors.New("")
227 })
228 },
229 expectedError: true,
230 },
231 {
232 name: "configmap is not found, create it",
233 setupClient: func(client *clientsetfake.Clientset) {
234 client.PrependReactor("get", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
235 return true, nil, apierrors.NewNotFound(schema.GroupResource{}, "name")
236 })
237 client.PrependReactor("create", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
238 return true, nil, nil
239 })
240 },
241 expectedError: false,
242 },
243 {
244 name: "configmap is not found, create returns an error",
245 setupClient: func(client *clientsetfake.Clientset) {
246 client.PrependReactor("get", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
247 return true, nil, apierrors.NewNotFound(schema.GroupResource{}, "name")
248 })
249 client.PrependReactor("create", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
250 return true, nil, errors.New("")
251 })
252 },
253 expectedError: true,
254 },
255 }
256
257 for _, tc := range tests {
258 t.Run(tc.name, func(t *testing.T) {
259 client := clientsetfake.NewSimpleClientset()
260 tc.setupClient(client)
261 err := CreateOrRetainConfigMap(client, &v1.ConfigMap{}, "some-cm")
262 if (err != nil) != tc.expectedError {
263 t.Fatalf("expected error: %v, got %v, error: %v", tc.expectedError, err != nil, err)
264 }
265 })
266 }
267 }
268
269 func TestCreateOrUpdateSecret(t *testing.T) {
270 tests := []struct {
271 name string
272 setupClient func(*clientsetfake.Clientset)
273 expectedError bool
274 }{
275 {
276 name: "create secret success",
277 setupClient: func(client *clientsetfake.Clientset) {
278 client.PrependReactor("create", "secrets", func(clientgotesting.Action) (bool, runtime.Object, error) {
279 return true, nil, nil
280 })
281 },
282 expectedError: false,
283 },
284 {
285 name: "create secret returns error",
286 setupClient: func(client *clientsetfake.Clientset) {
287 client.PrependReactor("create", "secrets", func(clientgotesting.Action) (bool, runtime.Object, error) {
288 return true, nil, errors.New("unknown error")
289 })
290 },
291 expectedError: true,
292 },
293 {
294 name: "secret exists, update it",
295 setupClient: func(client *clientsetfake.Clientset) {
296 client.PrependReactor("create", "secrets", func(clientgotesting.Action) (bool, runtime.Object, error) {
297 return true, nil, apierrors.NewAlreadyExists(schema.GroupResource{}, "name")
298 })
299 client.PrependReactor("update", "secrets", func(clientgotesting.Action) (bool, runtime.Object, error) {
300 return true, nil, nil
301 })
302 },
303 expectedError: false,
304 },
305 {
306 name: "secret exists, update error",
307 setupClient: func(client *clientsetfake.Clientset) {
308 client.PrependReactor("create", "secrets", func(clientgotesting.Action) (bool, runtime.Object, error) {
309 return true, nil, apierrors.NewAlreadyExists(schema.GroupResource{}, "name")
310 })
311 client.PrependReactor("update", "secrets", func(clientgotesting.Action) (bool, runtime.Object, error) {
312 return true, nil, errors.New("")
313 })
314 },
315 expectedError: true,
316 },
317 }
318
319 for _, tc := range tests {
320 t.Run(tc.name, func(t *testing.T) {
321 client := clientsetfake.NewSimpleClientset()
322 tc.setupClient(client)
323 err := CreateOrUpdateSecret(client, &v1.Secret{})
324 if (err != nil) != tc.expectedError {
325 t.Fatalf("expected error: %v, got %v, error: %v", tc.expectedError, err != nil, err)
326 }
327 })
328 }
329 }
330
331 func TestCreateOrUpdateServiceAccount(t *testing.T) {
332 tests := []struct {
333 name string
334 setupClient func(*clientsetfake.Clientset)
335 expectedError bool
336 }{
337 {
338 name: "create serviceaccount success",
339 setupClient: func(client *clientsetfake.Clientset) {
340 client.PrependReactor("create", "serviceaccounts", func(clientgotesting.Action) (bool, runtime.Object, error) {
341 return true, nil, nil
342 })
343 },
344 expectedError: false,
345 },
346 {
347 name: "create serviceaccount returns error",
348 setupClient: func(client *clientsetfake.Clientset) {
349 client.PrependReactor("create", "serviceaccounts", func(clientgotesting.Action) (bool, runtime.Object, error) {
350 return true, nil, errors.New("unknown error")
351 })
352 },
353 expectedError: true,
354 },
355 {
356 name: "serviceaccount exists, update it",
357 setupClient: func(client *clientsetfake.Clientset) {
358 client.PrependReactor("create", "serviceaccounts", func(clientgotesting.Action) (bool, runtime.Object, error) {
359 return true, nil, apierrors.NewAlreadyExists(schema.GroupResource{}, "name")
360 })
361 client.PrependReactor("update", "serviceaccounts", func(clientgotesting.Action) (bool, runtime.Object, error) {
362 return true, nil, nil
363 })
364 },
365 expectedError: false,
366 },
367 {
368 name: "serviceaccount exists, update error",
369 setupClient: func(client *clientsetfake.Clientset) {
370 client.PrependReactor("create", "serviceaccounts", func(clientgotesting.Action) (bool, runtime.Object, error) {
371 return true, nil, apierrors.NewAlreadyExists(schema.GroupResource{}, "name")
372 })
373 client.PrependReactor("update", "serviceaccounts", func(clientgotesting.Action) (bool, runtime.Object, error) {
374 return true, nil, errors.New("")
375 })
376 },
377 expectedError: true,
378 },
379 }
380
381 for _, tc := range tests {
382 t.Run(tc.name, func(t *testing.T) {
383 client := clientsetfake.NewSimpleClientset()
384 tc.setupClient(client)
385 err := CreateOrUpdateServiceAccount(client, &v1.ServiceAccount{})
386 if (err != nil) != tc.expectedError {
387 t.Fatalf("expected error: %v, got %v, error: %v", tc.expectedError, err != nil, err)
388 }
389 })
390 }
391 }
392
393 func TestCreateOrUpdateDeployment(t *testing.T) {
394 tests := []struct {
395 name string
396 setupClient func(*clientsetfake.Clientset)
397 expectedError bool
398 }{
399 {
400 name: "create deployment success",
401 setupClient: func(client *clientsetfake.Clientset) {
402 client.PrependReactor("create", "deployments", func(clientgotesting.Action) (bool, runtime.Object, error) {
403 return true, nil, nil
404 })
405 },
406 expectedError: false,
407 },
408 {
409 name: "create deployment returns error",
410 setupClient: func(client *clientsetfake.Clientset) {
411 client.PrependReactor("create", "deployments", func(clientgotesting.Action) (bool, runtime.Object, error) {
412 return true, nil, errors.New("unknown error")
413 })
414 },
415 expectedError: true,
416 },
417 {
418 name: "deployment exists, update it",
419 setupClient: func(client *clientsetfake.Clientset) {
420 client.PrependReactor("create", "deployments", func(clientgotesting.Action) (bool, runtime.Object, error) {
421 return true, nil, apierrors.NewAlreadyExists(schema.GroupResource{}, "name")
422 })
423 client.PrependReactor("update", "deployments", func(clientgotesting.Action) (bool, runtime.Object, error) {
424 return true, nil, nil
425 })
426 },
427 expectedError: false,
428 },
429 {
430 name: "deployment exists, update error",
431 setupClient: func(client *clientsetfake.Clientset) {
432 client.PrependReactor("create", "deployments", func(clientgotesting.Action) (bool, runtime.Object, error) {
433 return true, nil, apierrors.NewAlreadyExists(schema.GroupResource{}, "name")
434 })
435 client.PrependReactor("update", "deployments", func(clientgotesting.Action) (bool, runtime.Object, error) {
436 return true, nil, errors.New("")
437 })
438 },
439 expectedError: true,
440 },
441 }
442
443 for _, tc := range tests {
444 t.Run(tc.name, func(t *testing.T) {
445 client := clientsetfake.NewSimpleClientset()
446 tc.setupClient(client)
447 err := CreateOrUpdateDeployment(client, &apps.Deployment{})
448 if (err != nil) != tc.expectedError {
449 t.Fatalf("expected error: %v, got %v, error: %v", tc.expectedError, err != nil, err)
450 }
451 })
452 }
453 }
454
455 func TestCreateOrRetainDeployment(t *testing.T) {
456 tests := []struct {
457 name string
458 setupClient func(*clientsetfake.Clientset)
459 expectedError bool
460 }{
461 {
462 name: "deployment exists",
463 setupClient: func(client *clientsetfake.Clientset) {
464 client.PrependReactor("get", "deployments", func(clientgotesting.Action) (bool, runtime.Object, error) {
465 return true, &apps.Deployment{}, nil
466 })
467 },
468 expectedError: false,
469 },
470 {
471 name: "deployment get returns an error",
472 setupClient: func(client *clientsetfake.Clientset) {
473 client.PrependReactor("get", "deployments", func(clientgotesting.Action) (bool, runtime.Object, error) {
474 return true, nil, errors.New("")
475 })
476 },
477 expectedError: true,
478 },
479 {
480 name: "deployment is not found, create it",
481 setupClient: func(client *clientsetfake.Clientset) {
482 client.PrependReactor("get", "deployments", func(clientgotesting.Action) (bool, runtime.Object, error) {
483 return true, nil, apierrors.NewNotFound(schema.GroupResource{}, "name")
484 })
485 client.PrependReactor("create", "deployments", func(clientgotesting.Action) (bool, runtime.Object, error) {
486 return true, nil, nil
487 })
488 },
489 expectedError: false,
490 },
491 {
492 name: "deployment is not found, create returns an error",
493 setupClient: func(client *clientsetfake.Clientset) {
494 client.PrependReactor("get", "deployments", func(clientgotesting.Action) (bool, runtime.Object, error) {
495 return true, nil, apierrors.NewNotFound(schema.GroupResource{}, "name")
496 })
497 client.PrependReactor("create", "deployments", func(clientgotesting.Action) (bool, runtime.Object, error) {
498 return true, nil, errors.New("")
499 })
500 },
501 expectedError: true,
502 },
503 }
504
505 for _, tc := range tests {
506 t.Run(tc.name, func(t *testing.T) {
507 client := clientsetfake.NewSimpleClientset()
508 tc.setupClient(client)
509 err := CreateOrRetainDeployment(client, &apps.Deployment{}, "some-deployment")
510 if (err != nil) != tc.expectedError {
511 t.Fatalf("expected error: %v, got %v, error: %v", tc.expectedError, err != nil, err)
512 }
513 })
514 }
515 }
516
517 func TestCreateOrUpdateDaemonSet(t *testing.T) {
518 tests := []struct {
519 name string
520 setupClient func(*clientsetfake.Clientset)
521 expectedError bool
522 }{
523 {
524 name: "create daemonset success",
525 setupClient: func(client *clientsetfake.Clientset) {
526 client.PrependReactor("create", "daemonsets", func(clientgotesting.Action) (bool, runtime.Object, error) {
527 return true, nil, nil
528 })
529 },
530 expectedError: false,
531 },
532 {
533 name: "create daemonset returns error",
534 setupClient: func(client *clientsetfake.Clientset) {
535 client.PrependReactor("create", "daemonsets", func(clientgotesting.Action) (bool, runtime.Object, error) {
536 return true, nil, errors.New("unknown error")
537 })
538 },
539 expectedError: true,
540 },
541 {
542 name: "daemonset exists, update it",
543 setupClient: func(client *clientsetfake.Clientset) {
544 client.PrependReactor("create", "daemonsets", func(clientgotesting.Action) (bool, runtime.Object, error) {
545 return true, nil, apierrors.NewAlreadyExists(schema.GroupResource{}, "name")
546 })
547 client.PrependReactor("update", "daemonsets", func(clientgotesting.Action) (bool, runtime.Object, error) {
548 return true, nil, nil
549 })
550 },
551 expectedError: false,
552 },
553 {
554 name: "daemonset exists, update error",
555 setupClient: func(client *clientsetfake.Clientset) {
556 client.PrependReactor("create", "daemonsets", func(clientgotesting.Action) (bool, runtime.Object, error) {
557 return true, nil, apierrors.NewAlreadyExists(schema.GroupResource{}, "name")
558 })
559 client.PrependReactor("update", "daemonsets", func(clientgotesting.Action) (bool, runtime.Object, error) {
560 return true, nil, errors.New("")
561 })
562 },
563 expectedError: true,
564 },
565 }
566
567 for _, tc := range tests {
568 t.Run(tc.name, func(t *testing.T) {
569 client := clientsetfake.NewSimpleClientset()
570 tc.setupClient(client)
571 err := CreateOrUpdateDaemonSet(client, &apps.DaemonSet{})
572 if (err != nil) != tc.expectedError {
573 t.Fatalf("expected error: %v, got %v, error: %v", tc.expectedError, err != nil, err)
574 }
575 })
576 }
577 }
578
579 func TestCreateOrUpdateRole(t *testing.T) {
580 tests := []struct {
581 name string
582 setupClient func(*clientsetfake.Clientset)
583 expectedError bool
584 }{
585 {
586 name: "create role success",
587 setupClient: func(client *clientsetfake.Clientset) {
588 client.PrependReactor("create", "roles", func(clientgotesting.Action) (bool, runtime.Object, error) {
589 return true, nil, nil
590 })
591 },
592 expectedError: false,
593 },
594 {
595 name: "create role returns error",
596 setupClient: func(client *clientsetfake.Clientset) {
597 client.PrependReactor("create", "roles", func(clientgotesting.Action) (bool, runtime.Object, error) {
598 return true, nil, errors.New("unknown error")
599 })
600 },
601 expectedError: true,
602 },
603 {
604 name: "role exists, update it",
605 setupClient: func(client *clientsetfake.Clientset) {
606 client.PrependReactor("create", "roles", func(clientgotesting.Action) (bool, runtime.Object, error) {
607 return true, nil, apierrors.NewAlreadyExists(schema.GroupResource{}, "name")
608 })
609 client.PrependReactor("update", "roles", func(clientgotesting.Action) (bool, runtime.Object, error) {
610 return true, nil, nil
611 })
612 },
613 expectedError: false,
614 },
615 {
616 name: "role exists, update error",
617 setupClient: func(client *clientsetfake.Clientset) {
618 client.PrependReactor("create", "roles", func(clientgotesting.Action) (bool, runtime.Object, error) {
619 return true, nil, apierrors.NewAlreadyExists(schema.GroupResource{}, "name")
620 })
621 client.PrependReactor("update", "roles", func(clientgotesting.Action) (bool, runtime.Object, error) {
622 return true, nil, errors.New("")
623 })
624 },
625 expectedError: true,
626 },
627 }
628
629 for _, tc := range tests {
630 t.Run(tc.name, func(t *testing.T) {
631 client := clientsetfake.NewSimpleClientset()
632 tc.setupClient(client)
633 err := CreateOrUpdateRole(client, &rbac.Role{})
634 if (err != nil) != tc.expectedError {
635 t.Fatalf("expected error: %v, got %v, error: %v", tc.expectedError, err != nil, err)
636 }
637 })
638 }
639 }
640
641 func TestCreateOrUpdateRoleBindings(t *testing.T) {
642 tests := []struct {
643 name string
644 setupClient func(*clientsetfake.Clientset)
645 expectedError bool
646 }{
647 {
648 name: "create rolebinding success",
649 setupClient: func(client *clientsetfake.Clientset) {
650 client.PrependReactor("create", "rolebindings", func(clientgotesting.Action) (bool, runtime.Object, error) {
651 return true, nil, nil
652 })
653 },
654 expectedError: false,
655 },
656 {
657 name: "create rolebinding returns error",
658 setupClient: func(client *clientsetfake.Clientset) {
659 client.PrependReactor("create", "rolebindings", func(clientgotesting.Action) (bool, runtime.Object, error) {
660 return true, nil, errors.New("unknown error")
661 })
662 },
663 expectedError: true,
664 },
665 {
666 name: "rolebinding exists, update it",
667 setupClient: func(client *clientsetfake.Clientset) {
668 client.PrependReactor("create", "rolebindings", func(clientgotesting.Action) (bool, runtime.Object, error) {
669 return true, nil, apierrors.NewAlreadyExists(schema.GroupResource{}, "name")
670 })
671 client.PrependReactor("update", "rolebindings", func(clientgotesting.Action) (bool, runtime.Object, error) {
672 return true, nil, nil
673 })
674 },
675 expectedError: false,
676 },
677 {
678 name: "rolebinding exists, update error",
679 setupClient: func(client *clientsetfake.Clientset) {
680 client.PrependReactor("create", "rolebindings", func(clientgotesting.Action) (bool, runtime.Object, error) {
681 return true, nil, apierrors.NewAlreadyExists(schema.GroupResource{}, "name")
682 })
683 client.PrependReactor("update", "rolebindings", func(clientgotesting.Action) (bool, runtime.Object, error) {
684 return true, nil, errors.New("")
685 })
686 },
687 expectedError: true,
688 },
689 }
690
691 for _, tc := range tests {
692 t.Run(tc.name, func(t *testing.T) {
693 client := clientsetfake.NewSimpleClientset()
694 tc.setupClient(client)
695 err := CreateOrUpdateRoleBinding(client, &rbac.RoleBinding{})
696 if (err != nil) != tc.expectedError {
697 t.Fatalf("expected error: %v, got %v, error: %v", tc.expectedError, err != nil, err)
698 }
699 })
700 }
701 }
702
703 func TestCreateOrUpdateClusterRole(t *testing.T) {
704 tests := []struct {
705 name string
706 setupClient func(*clientsetfake.Clientset)
707 expectedError bool
708 }{
709 {
710 name: "create clusterrole success",
711 setupClient: func(client *clientsetfake.Clientset) {
712 client.PrependReactor("create", "clusterroles", func(clientgotesting.Action) (bool, runtime.Object, error) {
713 return true, nil, nil
714 })
715 },
716 expectedError: false,
717 },
718 {
719 name: "create clusterrole returns error",
720 setupClient: func(client *clientsetfake.Clientset) {
721 client.PrependReactor("create", "clusterroles", func(clientgotesting.Action) (bool, runtime.Object, error) {
722 return true, nil, errors.New("unknown error")
723 })
724 },
725 expectedError: true,
726 },
727 {
728 name: "clusterrole exists, update it",
729 setupClient: func(client *clientsetfake.Clientset) {
730 client.PrependReactor("create", "clusterroles", func(clientgotesting.Action) (bool, runtime.Object, error) {
731 return true, nil, apierrors.NewAlreadyExists(schema.GroupResource{}, "name")
732 })
733 client.PrependReactor("update", "clusterroles", func(clientgotesting.Action) (bool, runtime.Object, error) {
734 return true, nil, nil
735 })
736 },
737 expectedError: false,
738 },
739 {
740 name: "clusterrole exists, update error",
741 setupClient: func(client *clientsetfake.Clientset) {
742 client.PrependReactor("create", "clusterroles", func(clientgotesting.Action) (bool, runtime.Object, error) {
743 return true, nil, apierrors.NewAlreadyExists(schema.GroupResource{}, "name")
744 })
745 client.PrependReactor("update", "clusterroles", func(clientgotesting.Action) (bool, runtime.Object, error) {
746 return true, nil, errors.New("")
747 })
748 },
749 expectedError: true,
750 },
751 }
752
753 for _, tc := range tests {
754 t.Run(tc.name, func(t *testing.T) {
755 client := clientsetfake.NewSimpleClientset()
756 tc.setupClient(client)
757 err := CreateOrUpdateClusterRole(client, &rbac.ClusterRole{})
758 if (err != nil) != tc.expectedError {
759 t.Fatalf("expected error: %v, got %v, error: %v", tc.expectedError, err != nil, err)
760 }
761 })
762 }
763 }
764
765 func TestCreateOrUpdateClusterRoleBindings(t *testing.T) {
766 tests := []struct {
767 name string
768 setupClient func(*clientsetfake.Clientset)
769 expectedError bool
770 }{
771 {
772 name: "create clusterrolebinding success",
773 setupClient: func(client *clientsetfake.Clientset) {
774 client.PrependReactor("create", "clusterrolebindings", func(clientgotesting.Action) (bool, runtime.Object, error) {
775 return true, nil, nil
776 })
777 },
778 expectedError: false,
779 },
780 {
781 name: "create clusterrolebinding returns error",
782 setupClient: func(client *clientsetfake.Clientset) {
783 client.PrependReactor("create", "clusterrolebindings", func(clientgotesting.Action) (bool, runtime.Object, error) {
784 return true, nil, errors.New("unknown error")
785 })
786 },
787 expectedError: true,
788 },
789 {
790 name: "clusterrolebinding exists, update it",
791 setupClient: func(client *clientsetfake.Clientset) {
792 client.PrependReactor("create", "clusterrolebindings", func(clientgotesting.Action) (bool, runtime.Object, error) {
793 return true, nil, apierrors.NewAlreadyExists(schema.GroupResource{}, "name")
794 })
795 client.PrependReactor("update", "clusterrolebindings", func(clientgotesting.Action) (bool, runtime.Object, error) {
796 return true, nil, nil
797 })
798 },
799 expectedError: false,
800 },
801 {
802 name: "clusterrolebinding exists, update error",
803 setupClient: func(client *clientsetfake.Clientset) {
804 client.PrependReactor("create", "clusterrolebindings", func(clientgotesting.Action) (bool, runtime.Object, error) {
805 return true, nil, apierrors.NewAlreadyExists(schema.GroupResource{}, "name")
806 })
807 client.PrependReactor("update", "clusterrolebindings", func(clientgotesting.Action) (bool, runtime.Object, error) {
808 return true, nil, errors.New("")
809 })
810 },
811 expectedError: true,
812 },
813 }
814
815 for _, tc := range tests {
816 t.Run(tc.name, func(t *testing.T) {
817 client := clientsetfake.NewSimpleClientset()
818 tc.setupClient(client)
819 err := CreateOrUpdateClusterRoleBinding(client, &rbac.ClusterRoleBinding{})
820 if (err != nil) != tc.expectedError {
821 t.Fatalf("expected error: %v, got %v, error: %v", tc.expectedError, err != nil, err)
822 }
823 })
824 }
825 }
826
827 func TestPatchNodeOnce(t *testing.T) {
828 testcases := []struct {
829 name string
830 lookupName string
831 node v1.Node
832 success bool
833 fakeError error
834 }{
835 {
836 name: "simple update",
837 lookupName: "testnode",
838 node: v1.Node{
839 ObjectMeta: metav1.ObjectMeta{
840 Name: "testnode",
841 Labels: map[string]string{v1.LabelHostname: ""},
842 },
843 },
844 success: true,
845 },
846 {
847 name: "node does not exist",
848 lookupName: "whale",
849 success: false,
850 },
851 {
852 name: "node not labelled yet",
853 lookupName: "robin",
854 node: v1.Node{
855 ObjectMeta: metav1.ObjectMeta{
856 Name: "robin",
857 },
858 },
859 success: false,
860 },
861 {
862 name: "patch node when timeout",
863 lookupName: "testnode",
864 node: v1.Node{
865 ObjectMeta: metav1.ObjectMeta{
866 Name: "testnode",
867 Labels: map[string]string{v1.LabelHostname: ""},
868 },
869 },
870 success: false,
871 fakeError: apierrors.NewTimeoutError("fake timeout", -1),
872 },
873 {
874 name: "patch node when conflict",
875 lookupName: "testnode",
876 node: v1.Node{
877 ObjectMeta: metav1.ObjectMeta{
878 Name: "testnode",
879 Labels: map[string]string{v1.LabelHostname: ""},
880 },
881 },
882 success: false,
883 fakeError: apierrors.NewConflict(schema.GroupResource{}, "fake conflict", nil),
884 },
885 {
886 name: "patch node when there is a server timeout",
887 lookupName: "testnode",
888 node: v1.Node{
889 ObjectMeta: metav1.ObjectMeta{
890 Name: "testnode",
891 Labels: map[string]string{v1.LabelHostname: ""},
892 },
893 },
894 success: false,
895 fakeError: apierrors.NewServerTimeout(schema.GroupResource{}, "fake server timeout", 1),
896 },
897 {
898 name: "patch node when the service is unavailable",
899 lookupName: "testnode",
900 node: v1.Node{
901 ObjectMeta: metav1.ObjectMeta{
902 Name: "testnode",
903 Labels: map[string]string{v1.LabelHostname: ""},
904 },
905 },
906 success: false,
907 fakeError: apierrors.NewServiceUnavailable("fake service unavailable"),
908 },
909 {
910 name: "patch node failed with unknown error",
911 lookupName: "testnode",
912 node: v1.Node{
913 ObjectMeta: metav1.ObjectMeta{
914 Name: "testnode",
915 Labels: map[string]string{v1.LabelHostname: ""},
916 },
917 },
918 success: false,
919 fakeError: errors.New("unknown error"),
920 },
921 }
922
923 for _, tc := range testcases {
924 t.Run(tc.name, func(t *testing.T) {
925 client := clientsetfake.NewSimpleClientset()
926 _, err := client.CoreV1().Nodes().Create(context.Background(), &tc.node, metav1.CreateOptions{})
927 if err != nil {
928 t.Fatalf("failed to create node to fake client: %v", err)
929 }
930 if tc.fakeError != nil {
931 client.PrependReactor("patch", "nodes", func(action clientgotesting.Action) (handled bool, ret runtime.Object, err error) {
932 return true, nil, tc.fakeError
933 })
934 }
935 var lastError error
936 conditionFunction := PatchNodeOnce(client, tc.lookupName, func(node *v1.Node) {
937 node.Annotations = map[string]string{
938 "updatedBy": "test",
939 }
940 }, &lastError)
941 success, err := conditionFunction(context.Background())
942 if err != nil && tc.success {
943 t.Fatalf("did not expect error: %v", err)
944 }
945 if success != tc.success {
946 t.Fatalf("expected %v got %v", tc.success, success)
947 }
948 })
949 }
950 }
951
952 func TestPatchNode(t *testing.T) {
953 tests := []struct {
954 name string
955 setupClient func(*clientsetfake.Clientset)
956 expectedError bool
957 }{
958 {
959 name: "success",
960 setupClient: func(client *clientsetfake.Clientset) {
961 client.PrependReactor("get", "nodes", func(clientgotesting.Action) (bool, runtime.Object, error) {
962 return true, &v1.Node{
963 ObjectMeta: metav1.ObjectMeta{
964 Name: "some-node",
965 Labels: map[string]string{v1.LabelHostname: ""},
966 },
967 }, nil
968 })
969 client.PrependReactor("patch", "nodes", func(clientgotesting.Action) (bool, runtime.Object, error) {
970 return true, nil, nil
971 })
972 },
973 expectedError: false,
974 },
975 {
976 name: "error",
977 setupClient: func(client *clientsetfake.Clientset) {
978 client.PrependReactor("get", "nodes", func(clientgotesting.Action) (bool, runtime.Object, error) {
979 return true, nil, errors.New("unknown error")
980 })
981 },
982 expectedError: true,
983 },
984 }
985
986 for _, tc := range tests {
987 t.Run(tc.name, func(t *testing.T) {
988 client := clientsetfake.NewSimpleClientset()
989 tc.setupClient(client)
990 patchFn := func(*v1.Node) {}
991 err := PatchNode(client, "some-node", patchFn)
992 if (err != nil) != tc.expectedError {
993 t.Fatalf("expected error: %v, got %v, error: %v", tc.expectedError, err != nil, err)
994 }
995 })
996 }
997 }
998
999 func TestGetConfigMapWithShortRetry(t *testing.T) {
1000 expectedConfigMap := &v1.ConfigMap{
1001 ObjectMeta: metav1.ObjectMeta{
1002 Namespace: "ns",
1003 Name: "some-cm",
1004 },
1005 }
1006 tests := []struct {
1007 name string
1008 setupClient func(*clientsetfake.Clientset)
1009 expectedConfigMap *v1.ConfigMap
1010 expectedError bool
1011 }{
1012 {
1013 name: "configmap exists",
1014 setupClient: func(client *clientsetfake.Clientset) {
1015 client.PrependReactor("get", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
1016 return true, expectedConfigMap, nil
1017 })
1018 },
1019 expectedConfigMap: expectedConfigMap,
1020 expectedError: false,
1021 },
1022 {
1023 name: "configmap get returns an error",
1024 setupClient: func(client *clientsetfake.Clientset) {
1025 client.PrependReactor("get", "configmaps", func(clientgotesting.Action) (bool, runtime.Object, error) {
1026 return true, nil, errors.New("")
1027 })
1028 },
1029 expectedError: true,
1030 },
1031 }
1032
1033 for _, tc := range tests {
1034 t.Run(tc.name, func(t *testing.T) {
1035 client := clientsetfake.NewSimpleClientset()
1036 tc.setupClient(client)
1037 actual, err := GetConfigMapWithShortRetry(client, "ns", "some-cm")
1038 if (err != nil) != tc.expectedError {
1039 t.Fatalf("expected error: %v, got %v, error: %v", tc.expectedError, err != nil, err)
1040 }
1041 if err != nil {
1042 return
1043 }
1044 diff := cmp.Diff(tc.expectedConfigMap, actual)
1045 if len(diff) > 0 {
1046 t.Fatalf("got a diff with the expected config (-want,+got):\n%s", diff)
1047 }
1048 })
1049 }
1050 }
1051
View as plain text