k8s.io/kubernetes@v1.29.3/pkg/client/tests/fake_client_test.go (about) 1 /* 2 Copyright 2016 The Kubernetes 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 tests 18 19 import ( 20 "context" 21 "testing" 22 23 corev1 "k8s.io/api/core/v1" 24 metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" 25 clientsetfake "k8s.io/client-go/kubernetes/fake" 26 27 _ "k8s.io/kubernetes/pkg/apis/core/install" 28 ) 29 30 func TestFakeClientSetFiltering(t *testing.T) { 31 tc := clientsetfake.NewSimpleClientset( 32 testPod("nsA", "pod-1"), 33 testPod("nsB", "pod-2"), 34 testSA("nsA", "sa-1"), 35 testSA("nsA", "sa-2"), 36 testSA("nsB", "sa-1"), 37 testSA("nsB", "sa-2"), 38 testSA("nsB", "sa-3"), 39 ) 40 41 saList1, err := tc.CoreV1().ServiceAccounts("nsA").List(context.TODO(), metav1.ListOptions{}) 42 if err != nil { 43 t.Fatalf("ServiceAccounts.List: %s", err) 44 } 45 if actual, expected := len(saList1.Items), 2; expected != actual { 46 t.Fatalf("Expected %d records to match, got %d", expected, actual) 47 } 48 for _, sa := range saList1.Items { 49 if sa.Namespace != "nsA" { 50 t.Fatalf("Expected namespace %q; got %q", "nsA", sa.Namespace) 51 } 52 } 53 54 saList2, err := tc.CoreV1().ServiceAccounts("nsB").List(context.TODO(), metav1.ListOptions{}) 55 if err != nil { 56 t.Fatalf("ServiceAccounts.List: %s", err) 57 } 58 if actual, expected := len(saList2.Items), 3; expected != actual { 59 t.Fatalf("Expected %d records to match, got %d", expected, actual) 60 } 61 for _, sa := range saList2.Items { 62 if sa.Namespace != "nsB" { 63 t.Fatalf("Expected namespace %q; got %q", "nsA", sa.Namespace) 64 } 65 } 66 67 pod1, err := tc.CoreV1().Pods("nsA").Get(context.TODO(), "pod-1", metav1.GetOptions{}) 68 if err != nil { 69 t.Fatalf("Pods.Get: %s", err) 70 } 71 if pod1 == nil { 72 t.Fatalf("Expected to find pod nsA/pod-1 but it wasn't found") 73 } 74 if pod1.Namespace != "nsA" || pod1.Name != "pod-1" { 75 t.Fatalf("Expected to find pod nsA/pod-1t, got %s/%s", pod1.Namespace, pod1.Name) 76 } 77 78 wrongPod, err := tc.CoreV1().Pods("nsB").Get(context.TODO(), "pod-1", metav1.GetOptions{}) 79 if err == nil { 80 t.Fatalf("Pods.Get: expected nsB/pod-1 not to match, but it matched %s/%s", wrongPod.Namespace, wrongPod.Name) 81 } 82 83 allPods, err := tc.CoreV1().Pods(metav1.NamespaceAll).List(context.TODO(), metav1.ListOptions{}) 84 if err != nil { 85 t.Fatalf("Pods.List: %s", err) 86 } 87 if actual, expected := len(allPods.Items), 2; expected != actual { 88 t.Fatalf("Expected %d pods to match, got %d", expected, actual) 89 } 90 91 allSAs, err := tc.CoreV1().ServiceAccounts(metav1.NamespaceAll).List(context.TODO(), metav1.ListOptions{}) 92 if err != nil { 93 t.Fatalf("ServiceAccounts.List: %s", err) 94 } 95 if actual, expected := len(allSAs.Items), 5; expected != actual { 96 t.Fatalf("Expected %d service accounts to match, got %d", expected, actual) 97 } 98 } 99 100 func TestFakeClientsetInheritsNamespace(t *testing.T) { 101 tc := clientsetfake.NewSimpleClientset( 102 testNamespace("nsA"), 103 testPod("nsA", "pod-1"), 104 ) 105 106 _, err := tc.CoreV1().Namespaces().Create(context.TODO(), testNamespace("nsB"), metav1.CreateOptions{}) 107 if err != nil { 108 t.Fatalf("Namespaces.Create: %s", err) 109 } 110 111 allNS, err := tc.CoreV1().Namespaces().List(context.TODO(), metav1.ListOptions{}) 112 if err != nil { 113 t.Fatalf("Namespaces.List: %s", err) 114 } 115 if actual, expected := len(allNS.Items), 2; expected != actual { 116 t.Fatalf("Expected %d namespaces to match, got %d", expected, actual) 117 } 118 119 _, err = tc.CoreV1().Pods("nsB").Create(context.TODO(), testPod("", "pod-1"), metav1.CreateOptions{}) 120 if err != nil { 121 t.Fatalf("Pods.Create nsB/pod-1: %s", err) 122 } 123 124 podB1, err := tc.CoreV1().Pods("nsB").Get(context.TODO(), "pod-1", metav1.GetOptions{}) 125 if err != nil { 126 t.Fatalf("Pods.Get nsB/pod-1: %s", err) 127 } 128 if podB1 == nil { 129 t.Fatalf("Expected to find pod nsB/pod-1 but it wasn't found") 130 } 131 if podB1.Namespace != "nsB" || podB1.Name != "pod-1" { 132 t.Fatalf("Expected to find pod nsB/pod-1t, got %s/%s", podB1.Namespace, podB1.Name) 133 } 134 135 _, err = tc.CoreV1().Pods("nsA").Create(context.TODO(), testPod("", "pod-1"), metav1.CreateOptions{}) 136 if err == nil { 137 t.Fatalf("Expected Pods.Create to fail with already exists error") 138 } 139 140 _, err = tc.CoreV1().Pods("nsA").Update(context.TODO(), testPod("", "pod-1"), metav1.UpdateOptions{}) 141 if err != nil { 142 t.Fatalf("Pods.Update nsA/pod-1: %s", err) 143 } 144 145 _, err = tc.CoreV1().Pods("nsA").Create(context.TODO(), testPod("nsB", "pod-2"), metav1.CreateOptions{}) 146 if err == nil { 147 t.Fatalf("Expected Pods.Create to fail with bad request from namespace mismtach") 148 } 149 if err.Error() != `request namespace does not match object namespace, request: "nsA" object: "nsB"` { 150 t.Fatalf("Expected Pods.Create error to provide object and request namespaces, got %q", err) 151 } 152 153 _, err = tc.CoreV1().Pods("nsA").Update(context.TODO(), testPod("", "pod-3"), metav1.UpdateOptions{}) 154 if err == nil { 155 t.Fatalf("Expected Pods.Update nsA/pod-3 to fail with not found error") 156 } 157 } 158 159 func testSA(ns, name string) *corev1.ServiceAccount { 160 return &corev1.ServiceAccount{ 161 ObjectMeta: metav1.ObjectMeta{ 162 Namespace: ns, 163 Name: name, 164 }, 165 } 166 } 167 168 func testPod(ns, name string) *corev1.Pod { 169 return &corev1.Pod{ 170 ObjectMeta: metav1.ObjectMeta{ 171 Namespace: ns, 172 Name: name, 173 }, 174 } 175 } 176 177 func testNamespace(ns string) *corev1.Namespace { 178 return &corev1.Namespace{ 179 ObjectMeta: metav1.ObjectMeta{ 180 Name: ns, 181 }, 182 } 183 }