@@ -17,11 +17,14 @@ limitations under the License.
1717package v1alpha1
1818
1919import (
20+ "fmt"
21+
2022 promv1 "github.com/prometheus-operator/prometheus-operator/pkg/apis/monitoring/v1"
2123 autoscalingv2 "k8s.io/api/autoscaling/v2"
2224 corev1 "k8s.io/api/core/v1"
2325 networkingv1 "k8s.io/api/networking/v1"
2426 "k8s.io/utils/ptr"
27+ gatewayv1 "sigs.k8s.io/gateway-api/apis/v1"
2528)
2629
2730const (
@@ -38,7 +41,39 @@ const (
3841// Expose defines attributes to expose the service.
3942type Expose struct {
4043 Service Service `json:"service,omitempty"`
41- Ingress Ingress `json:"ingress,omitempty"`
44+ // Deprecated: Use .spec.router instead.
45+ // Ingress Ingress `json:"ingress,omitempty"`
46+ // Deprecated: Use .spec.router instead.
47+ // HTTPRoute HTTPRoute `json:"httpRoute,omitempty"`
48+ }
49+
50+ // +kubebuilder:validation:XValidation:rule="!(has(self.gateway) && has(self.ingressClass))", message="ingressClass and gateway cannot be specified together"
51+ type Router struct {
52+ // HostDomainName is the domain name of the hostname matched by the router.
53+ // The hostname is constructed as "<nimServiceName>.<hostDomainName>", where the <nimServiceName> a subdomain of the matched hostname.
54+ // eg. example.com for "<nimServiceName>.example.com"
55+ // +kubebuilder:validation:MinLength=1
56+ // +kubebuilder:validation:MaxLength=63
57+ // +kubebuilder:validation:Pattern=`^(([a-z0-9][a-z0-9\-]*[a-z0-9])|[a-z0-9]+\.)*([a-z]+|xn\-\-[a-z0-9]+)\.?$`
58+ HostDomainName string `json:"hostDomainName,omitempty"`
59+
60+ // Annotations for the router, e.g. for ingress class or gateway
61+ Annotations map [string ]string `json:"annotations,omitempty"`
62+
63+ // IngressClass is the class of the ingress controller to use for the created ingress.
64+ IngressClass * string `json:"ingressClass,omitempty"`
65+
66+ // Gateway is the gateway to use for the created HTTPRoute.
67+ Gateway * Gateway `json:"gateway,omitempty"`
68+ }
69+
70+ type Gateway struct {
71+ // +kubebuilder:validation:MinLength=1
72+ // Namespace of the gateway
73+ Namespace string `json:"namespace"`
74+ // +kubebuilder:validation:MinLength=1
75+ // Name of the gateway
76+ Name string `json:"name"`
4277}
4378
4479// Service defines attributes to create a service.
@@ -67,12 +102,6 @@ type Service struct {
67102 Annotations map [string ]string `json:"annotations,omitempty"`
68103}
69104
70- // ExposeV1 defines attributes to expose the service.
71- type ExposeV1 struct {
72- Service Service `json:"service,omitempty"`
73- Ingress IngressV1 `json:"ingress,omitempty"`
74- }
75-
76105// Metrics defines attributes to setup metrics collection.
77106type Metrics struct {
78107 Enabled * bool `json:"enabled,omitempty"`
@@ -119,6 +148,32 @@ type Ingress struct {
119148 Spec networkingv1.IngressSpec `json:"spec,omitempty"`
120149}
121150
151+ // HTTPRoute defines attributes to HTTPRoute in Gateway API.
152+ type HTTPRoute struct {
153+ Enabled * bool `json:"enabled,omitempty"`
154+ Annotations map [string ]string `json:"annotations,omitempty"`
155+ Spec * HTTPRouteSpec `json:"spec,omitempty"`
156+ }
157+
158+ type HTTPRouteSpec struct {
159+ gatewayv1.CommonRouteSpec `json:",inline"`
160+ Host gatewayv1.Hostname `json:"host,omitempty"`
161+ Paths []HTTPPathMatch `json:"paths,omitempty"`
162+ }
163+
164+ type HTTPPathMatch struct {
165+ // Type specifies how to match against the path Value.
166+ // +optional
167+ // +kubebuilder:default=PathPrefix
168+ Type * gatewayv1.PathMatchType `json:"type,omitempty"`
169+
170+ // Value of the HTTP path to match against.
171+ // +optional
172+ // +kubebuilder:default="/"
173+ // +kubebuilder:validation:MaxLength=1024
174+ Value * string `json:"value,omitempty"`
175+ }
176+
122177// IngressV1 defines attributes for ingress
123178//
124179// +kubebuilder:validation:XValidation:rule="(has(self.spec) && has(self.enabled) && self.enabled) || !has(self.enabled) || !self.enabled", message="spec cannot be nil when ingress is enabled"
@@ -142,46 +197,81 @@ type ResourceRequirements struct {
142197 Requests corev1.ResourceList `json:"requests,omitempty" protobuf:"bytes,2,rep,name=requests,casttype=ResourceList,castkey=ResourceName"`
143198}
144199
145- func (i * IngressV1 ) GenerateNetworkingV1IngressSpec (name string ) networkingv1. IngressSpec {
146- if i . Spec == nil {
147- return networkingv1. IngressSpec {}
200+ func (r * Router ) GenerateGatewayHTTPRouteSpec (name string ) gatewayv1. HTTPRouteSpec {
201+ if r . Gateway == nil {
202+ return gatewayv1. HTTPRouteSpec {}
148203 }
149204
150- ingressSpec := networkingv1.IngressSpec {
151- IngressClassName : & i .Spec .IngressClassName ,
152- Rules : []networkingv1.IngressRule {
205+ return gatewayv1.HTTPRouteSpec {
206+ CommonRouteSpec : gatewayv1.CommonRouteSpec {
207+ ParentRefs : []gatewayv1.ParentReference {
208+ {
209+ Name : gatewayv1 .ObjectName (r .Gateway .Name ),
210+ Namespace : ptr .To (gatewayv1 .Namespace (r .Gateway .Namespace )),
211+ },
212+ },
213+ },
214+ Hostnames : []gatewayv1.Hostname {gatewayv1 .Hostname (r .getHostname (name ))},
215+ Rules : []gatewayv1.HTTPRouteRule {
153216 {
154- Host : i .Spec .Host ,
155- IngressRuleValue : networkingv1.IngressRuleValue {
156- HTTP : & networkingv1.HTTPIngressRuleValue {},
217+ BackendRefs : []gatewayv1.HTTPBackendRef {
218+ {
219+ BackendRef : gatewayv1.BackendRef {
220+ BackendObjectReference : gatewayv1.BackendObjectReference {
221+ Name : gatewayv1 .ObjectName (name ),
222+ Port : ptr .To (gatewayv1 .PortNumber (DefaultAPIPort )),
223+ },
224+ },
225+ },
226+ },
227+ Matches : []gatewayv1.HTTPRouteMatch {
228+ {
229+ Path : & gatewayv1.HTTPPathMatch {
230+ Type : ptr .To (gatewayv1 .PathMatchPathPrefix ),
231+ Value : ptr .To ("/" ),
232+ },
233+ },
157234 },
158235 },
159236 },
160237 }
238+ }
161239
162- svcBackend := networkingv1.IngressBackend {
163- Service : & networkingv1.IngressServiceBackend {
164- Name : name ,
165- Port : networkingv1.ServiceBackendPort {
166- Name : DefaultNamedPortAPI ,
240+ func (r * Router ) getHostname (name string ) string {
241+ return fmt .Sprintf ("%s.%s" , name , r .HostDomainName )
242+ }
243+
244+ func (r * Router ) GenerateIngressSpec (name string ) networkingv1.IngressSpec {
245+ if r .IngressClass == nil {
246+ return networkingv1.IngressSpec {}
247+ }
248+
249+ return networkingv1.IngressSpec {
250+ IngressClassName : r .IngressClass ,
251+ Rules : []networkingv1.IngressRule {
252+ {
253+ Host : r .getHostname (name ),
254+ IngressRuleValue : networkingv1.IngressRuleValue {
255+ HTTP : & networkingv1.HTTPIngressRuleValue {
256+ Paths : []networkingv1.HTTPIngressPath {
257+ {
258+ Path : "/" ,
259+ PathType : ptr .To (networkingv1 .PathTypePrefix ),
260+ Backend : networkingv1.IngressBackend {
261+ Service : & networkingv1.IngressServiceBackend {
262+ Name : name ,
263+ Port : networkingv1.ServiceBackendPort {
264+ Name : DefaultNamedPortAPI ,
265+ },
266+ },
267+ },
268+ },
269+ },
270+ },
271+ },
167272 },
168273 },
169274 }
170- if len (i .Spec .Paths ) == 0 {
171- ingressSpec .Rules [0 ].HTTP .Paths = append (ingressSpec .Rules [0 ].HTTP .Paths , networkingv1.HTTPIngressPath {
172- Path : "/" ,
173- PathType : ptr .To (networkingv1 .PathTypePrefix ),
174- Backend : svcBackend ,
175- })
176- }
177- for _ , path := range i .Spec .Paths {
178- ingressSpec .Rules [0 ].HTTP .Paths = append (ingressSpec .Rules [0 ].HTTP .Paths , networkingv1.HTTPIngressPath {
179- Path : path .Path ,
180- PathType : path .PathType ,
181- Backend : svcBackend ,
182- })
183- }
184- return ingressSpec
185275}
186276
187277type IngressSpec struct {
0 commit comments