github.com/GoogleContainerTools/skaffold/v2@v2.13.2/pkg/diag/validator/config_connector_test.go (about) 1 /* 2 Copyright 2021 The Skaffold Authors 3 4 Licensed under the Apache License, Version 2.0 (the "License"); 5 you may not use this file except in compliance with the License. 6 You may obtain a copy of the License at 7 8 http://www.apache.org/licenses/LICENSE-2.0 9 10 Unless required by applicable law or agreed to in writing, software 11 distributed under the License is distributed on an "AS IS" BASIS, 12 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 See the License for the specific language governing permissions and 14 limitations under the License. 15 */ 16 17 package validator 18 19 import ( 20 "context" 21 "fmt" 22 "testing" 23 24 "github.com/google/go-cmp/cmp" 25 "google.golang.org/protobuf/testing/protocmp" 26 metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" 27 "k8s.io/apimachinery/pkg/apis/meta/v1/unstructured" 28 "k8s.io/apimachinery/pkg/runtime/schema" 29 fakedynclient "k8s.io/client-go/dynamic/fake" 30 fakeclient "k8s.io/client-go/kubernetes/fake" 31 "k8s.io/kubectl/pkg/scheme" 32 33 "github.com/GoogleContainerTools/skaffold/v2/proto/v1" 34 "github.com/GoogleContainerTools/skaffold/v2/testutil" 35 ) 36 37 func TestConfigConnectorValidator(t *testing.T) { 38 tests := []struct { 39 description string 40 status map[string]interface{} 41 expected []Resource 42 }{ 43 { 44 description: "resource ready", 45 status: map[string]interface{}{ 46 "status": "True", 47 "type": "Ready", 48 }, 49 expected: []Resource{ 50 { 51 kind: "bar", 52 name: "foo1", 53 status: "Current", 54 ae: &proto.ActionableErr{ErrCode: proto.StatusCode_STATUSCHECK_SUCCESS}, 55 }, 56 }, 57 }, 58 { 59 description: "resource in progress with message", 60 status: map[string]interface{}{ 61 "status": "False", 62 "type": "Ready", 63 "message": "waiting on dependency", 64 }, 65 expected: []Resource{ 66 { 67 kind: "bar", 68 name: "foo1", 69 status: "InProgress", 70 ae: &proto.ActionableErr{ErrCode: proto.StatusCode_STATUSCHECK_CONFIG_CONNECTOR_IN_PROGRESS, Message: "waiting on dependency"}, 71 }, 72 }, 73 }, 74 { 75 description: "resource in progress without message", 76 status: map[string]interface{}{ 77 "status": "False", 78 "type": "Ready", 79 }, 80 expected: []Resource{ 81 { 82 kind: "bar", 83 name: "foo1", 84 status: "InProgress", 85 ae: &proto.ActionableErr{ErrCode: proto.StatusCode_STATUSCHECK_CONFIG_CONNECTOR_IN_PROGRESS}, 86 }, 87 }, 88 }, 89 } 90 91 for _, test := range tests { 92 testutil.Run(t, test.description, func(t *testutil.T) { 93 targetGvk := schema.GroupVersionKind{Version: "foo", Kind: "bar"} 94 obj := []map[string]interface{}{ 95 { 96 "kind": "bar", 97 "apiVersion": "foo", 98 "metadata": map[string]interface{}{"name": "foo1"}, 99 "status": map[string]interface{}{ 100 "conditions": []interface{}{ 101 test.status, 102 }, 103 }, 104 }, 105 } 106 res := &unstructured.UnstructuredList{} 107 gvrs := map[schema.GroupVersionResource]string{} 108 for _, item := range obj { 109 obj := unstructured.Unstructured{Object: item} 110 gvk := obj.GroupVersionKind() 111 res.Items = append(res.Items, obj) 112 gvr := schema.GroupVersionResource{Group: gvk.Group, Version: gvk.Version, Resource: fmt.Sprintf("%ss", gvk.Kind)} 113 gvrs[gvr] = gvk.Kind + "List" 114 } 115 116 // Mock Kubernetes 117 client := fakeclient.NewSimpleClientset(res) 118 dynClient := fakedynclient.NewSimpleDynamicClientWithCustomListKinds(scheme.Scheme, gvrs, res) 119 for _, item := range res.Items { 120 gvk := item.GroupVersionKind() 121 client.Resources = append(client.Resources, &metav1.APIResourceList{ 122 GroupVersion: item.GetObjectKind().GroupVersionKind().GroupVersion().String(), 123 APIResources: []metav1.APIResource{{ 124 Kind: gvk.Kind, 125 Version: gvk.Version, 126 Group: gvk.Group, 127 128 Name: fmt.Sprintf("%ss", gvk.Kind), 129 }}, 130 }) 131 dynClient.Resources = append(dynClient.Resources, &metav1.APIResourceList{ 132 GroupVersion: item.GetObjectKind().GroupVersionKind().GroupVersion().String(), 133 APIResources: []metav1.APIResource{{ 134 Kind: item.GetObjectKind().GroupVersionKind().String(), 135 Name: item.GetName(), 136 }}, 137 }) 138 client.Tracker().Add(&item) 139 } 140 v := NewConfigConnectorValidator(client, dynClient, targetGvk) 141 r, err := v.Validate(context.Background(), "", metav1.ListOptions{}) 142 t.CheckNoError(err) 143 144 t.CheckDeepEqual(test.expected, r, cmp.AllowUnexported(Resource{}), cmp.Comparer(func(x, y error) bool { 145 if x == nil && y == nil { 146 return true 147 } else if x != nil && y != nil { 148 return x.Error() == y.Error() 149 } 150 return false 151 }), protocmp.Transform()) 152 }) 153 } 154 }