From d5d68cf603a3617144a8b9ff637f94dea980ab36 Mon Sep 17 00:00:00 2001 From: Daniel Lipovetsky Date: Fri, 28 Jun 2024 13:00:39 -0700 Subject: [PATCH 1/2] feat: Define ServiceLoadBalancer Configuration API --- api/v1alpha1/addon_types.go | 24 +++++++++++ .../caren.nutanix.com_awsclusterconfigs.yaml | 24 +++++++++++ ...aren.nutanix.com_dockerclusterconfigs.yaml | 24 +++++++++++ ...ren.nutanix.com_nutanixclusterconfigs.yaml | 24 +++++++++++ api/v1alpha1/zz_generated.deepcopy.go | 42 ++++++++++++++++++- 5 files changed, 137 insertions(+), 1 deletion(-) diff --git a/api/v1alpha1/addon_types.go b/api/v1alpha1/addon_types.go index c116c0992..d89f84bf6 100644 --- a/api/v1alpha1/addon_types.go +++ b/api/v1alpha1/addon_types.go @@ -257,4 +257,28 @@ type ServiceLoadBalancer struct { // +kubebuilder:validation:Enum=MetalLB // +kubebuilder:validation:Required Provider string `json:"provider"` + + // Configuration for the chosen ServiceLoadBalancer provider. + // +kubebuilder:validation:Optional + Configuration *ServiceLoadBalancerConfiguration `json:"configuration"` +} + +type ServiceLoadBalancerConfiguration struct { + // AddressRanges is a list of IPv4 or IPv6 address ranges from which + // the provider can choose a load balancer address. + AddressRanges []AddressRange `json:"addressRanges"` +} + +// AddressRange defines an IPv4 or IPv6 range. +type AddressRange struct { + // FIXME Both start and end should be of the same type (IPv4 or IPv6). + // Because the pattern accepts either type, start and end can be of different + // types. + // Source: https://github.com/metal3-io/ip-address-manager/blob/b4f7c2a/api/v1alpha1/common_types.go#L19 + + // +kubebuilder:validation:Pattern="((^((([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5]))$)|(^(([0-9a-fA-F]{1,4}:){7,7}[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,7}:|([0-9a-fA-F]{1,4}:){1,6}:[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,5}(:[0-9a-fA-F]{1,4}){1,2}|([0-9a-fA-F]{1,4}:){1,4}(:[0-9a-fA-F]{1,4}){1,3}|([0-9a-fA-F]{1,4}:){1,3}(:[0-9a-fA-F]{1,4}){1,4}|([0-9a-fA-F]{1,4}:){1,2}(:[0-9a-fA-F]{1,4}){1,5}|[0-9a-fA-F]{1,4}:((:[0-9a-fA-F]{1,4}){1,6})|:((:[0-9a-fA-F]{1,4}){1,7}|:))$))" + Start string `json:"start"` + + // +kubebuilder:validation:Pattern="((^((([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5]))$)|(^(([0-9a-fA-F]{1,4}:){7,7}[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,7}:|([0-9a-fA-F]{1,4}:){1,6}:[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,5}(:[0-9a-fA-F]{1,4}){1,2}|([0-9a-fA-F]{1,4}:){1,4}(:[0-9a-fA-F]{1,4}){1,3}|([0-9a-fA-F]{1,4}:){1,3}(:[0-9a-fA-F]{1,4}){1,4}|([0-9a-fA-F]{1,4}:){1,2}(:[0-9a-fA-F]{1,4}){1,5}|[0-9a-fA-F]{1,4}:((:[0-9a-fA-F]{1,4}){1,6})|:((:[0-9a-fA-F]{1,4}){1,7}|:))$))" + End string `json:"end"` } diff --git a/api/v1alpha1/crds/caren.nutanix.com_awsclusterconfigs.yaml b/api/v1alpha1/crds/caren.nutanix.com_awsclusterconfigs.yaml index c1a6926ec..05a5a5dde 100644 --- a/api/v1alpha1/crds/caren.nutanix.com_awsclusterconfigs.yaml +++ b/api/v1alpha1/crds/caren.nutanix.com_awsclusterconfigs.yaml @@ -218,6 +218,30 @@ spec: type: object serviceLoadBalancer: properties: + configuration: + description: Configuration for the chosen ServiceLoadBalancer provider. + properties: + addressRanges: + description: |- + AddressRanges is a list of IPv4 or IPv6 address ranges from which + the provider can choose a load balancer address. + items: + description: AddressRange defines an IPv4 or IPv6 range. + properties: + end: + pattern: ((^((([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5]))$)|(^(([0-9a-fA-F]{1,4}:){7,7}[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,7}:|([0-9a-fA-F]{1,4}:){1,6}:[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,5}(:[0-9a-fA-F]{1,4}){1,2}|([0-9a-fA-F]{1,4}:){1,4}(:[0-9a-fA-F]{1,4}){1,3}|([0-9a-fA-F]{1,4}:){1,3}(:[0-9a-fA-F]{1,4}){1,4}|([0-9a-fA-F]{1,4}:){1,2}(:[0-9a-fA-F]{1,4}){1,5}|[0-9a-fA-F]{1,4}:((:[0-9a-fA-F]{1,4}){1,6})|:((:[0-9a-fA-F]{1,4}){1,7}|:))$)) + type: string + start: + pattern: ((^((([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5]))$)|(^(([0-9a-fA-F]{1,4}:){7,7}[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,7}:|([0-9a-fA-F]{1,4}:){1,6}:[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,5}(:[0-9a-fA-F]{1,4}){1,2}|([0-9a-fA-F]{1,4}:){1,4}(:[0-9a-fA-F]{1,4}){1,3}|([0-9a-fA-F]{1,4}:){1,3}(:[0-9a-fA-F]{1,4}){1,4}|([0-9a-fA-F]{1,4}:){1,2}(:[0-9a-fA-F]{1,4}){1,5}|[0-9a-fA-F]{1,4}:((:[0-9a-fA-F]{1,4}){1,6})|:((:[0-9a-fA-F]{1,4}){1,7}|:))$)) + type: string + required: + - end + - start + type: object + type: array + required: + - addressRanges + type: object provider: description: |- The LoadBalancer-type Service provider to deploy. Not required in infrastructures where diff --git a/api/v1alpha1/crds/caren.nutanix.com_dockerclusterconfigs.yaml b/api/v1alpha1/crds/caren.nutanix.com_dockerclusterconfigs.yaml index c86fbd451..7eb9b66b8 100644 --- a/api/v1alpha1/crds/caren.nutanix.com_dockerclusterconfigs.yaml +++ b/api/v1alpha1/crds/caren.nutanix.com_dockerclusterconfigs.yaml @@ -218,6 +218,30 @@ spec: type: object serviceLoadBalancer: properties: + configuration: + description: Configuration for the chosen ServiceLoadBalancer provider. + properties: + addressRanges: + description: |- + AddressRanges is a list of IPv4 or IPv6 address ranges from which + the provider can choose a load balancer address. + items: + description: AddressRange defines an IPv4 or IPv6 range. + properties: + end: + pattern: ((^((([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5]))$)|(^(([0-9a-fA-F]{1,4}:){7,7}[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,7}:|([0-9a-fA-F]{1,4}:){1,6}:[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,5}(:[0-9a-fA-F]{1,4}){1,2}|([0-9a-fA-F]{1,4}:){1,4}(:[0-9a-fA-F]{1,4}){1,3}|([0-9a-fA-F]{1,4}:){1,3}(:[0-9a-fA-F]{1,4}){1,4}|([0-9a-fA-F]{1,4}:){1,2}(:[0-9a-fA-F]{1,4}){1,5}|[0-9a-fA-F]{1,4}:((:[0-9a-fA-F]{1,4}){1,6})|:((:[0-9a-fA-F]{1,4}){1,7}|:))$)) + type: string + start: + pattern: ((^((([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5]))$)|(^(([0-9a-fA-F]{1,4}:){7,7}[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,7}:|([0-9a-fA-F]{1,4}:){1,6}:[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,5}(:[0-9a-fA-F]{1,4}){1,2}|([0-9a-fA-F]{1,4}:){1,4}(:[0-9a-fA-F]{1,4}){1,3}|([0-9a-fA-F]{1,4}:){1,3}(:[0-9a-fA-F]{1,4}){1,4}|([0-9a-fA-F]{1,4}:){1,2}(:[0-9a-fA-F]{1,4}){1,5}|[0-9a-fA-F]{1,4}:((:[0-9a-fA-F]{1,4}){1,6})|:((:[0-9a-fA-F]{1,4}){1,7}|:))$)) + type: string + required: + - end + - start + type: object + type: array + required: + - addressRanges + type: object provider: description: |- The LoadBalancer-type Service provider to deploy. Not required in infrastructures where diff --git a/api/v1alpha1/crds/caren.nutanix.com_nutanixclusterconfigs.yaml b/api/v1alpha1/crds/caren.nutanix.com_nutanixclusterconfigs.yaml index f780c5d0e..d3cf8eea0 100644 --- a/api/v1alpha1/crds/caren.nutanix.com_nutanixclusterconfigs.yaml +++ b/api/v1alpha1/crds/caren.nutanix.com_nutanixclusterconfigs.yaml @@ -218,6 +218,30 @@ spec: type: object serviceLoadBalancer: properties: + configuration: + description: Configuration for the chosen ServiceLoadBalancer provider. + properties: + addressRanges: + description: |- + AddressRanges is a list of IPv4 or IPv6 address ranges from which + the provider can choose a load balancer address. + items: + description: AddressRange defines an IPv4 or IPv6 range. + properties: + end: + pattern: ((^((([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5]))$)|(^(([0-9a-fA-F]{1,4}:){7,7}[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,7}:|([0-9a-fA-F]{1,4}:){1,6}:[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,5}(:[0-9a-fA-F]{1,4}){1,2}|([0-9a-fA-F]{1,4}:){1,4}(:[0-9a-fA-F]{1,4}){1,3}|([0-9a-fA-F]{1,4}:){1,3}(:[0-9a-fA-F]{1,4}){1,4}|([0-9a-fA-F]{1,4}:){1,2}(:[0-9a-fA-F]{1,4}){1,5}|[0-9a-fA-F]{1,4}:((:[0-9a-fA-F]{1,4}){1,6})|:((:[0-9a-fA-F]{1,4}){1,7}|:))$)) + type: string + start: + pattern: ((^((([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5]))$)|(^(([0-9a-fA-F]{1,4}:){7,7}[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,7}:|([0-9a-fA-F]{1,4}:){1,6}:[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,5}(:[0-9a-fA-F]{1,4}){1,2}|([0-9a-fA-F]{1,4}:){1,4}(:[0-9a-fA-F]{1,4}){1,3}|([0-9a-fA-F]{1,4}:){1,3}(:[0-9a-fA-F]{1,4}){1,4}|([0-9a-fA-F]{1,4}:){1,2}(:[0-9a-fA-F]{1,4}){1,5}|[0-9a-fA-F]{1,4}:((:[0-9a-fA-F]{1,4}){1,6})|:((:[0-9a-fA-F]{1,4}){1,7}|:))$)) + type: string + required: + - end + - start + type: object + type: array + required: + - addressRanges + type: object provider: description: |- The LoadBalancer-type Service provider to deploy. Not required in infrastructures where diff --git a/api/v1alpha1/zz_generated.deepcopy.go b/api/v1alpha1/zz_generated.deepcopy.go index c546643ad..1a27f596a 100644 --- a/api/v1alpha1/zz_generated.deepcopy.go +++ b/api/v1alpha1/zz_generated.deepcopy.go @@ -398,6 +398,21 @@ func (in AdditionalSecurityGroup) DeepCopy() AdditionalSecurityGroup { return *out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *AddressRange) DeepCopyInto(out *AddressRange) { + *out = *in +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new AddressRange. +func (in *AddressRange) DeepCopy() *AddressRange { + if in == nil { + return nil + } + out := new(AddressRange) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *CCM) DeepCopyInto(out *CCM) { *out = *in @@ -847,7 +862,7 @@ func (in *GenericAddons) DeepCopyInto(out *GenericAddons) { if in.ServiceLoadBalancer != nil { in, out := &in.ServiceLoadBalancer, &out.ServiceLoadBalancer *out = new(ServiceLoadBalancer) - **out = **in + (*in).DeepCopyInto(*out) } } @@ -1424,6 +1439,11 @@ func (in *SecurityGroup) DeepCopy() *SecurityGroup { // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *ServiceLoadBalancer) DeepCopyInto(out *ServiceLoadBalancer) { *out = *in + if in.Configuration != nil { + in, out := &in.Configuration, &out.Configuration + *out = new(ServiceLoadBalancerConfiguration) + (*in).DeepCopyInto(*out) + } } // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ServiceLoadBalancer. @@ -1436,6 +1456,26 @@ func (in *ServiceLoadBalancer) DeepCopy() *ServiceLoadBalancer { return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *ServiceLoadBalancerConfiguration) DeepCopyInto(out *ServiceLoadBalancerConfiguration) { + *out = *in + if in.AddressRanges != nil { + in, out := &in.AddressRanges, &out.AddressRanges + *out = make([]AddressRange, len(*in)) + copy(*out, *in) + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ServiceLoadBalancerConfiguration. +func (in *ServiceLoadBalancerConfiguration) DeepCopy() *ServiceLoadBalancerConfiguration { + if in == nil { + return nil + } + out := new(ServiceLoadBalancerConfiguration) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *SnapshotController) DeepCopyInto(out *SnapshotController) { *out = *in From df5addb2e8dc1956e5cc3621c574fd19a0d785db Mon Sep 17 00:00:00 2001 From: Daniel Lipovetsky Date: Fri, 28 Jun 2024 14:59:20 -0700 Subject: [PATCH 2/2] fixup! feat: Define ServiceLoadBalancer Configuration API - Require at least one element in AddressRanges. - Add omitempty to Configuration JSON struct tag. --- api/v1alpha1/addon_types.go | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/api/v1alpha1/addon_types.go b/api/v1alpha1/addon_types.go index d89f84bf6..cbe7a0977 100644 --- a/api/v1alpha1/addon_types.go +++ b/api/v1alpha1/addon_types.go @@ -260,12 +260,13 @@ type ServiceLoadBalancer struct { // Configuration for the chosen ServiceLoadBalancer provider. // +kubebuilder:validation:Optional - Configuration *ServiceLoadBalancerConfiguration `json:"configuration"` + Configuration *ServiceLoadBalancerConfiguration `json:"configuration,omitempty"` } type ServiceLoadBalancerConfiguration struct { // AddressRanges is a list of IPv4 or IPv6 address ranges from which // the provider can choose a load balancer address. + // +kubebuilder:validation:MinItems=1 AddressRanges []AddressRange `json:"addressRanges"` }