Skip to content

Commit dba49e6

Browse files
authored
Merge pull request kubernetes#72249 from liggitt/resource-runtime-config
Allow enabling/disabling specific extensions/v1beta1 resources
2 parents a7cb03f + e016e13 commit dba49e6

File tree

6 files changed

+258
-27
lines changed

6 files changed

+258
-27
lines changed

pkg/master/master.go

Lines changed: 18 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -474,8 +474,6 @@ func DefaultAPIResourceConfigSource() *serverstorage.ResourceConfig {
474474
ret.EnableVersions(
475475
admissionregistrationv1beta1.SchemeGroupVersion,
476476
apiv1.SchemeGroupVersion,
477-
appsv1beta1.SchemeGroupVersion,
478-
appsv1beta2.SchemeGroupVersion,
479477
appsv1.SchemeGroupVersion,
480478
authenticationv1.SchemeGroupVersion,
481479
authenticationv1beta1.SchemeGroupVersion,
@@ -499,6 +497,24 @@ func DefaultAPIResourceConfigSource() *serverstorage.ResourceConfig {
499497
storageapiv1beta1.SchemeGroupVersion,
500498
schedulingapiv1beta1.SchemeGroupVersion,
501499
)
500+
// enable non-deprecated beta resources in extensions/v1beta1 explicitly so we have a full list of what's possible to serve
501+
ret.EnableResources(
502+
extensionsapiv1beta1.SchemeGroupVersion.WithResource("ingresses"),
503+
)
504+
// enable deprecated beta resources in extensions/v1beta1 explicitly so we have a full list of what's possible to serve
505+
ret.EnableResources(
506+
extensionsapiv1beta1.SchemeGroupVersion.WithResource("daemonsets"),
507+
extensionsapiv1beta1.SchemeGroupVersion.WithResource("deployments"),
508+
extensionsapiv1beta1.SchemeGroupVersion.WithResource("networkpolicies"),
509+
extensionsapiv1beta1.SchemeGroupVersion.WithResource("podsecuritypolicies"),
510+
extensionsapiv1beta1.SchemeGroupVersion.WithResource("replicasets"),
511+
extensionsapiv1beta1.SchemeGroupVersion.WithResource("replicationcontrollers"),
512+
)
513+
// enable deprecated beta versions explicitly so we have a full list of what's possible to serve
514+
ret.EnableVersions(
515+
appsv1beta1.SchemeGroupVersion,
516+
appsv1beta2.SchemeGroupVersion,
517+
)
502518
// disable alpha versions explicitly so we have a full list of what's possible to serve
503519
ret.DisableVersions(
504520
auditregistrationv1alpha1.SchemeGroupVersion,

pkg/registry/extensions/rest/storage_extensions.go

Lines changed: 36 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -52,39 +52,53 @@ func (p RESTStorageProvider) v1beta1Storage(apiResourceConfigSource serverstorag
5252

5353
// This is a dummy replication controller for scale subresource purposes.
5454
// TODO: figure out how to enable this only if needed as a part of scale subresource GA.
55-
controllerStorage := expcontrollerstore.NewStorage(restOptionsGetter)
56-
storage["replicationcontrollers"] = controllerStorage.ReplicationController
57-
storage["replicationcontrollers/scale"] = controllerStorage.Scale
55+
if apiResourceConfigSource.ResourceEnabled(extensionsapiv1beta1.SchemeGroupVersion.WithResource("replicationcontrollers")) {
56+
controllerStorage := expcontrollerstore.NewStorage(restOptionsGetter)
57+
storage["replicationcontrollers"] = controllerStorage.ReplicationController
58+
storage["replicationcontrollers/scale"] = controllerStorage.Scale
59+
}
5860

5961
// daemonsets
60-
daemonSetStorage, daemonSetStatusStorage := daemonstore.NewREST(restOptionsGetter)
61-
storage["daemonsets"] = daemonSetStorage.WithCategories(nil)
62-
storage["daemonsets/status"] = daemonSetStatusStorage
62+
if apiResourceConfigSource.ResourceEnabled(extensionsapiv1beta1.SchemeGroupVersion.WithResource("daemonsets")) {
63+
daemonSetStorage, daemonSetStatusStorage := daemonstore.NewREST(restOptionsGetter)
64+
storage["daemonsets"] = daemonSetStorage.WithCategories(nil)
65+
storage["daemonsets/status"] = daemonSetStatusStorage
66+
}
6367

6468
//deployments
65-
deploymentStorage := deploymentstore.NewStorage(restOptionsGetter)
66-
storage["deployments"] = deploymentStorage.Deployment.WithCategories(nil)
67-
storage["deployments/status"] = deploymentStorage.Status
68-
storage["deployments/rollback"] = deploymentStorage.Rollback
69-
storage["deployments/scale"] = deploymentStorage.Scale
69+
if apiResourceConfigSource.ResourceEnabled(extensionsapiv1beta1.SchemeGroupVersion.WithResource("deployments")) {
70+
deploymentStorage := deploymentstore.NewStorage(restOptionsGetter)
71+
storage["deployments"] = deploymentStorage.Deployment.WithCategories(nil)
72+
storage["deployments/status"] = deploymentStorage.Status
73+
storage["deployments/rollback"] = deploymentStorage.Rollback
74+
storage["deployments/scale"] = deploymentStorage.Scale
75+
}
7076
// ingresses
71-
ingressStorage, ingressStatusStorage := ingressstore.NewREST(restOptionsGetter)
72-
storage["ingresses"] = ingressStorage
73-
storage["ingresses/status"] = ingressStatusStorage
77+
if apiResourceConfigSource.ResourceEnabled(extensionsapiv1beta1.SchemeGroupVersion.WithResource("ingresses")) {
78+
ingressStorage, ingressStatusStorage := ingressstore.NewREST(restOptionsGetter)
79+
storage["ingresses"] = ingressStorage
80+
storage["ingresses/status"] = ingressStatusStorage
81+
}
7482

7583
// podsecuritypolicy
76-
podSecurityPolicyStorage := pspstore.NewREST(restOptionsGetter)
77-
storage["podSecurityPolicies"] = podSecurityPolicyStorage
84+
if apiResourceConfigSource.ResourceEnabled(extensionsapiv1beta1.SchemeGroupVersion.WithResource("podsecuritypolicies")) {
85+
podSecurityPolicyStorage := pspstore.NewREST(restOptionsGetter)
86+
storage["podSecurityPolicies"] = podSecurityPolicyStorage
87+
}
7888

7989
// replicasets
80-
replicaSetStorage := replicasetstore.NewStorage(restOptionsGetter)
81-
storage["replicasets"] = replicaSetStorage.ReplicaSet.WithCategories(nil)
82-
storage["replicasets/status"] = replicaSetStorage.Status
83-
storage["replicasets/scale"] = replicaSetStorage.Scale
90+
if apiResourceConfigSource.ResourceEnabled(extensionsapiv1beta1.SchemeGroupVersion.WithResource("replicasets")) {
91+
replicaSetStorage := replicasetstore.NewStorage(restOptionsGetter)
92+
storage["replicasets"] = replicaSetStorage.ReplicaSet.WithCategories(nil)
93+
storage["replicasets/status"] = replicaSetStorage.Status
94+
storage["replicasets/scale"] = replicaSetStorage.Scale
95+
}
8496

8597
// networkpolicies
86-
networkExtensionsStorage := networkpolicystore.NewREST(restOptionsGetter)
87-
storage["networkpolicies"] = networkExtensionsStorage
98+
if apiResourceConfigSource.ResourceEnabled(extensionsapiv1beta1.SchemeGroupVersion.WithResource("networkpolicies")) {
99+
networkExtensionsStorage := networkpolicystore.NewREST(restOptionsGetter)
100+
storage["networkpolicies"] = networkExtensionsStorage
101+
}
88102

89103
return storage
90104
}

staging/src/k8s.io/apiserver/pkg/server/resourceconfig/helpers.go

Lines changed: 20 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -94,7 +94,7 @@ func MergeAPIResourceConfigs(
9494
}
9595

9696
tokens := strings.Split(key, "/")
97-
if len(tokens) != 2 {
97+
if len(tokens) < 2 {
9898
continue
9999
}
100100
groupVersionString := tokens[0] + "/" + tokens[1]
@@ -103,6 +103,12 @@ func MergeAPIResourceConfigs(
103103
return nil, fmt.Errorf("invalid key %s", key)
104104
}
105105

106+
// individual resource enablement/disablement is only supported in the extensions/v1beta1 API group for legacy reasons.
107+
// all other API groups are expected to contain coherent sets of resources that are enabled/disabled together.
108+
if len(tokens) > 2 && (groupVersion != schema.GroupVersion{Group: "extensions", Version: "v1beta1"}) {
109+
return nil, fmt.Errorf("invalid key %s, individual resource enablement/disablement is not supported in %s", key, groupVersion.String())
110+
}
111+
106112
// Exclude group not registered into the registry.
107113
if !registry.IsGroupRegistered(groupVersion.Group) {
108114
continue
@@ -117,10 +123,22 @@ func MergeAPIResourceConfigs(
117123
return nil, err
118124
}
119125
if enabled {
126+
// enable the groupVersion for "group/version=true" and "group/version/resource=true"
120127
resourceConfig.EnableVersions(groupVersion)
121-
} else {
128+
} else if len(tokens) == 2 {
129+
// disable the groupVersion only for "group/version=false", not "group/version/resource=false"
122130
resourceConfig.DisableVersions(groupVersion)
123131
}
132+
133+
if len(tokens) < 3 {
134+
continue
135+
}
136+
groupVersionResource := groupVersion.WithResource(tokens[2])
137+
if enabled {
138+
resourceConfig.EnableResources(groupVersionResource)
139+
} else {
140+
resourceConfig.DisableResources(groupVersionResource)
141+
}
124142
}
125143

126144
return resourceConfig, nil

staging/src/k8s.io/apiserver/pkg/server/resourceconfig/helpers_test.go

Lines changed: 74 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -117,6 +117,11 @@ func TestParseRuntimeConfig(t *testing.T) {
117117
expectedAPIConfig: func() *serverstore.ResourceConfig {
118118
config := newFakeAPIResourceConfigSource()
119119
config.EnableVersions(scheme.PrioritizedVersionsAllGroups()...)
120+
config.EnableResources(
121+
extensionsapiv1beta1.SchemeGroupVersion.WithResource("deployments"),
122+
extensionsapiv1beta1.SchemeGroupVersion.WithResource("replicasets"),
123+
extensionsapiv1beta1.SchemeGroupVersion.WithResource("daemonsets"),
124+
)
120125
return config
121126
},
122127
err: false,
@@ -133,10 +138,71 @@ func TestParseRuntimeConfig(t *testing.T) {
133138
expectedAPIConfig: func() *serverstore.ResourceConfig {
134139
config := newFakeAPIResourceConfigSource()
135140
config.DisableVersions(extensionsapiv1beta1.SchemeGroupVersion)
141+
config.DisableResources(extensionsapiv1beta1.SchemeGroupVersion.WithResource("ingresses"))
136142
return config
137143
},
138144
err: false,
139145
},
146+
{
147+
// enable specific extensions resources
148+
runtimeConfig: map[string]string{
149+
"extensions/v1beta1/deployments": "true",
150+
},
151+
defaultResourceConfig: func() *serverstore.ResourceConfig {
152+
return newFakeAPIResourceConfigSource()
153+
},
154+
expectedAPIConfig: func() *serverstore.ResourceConfig {
155+
config := newFakeAPIResourceConfigSource()
156+
config.EnableResources(extensionsapiv1beta1.SchemeGroupVersion.WithResource("deployments"))
157+
return config
158+
},
159+
err: false,
160+
},
161+
{
162+
// disable specific extensions resources
163+
runtimeConfig: map[string]string{
164+
"extensions/v1beta1/ingresses": "false",
165+
},
166+
defaultResourceConfig: func() *serverstore.ResourceConfig {
167+
return newFakeAPIResourceConfigSource()
168+
},
169+
expectedAPIConfig: func() *serverstore.ResourceConfig {
170+
config := newFakeAPIResourceConfigSource()
171+
config.DisableResources(extensionsapiv1beta1.SchemeGroupVersion.WithResource("ingresses"))
172+
return config
173+
},
174+
err: false,
175+
},
176+
{
177+
// disable all extensions resources
178+
runtimeConfig: map[string]string{
179+
"extensions/v1beta1": "false",
180+
},
181+
defaultResourceConfig: func() *serverstore.ResourceConfig {
182+
return newFakeAPIResourceConfigSource()
183+
},
184+
expectedAPIConfig: func() *serverstore.ResourceConfig {
185+
config := newFakeAPIResourceConfigSource()
186+
config.DisableVersions(extensionsapiv1beta1.SchemeGroupVersion)
187+
return config
188+
},
189+
err: false,
190+
},
191+
{
192+
// disable a non-extensions resource
193+
runtimeConfig: map[string]string{
194+
"apps/v1/deployments": "false",
195+
},
196+
defaultResourceConfig: func() *serverstore.ResourceConfig {
197+
return newFakeAPIResourceConfigSource()
198+
},
199+
expectedAPIConfig: func() *serverstore.ResourceConfig {
200+
config := newFakeAPIResourceConfigSource()
201+
config.DisableVersions(extensionsapiv1beta1.SchemeGroupVersion)
202+
return config
203+
},
204+
err: true,
205+
},
140206
}
141207
for index, test := range testCases {
142208
t.Log(scheme.PrioritizedVersionsAllGroups())
@@ -161,6 +227,14 @@ func newFakeAPIResourceConfigSource() *serverstore.ResourceConfig {
161227
apiv1.SchemeGroupVersion,
162228
extensionsapiv1beta1.SchemeGroupVersion,
163229
)
230+
ret.EnableResources(
231+
extensionsapiv1beta1.SchemeGroupVersion.WithResource("ingresses"),
232+
)
233+
ret.DisableResources(
234+
extensionsapiv1beta1.SchemeGroupVersion.WithResource("deployments"),
235+
extensionsapiv1beta1.SchemeGroupVersion.WithResource("replicasets"),
236+
extensionsapiv1beta1.SchemeGroupVersion.WithResource("daemonsets"),
237+
)
164238

165239
return ret
166240
}

staging/src/k8s.io/apiserver/pkg/server/storage/resource_config.go

Lines changed: 32 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,29 +23,37 @@ import (
2323
// APIResourceConfigSource is the interface to determine which groups and versions are enabled
2424
type APIResourceConfigSource interface {
2525
VersionEnabled(version schema.GroupVersion) bool
26+
ResourceEnabled(resource schema.GroupVersionResource) bool
2627
AnyVersionForGroupEnabled(group string) bool
2728
}
2829

2930
var _ APIResourceConfigSource = &ResourceConfig{}
3031

3132
type ResourceConfig struct {
3233
GroupVersionConfigs map[schema.GroupVersion]bool
34+
ResourceConfigs map[schema.GroupVersionResource]bool
3335
}
3436

3537
func NewResourceConfig() *ResourceConfig {
36-
return &ResourceConfig{GroupVersionConfigs: map[schema.GroupVersion]bool{}}
38+
return &ResourceConfig{GroupVersionConfigs: map[schema.GroupVersion]bool{}, ResourceConfigs: map[schema.GroupVersionResource]bool{}}
3739
}
3840

3941
func (o *ResourceConfig) DisableAll() {
4042
for k := range o.GroupVersionConfigs {
4143
o.GroupVersionConfigs[k] = false
4244
}
45+
for k := range o.ResourceConfigs {
46+
o.ResourceConfigs[k] = false
47+
}
4348
}
4449

4550
func (o *ResourceConfig) EnableAll() {
4651
for k := range o.GroupVersionConfigs {
4752
o.GroupVersionConfigs[k] = true
4853
}
54+
for k := range o.ResourceConfigs {
55+
o.ResourceConfigs[k] = true
56+
}
4957
}
5058

5159
// DisableVersions disables the versions entirely.
@@ -70,6 +78,29 @@ func (o *ResourceConfig) VersionEnabled(version schema.GroupVersion) bool {
7078
return false
7179
}
7280

81+
func (o *ResourceConfig) DisableResources(resources ...schema.GroupVersionResource) {
82+
for _, resource := range resources {
83+
o.ResourceConfigs[resource] = false
84+
}
85+
}
86+
87+
func (o *ResourceConfig) EnableResources(resources ...schema.GroupVersionResource) {
88+
for _, resource := range resources {
89+
o.ResourceConfigs[resource] = true
90+
}
91+
}
92+
93+
func (o *ResourceConfig) ResourceEnabled(resource schema.GroupVersionResource) bool {
94+
if !o.VersionEnabled(resource.GroupVersion()) {
95+
return false
96+
}
97+
resourceEnabled, explicitlySet := o.ResourceConfigs[resource]
98+
if !explicitlySet {
99+
return true
100+
}
101+
return resourceEnabled
102+
}
103+
73104
func (o *ResourceConfig) AnyVersionForGroupEnabled(group string) bool {
74105
for version := range o.GroupVersionConfigs {
75106
if version.Group == group {

0 commit comments

Comments
 (0)