Skip to content

Commit d6e0308

Browse files
authored
Merge pull request #505 from stuggi/endpoint_webhook
Add service Endpoint Validate() method
2 parents 9417b46 + 01ef8c1 commit d6e0308

File tree

2 files changed

+168
-0
lines changed

2 files changed

+168
-0
lines changed

modules/common/service/types.go

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,9 +19,13 @@ limitations under the License.
1919
package service
2020

2121
import (
22+
"fmt"
2223
"time"
2324

25+
"golang.org/x/exp/slices"
26+
2427
corev1 "k8s.io/api/core/v1"
28+
"k8s.io/apimachinery/pkg/util/validation/field"
2529
)
2630

2731
// Endpoint - typedef to enumerate Endpoint verbs
@@ -60,6 +64,30 @@ func (e *Endpoint) String() string {
6064
return string(*e)
6165
}
6266

67+
// Validate - validates if the endpoint is an allowed one.
68+
func (e *Endpoint) Validate() error {
69+
if !slices.Contains([]Endpoint{EndpointInternal, EndpointPublic}, *e) {
70+
return fmt.Errorf("invalid endpoint type: %s", e.String())
71+
}
72+
return nil
73+
}
74+
75+
// ValidateRoutedOverrides - validates map of RoutedOverrideSpec
76+
func ValidateRoutedOverrides(basePath *field.Path, overrides map[Endpoint]RoutedOverrideSpec) field.ErrorList {
77+
allErrs := field.ErrorList{}
78+
79+
// validate the service override key is valid
80+
for k := range overrides {
81+
path := basePath.Key(k.String())
82+
83+
if err := k.Validate(); err != nil {
84+
allErrs = append(allErrs, field.Invalid(path, k.String(), err.Error()))
85+
}
86+
}
87+
88+
return allErrs
89+
}
90+
6391
func (p *Protocol) String() string {
6492
return string(*p)
6593
}

modules/common/service/types_test.go

Lines changed: 140 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,140 @@
1+
/*
2+
Copyright 2024 Red Hat
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+
// +kubebuilder:object:generate:=true
18+
19+
package service
20+
21+
import (
22+
"fmt"
23+
"testing"
24+
25+
. "github.com/onsi/gomega"
26+
"k8s.io/apimachinery/pkg/util/validation/field"
27+
)
28+
29+
func TestEndpointValidate(t *testing.T) {
30+
tests := []struct {
31+
name string
32+
e Endpoint
33+
want error
34+
}{
35+
{
36+
name: "Valid endpoint",
37+
e: EndpointInternal,
38+
want: nil,
39+
},
40+
{
41+
name: "Wrong endpoint",
42+
e: Endpoint("wrooong"),
43+
want: fmt.Errorf("invalid endpoint type: wrooong"),
44+
},
45+
}
46+
47+
for _, tt := range tests {
48+
t.Run(tt.name, func(t *testing.T) {
49+
g := NewWithT(t)
50+
51+
if tt.want == nil {
52+
g.Expect(tt.e.Validate()).To(Succeed())
53+
} else {
54+
g.Expect(tt.e.Validate()).To(Equal(tt.want))
55+
}
56+
})
57+
}
58+
}
59+
60+
func TestValidateRoutedOverrides(t *testing.T) {
61+
//basePath := field.NewPath("spec")
62+
63+
tests := []struct {
64+
name string
65+
basePath *field.Path
66+
overrides map[Endpoint]RoutedOverrideSpec
67+
want field.ErrorList
68+
}{
69+
{
70+
name: "Valid override config",
71+
basePath: field.NewPath("spec").Child("override").Child("service"),
72+
overrides: map[Endpoint]RoutedOverrideSpec{
73+
EndpointInternal: {},
74+
},
75+
want: field.ErrorList{},
76+
},
77+
{
78+
name: "Wrong override endpoint",
79+
basePath: field.NewPath("spec").Child("override").Child("service"),
80+
overrides: map[Endpoint]RoutedOverrideSpec{
81+
Endpoint("wrooong"): {},
82+
},
83+
want: field.ErrorList{
84+
&field.Error{
85+
Type: field.ErrorTypeInvalid,
86+
Field: "spec.override.service[wrooong]",
87+
BadValue: "wrooong",
88+
Detail: "invalid endpoint type: wrooong",
89+
},
90+
},
91+
},
92+
{
93+
name: "Both good and wrong override endpoint configs",
94+
basePath: field.NewPath("spec").Child("foo").Child("bar"),
95+
overrides: map[Endpoint]RoutedOverrideSpec{
96+
EndpointInternal: {},
97+
Endpoint("wrooong"): {},
98+
},
99+
want: field.ErrorList{
100+
&field.Error{
101+
Type: field.ErrorTypeInvalid,
102+
Field: "spec.foo.bar[wrooong]",
103+
BadValue: "wrooong",
104+
Detail: "invalid endpoint type: wrooong",
105+
},
106+
},
107+
},
108+
{
109+
name: "Multiple wrong override endpoints",
110+
basePath: field.NewPath("spec").Child("foo"),
111+
overrides: map[Endpoint]RoutedOverrideSpec{
112+
EndpointInternal: {},
113+
Endpoint("wrooong"): {},
114+
Endpoint("wroooooong"): {},
115+
},
116+
want: field.ErrorList{
117+
&field.Error{
118+
Type: field.ErrorTypeInvalid,
119+
Field: "spec.foo[wrooong]",
120+
BadValue: "wrooong",
121+
Detail: "invalid endpoint type: wrooong",
122+
},
123+
&field.Error{
124+
Type: field.ErrorTypeInvalid,
125+
Field: "spec.foo[wroooooong]",
126+
BadValue: "wroooooong",
127+
Detail: "invalid endpoint type: wroooooong",
128+
},
129+
},
130+
},
131+
}
132+
133+
for _, tt := range tests {
134+
t.Run(tt.name, func(t *testing.T) {
135+
g := NewWithT(t)
136+
137+
g.Expect(ValidateRoutedOverrides(tt.basePath, tt.overrides)).To(Equal(tt.want))
138+
})
139+
}
140+
}

0 commit comments

Comments
 (0)