Skip to content

Commit 8e3bbaf

Browse files
committed
Allow IdentityRef.Name change and add unit test to OpenStackCluster webhooks
Signed-off-by: Tobias Giese <[email protected]>
1 parent 8d402eb commit 8e3bbaf

File tree

2 files changed

+195
-1
lines changed

2 files changed

+195
-1
lines changed

api/v1alpha4/openstackcluster_webhook.go

Lines changed: 23 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -74,7 +74,29 @@ func (r *OpenStackCluster) ValidateUpdate(oldRaw runtime.Object) error {
7474
}
7575

7676
if r.Spec.IdentityRef != nil && r.Spec.IdentityRef.Kind != defaultIdentityRefKind {
77-
allErrs = append(allErrs, field.Forbidden(field.NewPath("spec", "identityRef", "kind"), "must be a Secret"))
77+
allErrs = append(allErrs,
78+
field.Invalid(field.NewPath("spec", "identityRef", "kind"),
79+
r.Spec.IdentityRef, "must be a Secret"),
80+
)
81+
}
82+
83+
// Allow changes to Spec.IdentityRef.Name.
84+
if old.Spec.IdentityRef != nil && r.Spec.IdentityRef != nil {
85+
old.Spec.IdentityRef.Name = ""
86+
r.Spec.IdentityRef.Name = ""
87+
}
88+
89+
// Allow changes to Spec.IdentityRef if it was unset.
90+
if old.Spec.IdentityRef == nil && r.Spec.IdentityRef != nil {
91+
old.Spec.IdentityRef = &OpenStackIdentityReference{}
92+
r.Spec.IdentityRef = &OpenStackIdentityReference{}
93+
}
94+
95+
if old.Spec.IdentityRef != nil && r.Spec.IdentityRef == nil {
96+
allErrs = append(allErrs,
97+
field.Invalid(field.NewPath("spec", "identityRef"),
98+
r.Spec.IdentityRef, "field cannot be set to nil"),
99+
)
78100
}
79101

80102
// Allow change only for the first time.
Lines changed: 172 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,172 @@
1+
/*
2+
Copyright 2021 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 v1alpha4
18+
19+
import (
20+
"testing"
21+
22+
. "github.com/onsi/gomega"
23+
)
24+
25+
func TestOpenStackCluster_ValidateUpdate(t *testing.T) {
26+
g := NewWithT(t)
27+
28+
tests := []struct {
29+
name string
30+
oldTemplate *OpenStackCluster
31+
newTemplate *OpenStackCluster
32+
wantErr bool
33+
}{
34+
{
35+
name: "OpenStackCluster.Spec.IdentityRef.Kind must always be Secret",
36+
oldTemplate: &OpenStackCluster{
37+
Spec: OpenStackClusterSpec{
38+
CloudName: "foobar",
39+
IdentityRef: &OpenStackIdentityReference{
40+
Kind: "Secret",
41+
Name: "foobar",
42+
},
43+
},
44+
},
45+
newTemplate: &OpenStackCluster{
46+
Spec: OpenStackClusterSpec{
47+
CloudName: "foobar",
48+
IdentityRef: &OpenStackIdentityReference{
49+
Kind: "foobar",
50+
Name: "foobar",
51+
},
52+
},
53+
},
54+
wantErr: true,
55+
},
56+
{
57+
name: "Changing OpenStackCluster.Spec.IdentityRef.Name is allowed",
58+
oldTemplate: &OpenStackCluster{
59+
Spec: OpenStackClusterSpec{
60+
CloudName: "foobar",
61+
IdentityRef: &OpenStackIdentityReference{
62+
Kind: "Secret",
63+
Name: "foobar",
64+
},
65+
},
66+
},
67+
newTemplate: &OpenStackCluster{
68+
Spec: OpenStackClusterSpec{
69+
CloudName: "foobar",
70+
IdentityRef: &OpenStackIdentityReference{
71+
Kind: "Secret",
72+
Name: "foobarbaz",
73+
},
74+
},
75+
},
76+
wantErr: false,
77+
},
78+
{
79+
name: "OpenStackCluster.Spec.IdentityRef can be changed if it was unset",
80+
oldTemplate: &OpenStackCluster{
81+
Spec: OpenStackClusterSpec{
82+
CloudName: "foobar",
83+
},
84+
},
85+
newTemplate: &OpenStackCluster{
86+
Spec: OpenStackClusterSpec{
87+
CloudName: "foobar",
88+
IdentityRef: &OpenStackIdentityReference{
89+
Kind: "Secret",
90+
Name: "foobar",
91+
},
92+
},
93+
},
94+
wantErr: false,
95+
},
96+
{
97+
name: "OpenStackCluster.Spec.IdentityRef must not be removed",
98+
oldTemplate: &OpenStackCluster{
99+
Spec: OpenStackClusterSpec{
100+
CloudName: "foobar",
101+
IdentityRef: &OpenStackIdentityReference{
102+
Kind: "Secret",
103+
Name: "foobar",
104+
},
105+
},
106+
},
107+
newTemplate: &OpenStackCluster{
108+
Spec: OpenStackClusterSpec{
109+
CloudName: "foobar",
110+
},
111+
},
112+
wantErr: true,
113+
},
114+
}
115+
for _, tt := range tests {
116+
t.Run(tt.name, func(t *testing.T) {
117+
err := tt.newTemplate.ValidateUpdate(tt.oldTemplate)
118+
if tt.wantErr {
119+
g.Expect(err).To(HaveOccurred())
120+
} else {
121+
g.Expect(err).NotTo(HaveOccurred())
122+
}
123+
})
124+
}
125+
}
126+
127+
func TestOpenStackCluster_ValidateCreate(t *testing.T) {
128+
g := NewWithT(t)
129+
130+
tests := []struct {
131+
name string
132+
template *OpenStackCluster
133+
wantErr bool
134+
}{
135+
{
136+
name: "OpenStackCluster.Spec.IdentityRef with correct spec on create",
137+
template: &OpenStackCluster{
138+
Spec: OpenStackClusterSpec{
139+
CloudName: "foobar",
140+
IdentityRef: &OpenStackIdentityReference{
141+
Kind: "Secret",
142+
Name: "foobar",
143+
},
144+
},
145+
},
146+
wantErr: false,
147+
},
148+
{
149+
name: "OpenStackCluster.Spec.IdentityRef with faulty spec on create",
150+
template: &OpenStackCluster{
151+
Spec: OpenStackClusterSpec{
152+
CloudName: "foobar",
153+
IdentityRef: &OpenStackIdentityReference{
154+
Kind: "foobar",
155+
Name: "foobar",
156+
},
157+
},
158+
},
159+
wantErr: true,
160+
},
161+
}
162+
for _, tt := range tests {
163+
t.Run(tt.name, func(t *testing.T) {
164+
err := tt.template.ValidateCreate()
165+
if tt.wantErr {
166+
g.Expect(err).To(HaveOccurred())
167+
} else {
168+
g.Expect(err).NotTo(HaveOccurred())
169+
}
170+
})
171+
}
172+
}

0 commit comments

Comments
 (0)