diff --git a/features/features.go b/features/features.go index af1ae8f4e3b..e34c011db1f 100644 --- a/features/features.go +++ b/features/features.go @@ -753,8 +753,8 @@ var ( mustRegister() FeatureGateAWSDedicatedHosts = newFeatureGate("AWSDedicatedHosts"). - reportProblemsToJiraComponent("Installer"). - contactPerson("faermanj"). + reportProblemsToJiraComponent("splat"). + contactPerson("rvanderp3"). productScope(ocpSpecific). enhancementPR("https://github.com/openshift/enhancements/pull/1781"). enableIn(configv1.DevPreviewNoUpgrade, configv1.TechPreviewNoUpgrade). diff --git a/machine/v1beta1/types_awsprovider.go b/machine/v1beta1/types_awsprovider.go index b3b38bc6cc1..263a718f601 100644 --- a/machine/v1beta1/types_awsprovider.go +++ b/machine/v1beta1/types_awsprovider.go @@ -114,6 +114,15 @@ type AWSMachineProviderConfig struct { // If this value is selected, capacityReservationID must be specified to identify the target reservation. // +optional MarketType MarketType `json:"marketType,omitempty"` + + // dedicatedHost configures placement on AWS Dedicated Hosts. + // When omitted, the instance is not constrained to a dedicated host. + // If hostAffinity is set to "Host", a host ID must be provided at dedicatedHost.host.hostID. + // If hostAffinity is set to "AnyAvailable", dedicatedHost.host must be omitted. + // If hostAffinity is omitted and host.hostID is set, the instance starts on that specific host. + // +openshift:enable:FeatureGate=AWSDedicatedHosts + // +optional + DedicatedHost *DedicatedHost `json:"dedicatedHost,omitempty"` } // AWSConfidentialComputePolicy represents the confidential compute configuration for the instance. @@ -393,3 +402,47 @@ const ( // When set to CapacityBlock the instance utilizes pre-purchased compute capacity (capacity blocks) with AWS Capacity Reservations. MarketTypeCapacityBlock MarketType = "CapacityBlock" ) + +type DedicatedHost struct { + // hostAffinity specifies the dedicated host affinity setting for the instance. + // When HostAffinity is set to Host, an instance started onto a specific host always restarts on the same host if stopped. + // When HostAffinity is set to AnyAvailable, and you stop and restart the instance, it can be restarted on any available host. + // When HostAffinity is defined, Host is required. + // The default value is AnyAvailable + // +kubebuilder:default=AnyAvailable + // +openshift:enable:FeatureGate=AWSDedicatedHosts + // +optional + HostAffinity HostAffinity `json:"hostAffinity,omitempty"` + + // host specifies a particular dedicated host when required by hostAffinity or when + // hostAffinity is omitted and you want to target a specific host. + // Must be omitted when hostAffinity is "AnyAvailable". + // +openshift:enable:FeatureGate=AWSDedicatedHosts + // +optional + Host Host `json:"host,omitzero"` +} + +// HostAffinity selects how an instance should be placed on AWS Dedicated Hosts. +// +kubebuilder:validation:Enum:=Host;AnyAvailable +type HostAffinity string + +const ( + // HostAffinityAnyAvailable lets the platform select any available dedicated host. + HostAffinityAnyAvailable HostAffinity = "AnyAvailable" + + // HostAffinityHost requires specifying a particular host via dedicatedHost.host.hostID. + HostAffinityHost HostAffinity = "Host" +) + +type Host struct { + // id identifies the AWS Dedicated Host on which the instance must run. + // The value must start with "h-" followed by 17 lowercase hexadecimal characters (0-9 and a-f). + // Minimum length is 19 characters. + // Maximum length is 19 characters. + // +kubebuilder:validation:XValidation:rule="self.matches('^h-[0-9a-f]{17}$')",message="hostID must start with 'h-' followed by 17 lowercase hexadecimal characters (0-9 and a-f)" + // +kubebuilder:validation:MinLength=19 + // +kubebuilder:validation:MaxLength=19 + // +openshift:enable:FeatureGate=AWSDedicatedHosts + // +required + HostID string `json:"id,omitempty"` +} diff --git a/machine/v1beta1/zz_generated.deepcopy.go b/machine/v1beta1/zz_generated.deepcopy.go index 5aa4f90a497..70d77c65013 100644 --- a/machine/v1beta1/zz_generated.deepcopy.go +++ b/machine/v1beta1/zz_generated.deepcopy.go @@ -85,6 +85,11 @@ func (in *AWSMachineProviderConfig) DeepCopyInto(out *AWSMachineProviderConfig) *out = new(int32) **out = **in } + if in.DedicatedHost != nil { + in, out := &in.DedicatedHost, &out.DedicatedHost + *out = new(DedicatedHost) + **out = **in + } return } @@ -509,6 +514,23 @@ func (in *DataDiskManagedDiskParameters) DeepCopy() *DataDiskManagedDiskParamete return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *DedicatedHost) DeepCopyInto(out *DedicatedHost) { + *out = *in + out.Host = in.Host + return +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new DedicatedHost. +func (in *DedicatedHost) DeepCopy() *DedicatedHost { + if in == nil { + return nil + } + out := new(DedicatedHost) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *DiskEncryptionSetParameters) DeepCopyInto(out *DiskEncryptionSetParameters) { *out = *in @@ -898,6 +920,22 @@ func (in *GCPShieldedInstanceConfig) DeepCopy() *GCPShieldedInstanceConfig { return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *Host) DeepCopyInto(out *Host) { + *out = *in + return +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new Host. +func (in *Host) DeepCopy() *Host { + if in == nil { + return nil + } + out := new(Host) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *Image) DeepCopyInto(out *Image) { *out = *in diff --git a/machine/v1beta1/zz_generated.swagger_doc_generated.go b/machine/v1beta1/zz_generated.swagger_doc_generated.go index 4a1b969a81e..f7792a1bc06 100644 --- a/machine/v1beta1/zz_generated.swagger_doc_generated.go +++ b/machine/v1beta1/zz_generated.swagger_doc_generated.go @@ -35,6 +35,7 @@ var map_AWSMachineProviderConfig = map[string]string{ "placementGroupPartition": "placementGroupPartition is the partition number within the placement group in which to launch the instance. This must be an integer value between 1 and 7. It is only valid if the placement group, referred in `PlacementGroupName` was created with strategy set to partition.", "capacityReservationId": "capacityReservationId specifies the target Capacity Reservation into which the instance should be launched. The field size should be greater than 0 and the field input must start with cr-***", "marketType": "marketType specifies the type of market for the EC2 instance. Valid values are OnDemand, Spot, CapacityBlock and omitted.\n\nDefaults to OnDemand. When SpotMarketOptions is provided, the marketType defaults to \"Spot\".\n\nWhen set to OnDemand the instance runs as a standard OnDemand instance. When set to Spot the instance runs as a Spot instance. When set to CapacityBlock the instance utilizes pre-purchased compute capacity (capacity blocks) with AWS Capacity Reservations. If this value is selected, capacityReservationID must be specified to identify the target reservation.", + "dedicatedHost": "dedicatedHost configures placement on AWS Dedicated Hosts. When omitted, the instance is not constrained to a dedicated host. If hostAffinity is set to \"Host\", a host ID must be provided at dedicatedHost.host.hostID. If hostAffinity is set to \"AnyAvailable\", dedicatedHost.host must be omitted. If hostAffinity is omitted and host.hostID is set, the instance starts on that specific host.", } func (AWSMachineProviderConfig) SwaggerDoc() map[string]string { @@ -92,6 +93,15 @@ func (CPUOptions) SwaggerDoc() map[string]string { return map_CPUOptions } +var map_DedicatedHost = map[string]string{ + "hostAffinity": "hostAffinity selects how the instance is placed on a dedicated host. Valid values are \"AnyAvailable\", \"Host\", and omitted. - AnyAvailable: the platform selects any available dedicated host; do not set host. - Host: the instance must run on a specific host; set host.hostID. - omitted: if host.hostID is set, the instance runs on that specific host; otherwise no host constraint is applied. When hostAffinity is set, host.hostID is required for \"Host\" and must be omitted for \"AnyAvailable\".", + "host": "host specifies a particular dedicated host when required by hostAffinity or when hostAffinity is omitted and you want to target a specific host. Must be omitted when hostAffinity is \"AnyAvailable\".", +} + +func (DedicatedHost) SwaggerDoc() map[string]string { + return map_DedicatedHost +} + var map_EBSBlockDeviceSpec = map[string]string{ "": "EBSBlockDeviceSpec describes a block device for an EBS volume. https://docs.aws.amazon.com/goto/WebAPI/ec2-2016-11-15/EbsBlockDevice", "deleteOnTermination": "Indicates whether the EBS volume is deleted on machine termination.\n\nDeprecated: setting this field has no effect.", @@ -116,6 +126,14 @@ func (Filter) SwaggerDoc() map[string]string { return map_Filter } +var map_Host = map[string]string{ + "hostID": "hostID identifies the AWS Dedicated Host on which the instance must run. Use this when hostAffinity is \"Host\" or when hostAffinity is omitted and you want a specific host. The value must start with \"h-\" followed by 17 lowercase hexadecimal characters (0-9 and a-f). Maximum length is 19 characters.", +} + +func (Host) SwaggerDoc() map[string]string { + return map_Host +} + var map_LoadBalancerReference = map[string]string{ "": "LoadBalancerReference is a reference to a load balancer on AWS.", } diff --git a/openapi/generated_openapi/zz_generated.openapi.go b/openapi/generated_openapi/zz_generated.openapi.go index 57338175cf8..ca201d3a6a0 100644 --- a/openapi/generated_openapi/zz_generated.openapi.go +++ b/openapi/generated_openapi/zz_generated.openapi.go @@ -794,6 +794,7 @@ func GetOpenAPIDefinitions(ref common.ReferenceCallback) map[string]common.OpenA "github.com/openshift/api/machine/v1beta1.ConfidentialVM": schema_openshift_api_machine_v1beta1_ConfidentialVM(ref), "github.com/openshift/api/machine/v1beta1.DataDisk": schema_openshift_api_machine_v1beta1_DataDisk(ref), "github.com/openshift/api/machine/v1beta1.DataDiskManagedDiskParameters": schema_openshift_api_machine_v1beta1_DataDiskManagedDiskParameters(ref), + "github.com/openshift/api/machine/v1beta1.DedicatedHost": schema_openshift_api_machine_v1beta1_DedicatedHost(ref), "github.com/openshift/api/machine/v1beta1.DiskEncryptionSetParameters": schema_openshift_api_machine_v1beta1_DiskEncryptionSetParameters(ref), "github.com/openshift/api/machine/v1beta1.DiskSettings": schema_openshift_api_machine_v1beta1_DiskSettings(ref), "github.com/openshift/api/machine/v1beta1.EBSBlockDeviceSpec": schema_openshift_api_machine_v1beta1_EBSBlockDeviceSpec(ref), @@ -808,6 +809,7 @@ func GetOpenAPIDefinitions(ref common.ReferenceCallback) map[string]common.OpenA "github.com/openshift/api/machine/v1beta1.GCPNetworkInterface": schema_openshift_api_machine_v1beta1_GCPNetworkInterface(ref), "github.com/openshift/api/machine/v1beta1.GCPServiceAccount": schema_openshift_api_machine_v1beta1_GCPServiceAccount(ref), "github.com/openshift/api/machine/v1beta1.GCPShieldedInstanceConfig": schema_openshift_api_machine_v1beta1_GCPShieldedInstanceConfig(ref), + "github.com/openshift/api/machine/v1beta1.Host": schema_openshift_api_machine_v1beta1_Host(ref), "github.com/openshift/api/machine/v1beta1.Image": schema_openshift_api_machine_v1beta1_Image(ref), "github.com/openshift/api/machine/v1beta1.LastOperation": schema_openshift_api_machine_v1beta1_LastOperation(ref), "github.com/openshift/api/machine/v1beta1.LifecycleHook": schema_openshift_api_machine_v1beta1_LifecycleHook(ref), @@ -39459,12 +39461,18 @@ func schema_openshift_api_machine_v1beta1_AWSMachineProviderConfig(ref common.Re Format: "", }, }, + "dedicatedHost": { + SchemaProps: spec.SchemaProps{ + Description: "dedicatedHost configures placement on AWS Dedicated Hosts. When omitted, the instance is not constrained to a dedicated host. If hostAffinity is set to \"Host\", a host ID must be provided at dedicatedHost.host.hostID. If hostAffinity is set to \"AnyAvailable\", dedicatedHost.host must be omitted. If hostAffinity is omitted and host.hostID is set, the instance starts on that specific host.", + Ref: ref("github.com/openshift/api/machine/v1beta1.DedicatedHost"), + }, + }, }, Required: []string{"ami", "instanceType", "deviceIndex", "subnet", "placement"}, }, }, Dependencies: []string{ - "github.com/openshift/api/machine/v1beta1.AWSResourceReference", "github.com/openshift/api/machine/v1beta1.BlockDeviceMappingSpec", "github.com/openshift/api/machine/v1beta1.CPUOptions", "github.com/openshift/api/machine/v1beta1.LoadBalancerReference", "github.com/openshift/api/machine/v1beta1.MetadataServiceOptions", "github.com/openshift/api/machine/v1beta1.Placement", "github.com/openshift/api/machine/v1beta1.SpotMarketOptions", "github.com/openshift/api/machine/v1beta1.TagSpecification", "k8s.io/api/core/v1.LocalObjectReference", "k8s.io/apimachinery/pkg/apis/meta/v1.ObjectMeta"}, + "github.com/openshift/api/machine/v1beta1.AWSResourceReference", "github.com/openshift/api/machine/v1beta1.BlockDeviceMappingSpec", "github.com/openshift/api/machine/v1beta1.CPUOptions", "github.com/openshift/api/machine/v1beta1.DedicatedHost", "github.com/openshift/api/machine/v1beta1.LoadBalancerReference", "github.com/openshift/api/machine/v1beta1.MetadataServiceOptions", "github.com/openshift/api/machine/v1beta1.Placement", "github.com/openshift/api/machine/v1beta1.SpotMarketOptions", "github.com/openshift/api/machine/v1beta1.TagSpecification", "k8s.io/api/core/v1.LocalObjectReference", "k8s.io/apimachinery/pkg/apis/meta/v1.ObjectMeta"}, } } @@ -40309,6 +40317,34 @@ func schema_openshift_api_machine_v1beta1_DataDiskManagedDiskParameters(ref comm } } +func schema_openshift_api_machine_v1beta1_DedicatedHost(ref common.ReferenceCallback) common.OpenAPIDefinition { + return common.OpenAPIDefinition{ + Schema: spec.Schema{ + SchemaProps: spec.SchemaProps{ + Type: []string{"object"}, + Properties: map[string]spec.Schema{ + "hostAffinity": { + SchemaProps: spec.SchemaProps{ + Description: "hostAffinity specifies the dedicated host affinity setting for the instance. When HostAffinity is set to Host, an instance started onto a specific host always restarts on the same host if stopped. When HostAffinity is set to AnyAvailable, and you stop and restart the instance, it can be restarted on any available host. When HostAffinity is defined, Host is required. The default value is AnyAvailable", + Type: []string{"string"}, + Format: "", + }, + }, + "host": { + SchemaProps: spec.SchemaProps{ + Description: "host specifies a particular dedicated host when required by hostAffinity or when hostAffinity is omitted and you want to target a specific host. Must be omitted when hostAffinity is \"AnyAvailable\".", + Default: map[string]interface{}{}, + Ref: ref("github.com/openshift/api/machine/v1beta1.Host"), + }, + }, + }, + }, + }, + Dependencies: []string{ + "github.com/openshift/api/machine/v1beta1.Host"}, + } +} + func schema_openshift_api_machine_v1beta1_DiskEncryptionSetParameters(ref common.ReferenceCallback) common.OpenAPIDefinition { return common.OpenAPIDefinition{ Schema: spec.Schema{ @@ -41102,6 +41138,26 @@ func schema_openshift_api_machine_v1beta1_GCPShieldedInstanceConfig(ref common.R } } +func schema_openshift_api_machine_v1beta1_Host(ref common.ReferenceCallback) common.OpenAPIDefinition { + return common.OpenAPIDefinition{ + Schema: spec.Schema{ + SchemaProps: spec.SchemaProps{ + Type: []string{"object"}, + Properties: map[string]spec.Schema{ + "id": { + SchemaProps: spec.SchemaProps{ + Description: "id identifies the AWS Dedicated Host on which the instance must run. The value must start with \"h-\" followed by 17 lowercase hexadecimal characters (0-9 and a-f). Minimum length is 19 characters. Maximum length is 19 characters.", + Type: []string{"string"}, + Format: "", + }, + }, + }, + Required: []string{"id"}, + }, + }, + } +} + func schema_openshift_api_machine_v1beta1_Image(ref common.ReferenceCallback) common.OpenAPIDefinition { return common.OpenAPIDefinition{ Schema: spec.Schema{ diff --git a/openapi/openapi.json b/openapi/openapi.json index a2af11a3e71..0d7464dd70c 100644 --- a/openapi/openapi.json +++ b/openapi/openapi.json @@ -22649,6 +22649,10 @@ "description": "credentialsSecret is a reference to the secret with AWS credentials. Otherwise, defaults to permissions provided by attached IAM role where the actuator is running.", "$ref": "#/definitions/io.k8s.api.core.v1.LocalObjectReference" }, + "dedicatedHost": { + "description": "dedicatedHost configures placement on AWS Dedicated Hosts. When omitted, the instance is not constrained to a dedicated host. If hostAffinity is set to \"Host\", a host ID must be provided at dedicatedHost.host.hostID. If hostAffinity is set to \"AnyAvailable\", dedicatedHost.host must be omitted. If hostAffinity is omitted and host.hostID is set, the instance starts on that specific host.", + "$ref": "#/definitions/com.github.openshift.api.machine.v1beta1.DedicatedHost" + }, "deviceIndex": { "description": "deviceIndex is the index of the device on the instance for the network interface attachment. Defaults to 0.", "type": "integer", @@ -23242,6 +23246,20 @@ } } }, + "com.github.openshift.api.machine.v1beta1.DedicatedHost": { + "type": "object", + "properties": { + "host": { + "description": "host specifies a particular dedicated host when required by hostAffinity or when hostAffinity is omitted and you want to target a specific host. Must be omitted when hostAffinity is \"AnyAvailable\".", + "default": {}, + "$ref": "#/definitions/com.github.openshift.api.machine.v1beta1.Host" + }, + "hostAffinity": { + "description": "hostAffinity specifies the dedicated host affinity setting for the instance. When HostAffinity is set to Host, an instance started onto a specific host always restarts on the same host if stopped. When HostAffinity is set to AnyAvailable, and you stop and restart the instance, it can be restarted on any available host. When HostAffinity is defined, Host is required. The default value is AnyAvailable", + "type": "string" + } + } + }, "com.github.openshift.api.machine.v1beta1.DiskEncryptionSetParameters": { "description": "DiskEncryptionSetParameters is the disk encryption set properties", "type": "object", @@ -23712,6 +23730,18 @@ } } }, + "com.github.openshift.api.machine.v1beta1.Host": { + "type": "object", + "required": [ + "id" + ], + "properties": { + "id": { + "description": "id identifies the AWS Dedicated Host on which the instance must run. The value must start with \"h-\" followed by 17 lowercase hexadecimal characters (0-9 and a-f). Minimum length is 19 characters. Maximum length is 19 characters.", + "type": "string" + } + } + }, "com.github.openshift.api.machine.v1beta1.Image": { "description": "Image is a mirror of azure sdk compute.ImageReference", "type": "object",