k8c.io/api/v3@v3.0.0-20230904060738-b0a93889c0b6/pkg/apis/ee.kubermatic/v1/common.go (about)

     1  /*
     2  Copyright 2023 The Kubermatic Kubernetes Platform contributors.
     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 v1
    18  
    19  import (
    20  	"fmt"
    21  	"net"
    22  
    23  	corev1 "k8s.io/api/core/v1"
    24  	"k8s.io/apimachinery/pkg/api/resource"
    25  	netutils "k8s.io/utils/net"
    26  )
    27  
    28  // +kubebuilder:validation:Pattern:=`^((\d{1,3}\.){3}\d{1,3}\/([0-9]|[1-2][0-9]|3[0-2]))$`
    29  type CIDR string
    30  
    31  // +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-9]|[1-2][0-9]|3[0-2])$)|(^(([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}|:))/([0-9]|[0-9][0-9]|1[0-1][0-9]|12[0-8])$))"
    32  
    33  // SubnetCIDR is used to store IPv4/IPv6 CIDR.
    34  type SubnetCIDR string
    35  
    36  const (
    37  	InitialMachineDeploymentRequestAnnotation        = "kubermatic.io/initial-machinedeployment-request"
    38  	InitialApplicationInstallationsRequestAnnotation = "kubermatic.io/initial-application-installations-request"
    39  	InitialCNIValuesRequestAnnotation                = "kubermatic.io/initial-cni-values-request"
    40  )
    41  
    42  type MachineFlavorFilter struct {
    43  	// +kubebuilder:default=0
    44  	// +kubebuilder:validation:Minimum:=0
    45  
    46  	// Minimum number of vCPU
    47  	MinCPU int `json:"minCPU"`
    48  
    49  	// +kubebuilder:default=0
    50  	// +kubebuilder:validation:Minimum:=0
    51  
    52  	// Maximum number of vCPU
    53  	MaxCPU int `json:"maxCPU"`
    54  
    55  	// +kubebuilder:default=0
    56  	// +kubebuilder:validation:Minimum:=0
    57  
    58  	// Minimum RAM size in GB
    59  	MinRAM int `json:"minRAM"`
    60  
    61  	// +kubebuilder:default=0
    62  	// +kubebuilder:validation:Minimum:=0
    63  
    64  	// Maximum RAM size in GB
    65  	MaxRAM int `json:"maxRAM"`
    66  
    67  	// Include VMs with GPU
    68  	EnableGPU bool `json:"enableGPU"` //nolint:tagliatelle
    69  }
    70  
    71  // NetworkRanges represents ranges of network addresses.
    72  type NetworkRanges struct {
    73  	CIDRBlocks []string `json:"cidrBlocks,omitempty"`
    74  }
    75  
    76  // Validate validates the network ranges. Returns nil if valid, error otherwise.
    77  func (r *NetworkRanges) Validate() error {
    78  	if r == nil {
    79  		return nil
    80  	}
    81  
    82  	for _, cidr := range r.CIDRBlocks {
    83  		if _, _, err := net.ParseCIDR(cidr); err != nil {
    84  			return fmt.Errorf("unable to parse CIDR %q: %w", cidr, err)
    85  		}
    86  	}
    87  
    88  	return nil
    89  }
    90  
    91  // GetIPv4CIDR returns the first found IPv4 CIDR in the network ranges, or an empty string if no IPv4 CIDR is found.
    92  func (r *NetworkRanges) GetIPv4CIDR() string {
    93  	for _, cidr := range r.CIDRBlocks {
    94  		if netutils.IsIPv4CIDRString(cidr) {
    95  			return cidr
    96  		}
    97  	}
    98  
    99  	return ""
   100  }
   101  
   102  // GetIPv4CIDRs returns all IPv4 CIDRs in the network ranges, or an empty string if no IPv4 CIDR is found.
   103  func (r *NetworkRanges) GetIPv4CIDRs() (res []string) {
   104  	for _, cidr := range r.CIDRBlocks {
   105  		if netutils.IsIPv4CIDRString(cidr) {
   106  			res = append(res, cidr)
   107  		}
   108  	}
   109  
   110  	return
   111  }
   112  
   113  // HasIPv4CIDR returns true if the network ranges contain any IPv4 CIDR, false otherwise.
   114  func (r *NetworkRanges) HasIPv4CIDR() bool {
   115  	return r.GetIPv4CIDR() != ""
   116  }
   117  
   118  // GetIPv6CIDR returns the first found IPv6 CIDR in the network ranges, or an empty string if no IPv6 CIDR is found.
   119  func (r *NetworkRanges) GetIPv6CIDR() string {
   120  	for _, cidr := range r.CIDRBlocks {
   121  		if netutils.IsIPv6CIDRString(cidr) {
   122  			return cidr
   123  		}
   124  	}
   125  
   126  	return ""
   127  }
   128  
   129  // GetIPv6CIDRs returns all IPv6 CIDRs in the network ranges, or an empty string if no IPv6 CIDR is found.
   130  func (r *NetworkRanges) GetIPv6CIDRs() (res []string) {
   131  	for _, cidr := range r.CIDRBlocks {
   132  		if netutils.IsIPv6CIDRString(cidr) {
   133  			res = append(res, cidr)
   134  		}
   135  	}
   136  
   137  	return
   138  }
   139  
   140  // HasIPv6CIDR returns true if the network ranges contain any IPv6 CIDR, false otherwise.
   141  func (r *NetworkRanges) HasIPv6CIDR() bool {
   142  	return r.GetIPv6CIDR() != ""
   143  }
   144  
   145  // ResourceDetails holds the CPU, Memory and Storage quantities.
   146  type ResourceDetails struct {
   147  	// CPU holds the quantity of CPU. For the format, please check k8s.io/apimachinery/pkg/api/resource.Quantity.
   148  	CPU *resource.Quantity `json:"cpu,omitempty"`
   149  	// Memory represents the quantity of RAM size. For the format, please check k8s.io/apimachinery/pkg/api/resource.Quantity.
   150  	Memory *resource.Quantity `json:"memory,omitempty"`
   151  	// Storage represents the disk size. For the format, please check k8s.io/apimachinery/pkg/api/resource.Quantity.
   152  	Storage *resource.Quantity `json:"storage,omitempty"`
   153  }
   154  
   155  func emptyQuantity(q *resource.Quantity) bool {
   156  	return q == nil || q.IsZero()
   157  }
   158  
   159  func (r *ResourceDetails) IsEmpty() bool {
   160  	return r == nil || (emptyQuantity(r.CPU) && emptyQuantity(r.Memory) && emptyQuantity(r.Storage))
   161  }
   162  
   163  // GlobalObjectKeySelector is needed as we can not use v1.SecretKeySelector
   164  // because it is not cross namespace.
   165  type GlobalObjectKeySelector struct {
   166  	corev1.ObjectReference `json:",inline"`
   167  	Key                    string `json:"key,omitempty"`
   168  }
   169  
   170  type GlobalSecretKeySelector GlobalObjectKeySelector
   171  type GlobalConfigMapKeySelector GlobalObjectKeySelector
   172  
   173  // ProxySettings allow configuring a HTTP proxy for the control planes and nodes.
   174  type ProxySettings struct {
   175  	// Optional: If set, this proxy will be configured for both HTTP and HTTPS.
   176  	HTTPProxy *string `json:"httpProxy,omitempty"`
   177  	// Optional: If set this will be set as NO_PROXY environment variable on the node;
   178  	// The value must be a comma-separated list of domains for which no proxy
   179  	// should be used, e.g. "*.example.com,internal.dev".
   180  	// Note that the in-cluster apiserver URL will be automatically prepended
   181  	// to this value.
   182  	NoProxy *string `json:"noProxy,omitempty"`
   183  }
   184  
   185  func emptyStrPtr(s *string) bool {
   186  	return s == nil || *s == ""
   187  }
   188  
   189  // Empty returns true if p or all of its children are nil or empty strings.
   190  func (p *ProxySettings) Empty() bool {
   191  	return p == nil || (emptyStrPtr(p.HTTPProxy) && emptyStrPtr(p.NoProxy))
   192  }
   193  
   194  // Merge applies the settings from p into dst if the corresponding setting
   195  // in dst is nil or an empty string.
   196  func (p *ProxySettings) Merge(dst *ProxySettings) {
   197  	if emptyStrPtr(dst.HTTPProxy) {
   198  		dst.HTTPProxy = p.HTTPProxy
   199  	}
   200  	if emptyStrPtr(dst.NoProxy) {
   201  		dst.NoProxy = p.NoProxy
   202  	}
   203  }
   204  
   205  // ClusterReference is a struct that allows referencing a single Cluster object.
   206  type ClusterReference struct {
   207  	// Name of the Cluster object.
   208  	Name string `json:"name"`
   209  }