1
16
17 package integration
18
19 import (
20 "context"
21 "strings"
22 "testing"
23
24 "github.com/stretchr/testify/assert"
25
26 apiextensionsv1 "k8s.io/apiextensions-apiserver/pkg/apis/apiextensions/v1"
27 "k8s.io/apiextensions-apiserver/test/integration/fixtures"
28 apierrors "k8s.io/apimachinery/pkg/api/errors"
29 metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
30 "k8s.io/apimachinery/pkg/apis/meta/v1/unstructured"
31 "k8s.io/apimachinery/pkg/runtime/schema"
32 "k8s.io/apimachinery/pkg/types"
33 "k8s.io/client-go/dynamic"
34 )
35
36 func TestHandlerScope(t *testing.T) {
37 tearDown, apiExtensionClient, dynamicClient, err := fixtures.StartDefaultServerWithClients(t)
38 if err != nil {
39 t.Fatal(err)
40 }
41 defer tearDown()
42
43 for _, scope := range []apiextensionsv1.ResourceScope{apiextensionsv1.ClusterScoped, apiextensionsv1.NamespaceScoped} {
44 t.Run(string(scope), func(t *testing.T) {
45
46 crd := &apiextensionsv1.CustomResourceDefinition{
47 ObjectMeta: metav1.ObjectMeta{
48 Name: strings.ToLower(string(scope)) + "s.test.apiextensions-apiserver.k8s.io",
49 Annotations: map[string]string{"api-approved.kubernetes.io": "unapproved, test-only"},
50 },
51 Spec: apiextensionsv1.CustomResourceDefinitionSpec{
52 Group: "test.apiextensions-apiserver.k8s.io",
53 Versions: []apiextensionsv1.CustomResourceDefinitionVersion{
54 {
55 Name: "v1beta1",
56 Served: true,
57 Storage: true,
58 Subresources: &apiextensionsv1.CustomResourceSubresources{
59 Status: &apiextensionsv1.CustomResourceSubresourceStatus{},
60 Scale: &apiextensionsv1.CustomResourceSubresourceScale{
61 SpecReplicasPath: ".spec.replicas",
62 StatusReplicasPath: ".status.replicas",
63 },
64 },
65 Schema: fixtures.AllowAllSchema(),
66 },
67 },
68 Names: apiextensionsv1.CustomResourceDefinitionNames{
69 Plural: strings.ToLower(string(scope)) + "s",
70 Singular: strings.ToLower(string(scope)),
71 Kind: string(scope),
72 ListKind: string(scope) + "List",
73 },
74 Scope: scope,
75 },
76 }
77 crd, err = fixtures.CreateNewV1CustomResourceDefinition(crd, apiExtensionClient, dynamicClient)
78 if err != nil {
79 t.Fatal(err)
80 }
81
82 gvr := schema.GroupVersionResource{Group: crd.Spec.Group, Version: crd.Spec.Versions[0].Name, Resource: crd.Spec.Names.Plural}
83
84 ns := "test"
85 var client dynamic.ResourceInterface = dynamicClient.Resource(gvr)
86 var otherScopeClient dynamic.ResourceInterface = dynamicClient.Resource(gvr).Namespace(ns)
87 if crd.Spec.Scope == apiextensionsv1.NamespaceScoped {
88 client, otherScopeClient = otherScopeClient, client
89 }
90
91 name := "bar"
92 cr := &unstructured.Unstructured{
93 Object: map[string]interface{}{
94 "kind": crd.Spec.Names.Kind,
95 "apiVersion": gvr.GroupVersion().String(),
96 "metadata": map[string]interface{}{
97 "name": name,
98 },
99 },
100 }
101
102 _, err := otherScopeClient.Create(context.TODO(), cr, metav1.CreateOptions{})
103 assert.True(t, apierrors.IsNotFound(err))
104
105 _, err = otherScopeClient.Create(context.TODO(), cr, metav1.CreateOptions{}, "status")
106 assert.True(t, apierrors.IsNotFound(err))
107
108 _, err = otherScopeClient.Create(context.TODO(), cr, metav1.CreateOptions{}, "scale")
109 assert.True(t, apierrors.IsNotFound(err))
110
111 _, err = client.Create(context.TODO(), cr, metav1.CreateOptions{})
112 assert.NoError(t, err)
113
114 _, err = otherScopeClient.Get(context.TODO(), name, metav1.GetOptions{})
115 assert.True(t, apierrors.IsNotFound(err))
116
117 _, err = otherScopeClient.Get(context.TODO(), name, metav1.GetOptions{}, "status")
118 assert.True(t, apierrors.IsNotFound(err))
119
120 _, err = otherScopeClient.Get(context.TODO(), name, metav1.GetOptions{}, "scale")
121 assert.True(t, apierrors.IsNotFound(err))
122
123 _, err = otherScopeClient.Update(context.TODO(), cr, metav1.UpdateOptions{})
124 assert.True(t, apierrors.IsNotFound(err))
125
126 _, err = otherScopeClient.Update(context.TODO(), cr, metav1.UpdateOptions{}, "status")
127 assert.True(t, apierrors.IsNotFound(err))
128
129 _, err = otherScopeClient.Update(context.TODO(), cr, metav1.UpdateOptions{}, "scale")
130 assert.True(t, apierrors.IsNotFound(err))
131
132 _, err = otherScopeClient.Patch(context.TODO(), name, types.MergePatchType, []byte(`{"metadata":{"annotations":{"test":"1"}}}`), metav1.PatchOptions{})
133 assert.True(t, apierrors.IsNotFound(err))
134
135 _, err = otherScopeClient.Patch(context.TODO(), name, types.MergePatchType, []byte(`{"metadata":{"annotations":{"test":"1"}}}`), metav1.PatchOptions{}, "status")
136 assert.True(t, apierrors.IsNotFound(err))
137
138 _, err = otherScopeClient.Patch(context.TODO(), name, types.MergePatchType, []byte(`{"metadata":{"annotations":{"test":"1"}}}`), metav1.PatchOptions{}, "scale")
139 assert.True(t, apierrors.IsNotFound(err))
140
141 err = otherScopeClient.Delete(context.TODO(), name, metav1.DeleteOptions{})
142 assert.True(t, apierrors.IsNotFound(err))
143
144 err = otherScopeClient.Delete(context.TODO(), name, metav1.DeleteOptions{}, "status")
145 assert.True(t, apierrors.IsNotFound(err))
146
147 err = otherScopeClient.Delete(context.TODO(), name, metav1.DeleteOptions{}, "scale")
148 assert.True(t, apierrors.IsNotFound(err))
149
150 err = otherScopeClient.DeleteCollection(context.TODO(), metav1.DeleteOptions{}, metav1.ListOptions{})
151 assert.True(t, apierrors.IsNotFound(err))
152
153 if scope == apiextensionsv1.ClusterScoped {
154 _, err = otherScopeClient.List(context.TODO(), metav1.ListOptions{})
155 assert.True(t, apierrors.IsNotFound(err))
156
157 _, err = otherScopeClient.Watch(context.TODO(), metav1.ListOptions{})
158 assert.True(t, apierrors.IsNotFound(err))
159 } else {
160 _, err = otherScopeClient.List(context.TODO(), metav1.ListOptions{})
161 assert.NoError(t, err)
162
163 w, err := otherScopeClient.Watch(context.TODO(), metav1.ListOptions{})
164 assert.NoError(t, err)
165 if w != nil {
166 w.Stop()
167 }
168 }
169 })
170 }
171 }
172
View as plain text