Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

✨ Update API with ClusterClass MachinePool support #8820

Merged
merged 1 commit into from
Jul 13, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 13 additions & 0 deletions api/v1alpha4/conversion.go
Original file line number Diff line number Diff line change
Expand Up @@ -73,6 +73,8 @@ func (src *Cluster) ConvertTo(dstRaw conversion.Hub) error {
dst.Spec.Topology.Workers.MachineDeployments[i].Strategy = restored.Spec.Topology.Workers.MachineDeployments[i].Strategy
dst.Spec.Topology.Workers.MachineDeployments[i].MachineHealthCheck = restored.Spec.Topology.Workers.MachineDeployments[i].MachineHealthCheck
}

dst.Spec.Topology.Workers.MachinePools = restored.Spec.Topology.Workers.MachinePools
}
}

Expand Down Expand Up @@ -125,6 +127,7 @@ func (src *ClusterClass) ConvertTo(dstRaw conversion.Hub) error {
dst.Spec.ControlPlane.NodeDrainTimeout = restored.Spec.ControlPlane.NodeDrainTimeout
dst.Spec.ControlPlane.NodeVolumeDetachTimeout = restored.Spec.ControlPlane.NodeVolumeDetachTimeout
dst.Spec.ControlPlane.NodeDeletionTimeout = restored.Spec.ControlPlane.NodeDeletionTimeout
dst.Spec.Workers.MachinePools = restored.Spec.Workers.MachinePools

for i := range restored.Spec.Workers.MachineDeployments {
dst.Spec.Workers.MachineDeployments[i].MachineHealthCheck = restored.Spec.Workers.MachineDeployments[i].MachineHealthCheck
Expand Down Expand Up @@ -375,3 +378,13 @@ func Convert_v1beta1_ClusterClass_To_v1alpha4_ClusterClass(in *clusterv1.Cluster
// ClusterClass.Status has been added in v1beta1.
return autoConvert_v1beta1_ClusterClass_To_v1alpha4_ClusterClass(in, out, s)
}

func Convert_v1beta1_WorkersClass_To_v1alpha4_WorkersClass(in *clusterv1.WorkersClass, out *WorkersClass, s apiconversion.Scope) error {
// WorkersClass.MachinePools has been added in v1beta1.
return autoConvert_v1beta1_WorkersClass_To_v1alpha4_WorkersClass(in, out, s)
willie-yao marked this conversation as resolved.
Show resolved Hide resolved
}

func Convert_v1beta1_WorkersTopology_To_v1alpha4_WorkersTopology(in *clusterv1.WorkersTopology, out *WorkersTopology, s apiconversion.Scope) error {
// WorkersTopology.MachinePools has been added in v1beta1.
return autoConvert_v1beta1_WorkersTopology_To_v1alpha4_WorkersTopology(in, out, s)
}
32 changes: 12 additions & 20 deletions api/v1alpha4/zz_generated.conversion.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

71 changes: 71 additions & 0 deletions api/v1beta1/cluster_types.go
Original file line number Diff line number Diff line change
Expand Up @@ -147,6 +147,10 @@ type WorkersTopology struct {
// MachineDeployments is a list of machine deployments in the cluster.
// +optional
MachineDeployments []MachineDeploymentTopology `json:"machineDeployments,omitempty"`

// MachinePools is a list of machine pools in the cluster.
// +optional
MachinePools []MachinePoolTopology `json:"machinePools,omitempty"`
}

// MachineDeploymentTopology specifies the different parameters for a set of worker nodes in the topology.
Expand Down Expand Up @@ -238,6 +242,66 @@ type MachineHealthCheckTopology struct {
MachineHealthCheckClass `json:",inline"`
}

// MachinePoolTopology specifies the different parameters for a pool of worker nodes in the topology.
// This pool of nodes is managed by a MachinePool object whose lifecycle is managed by the Cluster controller.
type MachinePoolTopology struct {
// Metadata is the metadata applied to the MachinePool.
// At runtime this metadata is merged with the corresponding metadata from the ClusterClass.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Note for a follow-up, when this is merged/implemented we have to update the corresponding documentation in the book

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should we actually try to bundle the book related changes within this PR? Or at least have an issue open before we merge this?

Copy link
Member

@sbueringer sbueringer Jul 11, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We have an umbrella issue here #5991 (comment) including an update docs task. Are we looking for something specific?

// +optional
Metadata ObjectMeta `json:"metadata,omitempty"`

// Class is the name of the MachinePoolClass used to create the pool of worker nodes.
// This should match one of the deployment classes defined in the ClusterClass object
// mentioned in the `Cluster.Spec.Class` field.
Class string `json:"class"`

// Name is the unique identifier for this MachinePoolTopology.
// The value is used with other unique identifiers to create a MachinePool's Name
// (e.g. cluster's name, etc). In case the name is greater than the allowed maximum length,
// the values are hashed together.
Name string `json:"name"`

// FailureDomains is the list of failure domains the machine pool will be created in.
// Must match a key in the FailureDomains map stored on the cluster object.
// +optional
FailureDomains []string `json:"failureDomains,omitempty"`

// NodeDrainTimeout is the total amount of time that the controller will spend on draining a node.
// The default value is 0, meaning that the node can be drained without any time limitations.
// NOTE: NodeDrainTimeout is different from `kubectl drain --timeout`
// +optional
NodeDrainTimeout *metav1.Duration `json:"nodeDrainTimeout,omitempty"`

// NodeVolumeDetachTimeout is the total amount of time that the controller will spend on waiting for all volumes
// to be detached. The default value is 0, meaning that the volumes can be detached without any time limitations.
// +optional
NodeVolumeDetachTimeout *metav1.Duration `json:"nodeVolumeDetachTimeout,omitempty"`

// NodeDeletionTimeout defines how long the controller will attempt to delete the Node that the MachinePool
// hosts after the MachinePool is marked for deletion. A duration of 0 will retry deletion indefinitely.
// Defaults to 10 seconds.
// +optional
NodeDeletionTimeout *metav1.Duration `json:"nodeDeletionTimeout,omitempty"`

// Minimum number of seconds for which a newly created machine pool should
// be ready.
// Defaults to 0 (machine will be considered available as soon as it
// is ready)
// +optional
MinReadySeconds *int32 `json:"minReadySeconds,omitempty"`

// Replicas is the number of nodes belonging to this pool.
// If the value is nil, the MachinePool is created without the number of Replicas (defaulting to 1)
// and it's assumed that an external entity (like cluster autoscaler) is responsible for the management
// of this value.
// +optional
Replicas *int32 `json:"replicas,omitempty"`

sbueringer marked this conversation as resolved.
Show resolved Hide resolved
// Variables can be used to customize the MachinePool through patches.
sbueringer marked this conversation as resolved.
Show resolved Hide resolved
// +optional
Variables *MachinePoolVariables `json:"variables,omitempty"`
}

// ClusterVariable can be used to customize the Cluster through patches. Each ClusterVariable is associated with a
// Variable definition in the ClusterClass `status` variables.
type ClusterVariable struct {
Expand Down Expand Up @@ -268,6 +332,13 @@ type MachineDeploymentVariables struct {
Overrides []ClusterVariable `json:"overrides,omitempty"`
}

// MachinePoolVariables can be used to provide variables for a specific MachinePool.
type MachinePoolVariables struct {
// Overrides can be used to override Cluster level variables.
// +optional
Overrides []ClusterVariable `json:"overrides,omitempty"`
}

// ANCHOR_END: ClusterSpec

// ANCHOR: ClusterNetwork
Expand Down
81 changes: 81 additions & 0 deletions api/v1beta1/clusterclass_types.go
Original file line number Diff line number Diff line change
Expand Up @@ -133,6 +133,11 @@ type WorkersClass struct {
// a set of worker nodes.
// +optional
MachineDeployments []MachineDeploymentClass `json:"machineDeployments,omitempty"`

// MachinePools is a list of machine pool classes that can be used to create
// a set of worker nodes.
// +optional
MachinePools []MachinePoolClass `json:"machinePools,omitempty"`
}

// MachineDeploymentClass serves as a template to define a set of worker nodes of the cluster
Expand Down Expand Up @@ -244,6 +249,69 @@ type MachineHealthCheckClass struct {
RemediationTemplate *corev1.ObjectReference `json:"remediationTemplate,omitempty"`
}

// MachinePoolClass serves as a template to define a pool of worker nodes of the cluster
// provisioned using `ClusterClass`.
type MachinePoolClass struct {
// Class denotes a type of machine pool present in the cluster,
// this name MUST be unique within a ClusterClass and can be referenced
// in the Cluster to create a managed MachinePool.
Class string `json:"class"`

// Template is a local struct containing a collection of templates for creation of
// MachinePools objects representing a pool of worker nodes.
Template MachinePoolClassTemplate `json:"template"`

// FailureDomains is the list of failure domains the MachinePool should be attached to.
// Must match a key in the FailureDomains map stored on the cluster object.
// NOTE: This value can be overridden while defining a Cluster.Topology using this MachinePoolClass.
// +optional
FailureDomains []string `json:"failureDomains,omitempty"`

// NodeDrainTimeout is the total amount of time that the controller will spend on draining a node.
// The default value is 0, meaning that the node can be drained without any time limitations.
// NOTE: NodeDrainTimeout is different from `kubectl drain --timeout`
// NOTE: This value can be overridden while defining a Cluster.Topology using this MachinePoolClass.
// +optional
NodeDrainTimeout *metav1.Duration `json:"nodeDrainTimeout,omitempty"`

// NodeVolumeDetachTimeout is the total amount of time that the controller will spend on waiting for all volumes
// to be detached. The default value is 0, meaning that the volumes can be detached without any time limitations.
// NOTE: This value can be overridden while defining a Cluster.Topology using this MachinePoolClass.
// +optional
NodeVolumeDetachTimeout *metav1.Duration `json:"nodeVolumeDetachTimeout,omitempty"`

// NodeDeletionTimeout defines how long the controller will attempt to delete the Node that the Machine
// hosts after the Machine Pool is marked for deletion. A duration of 0 will retry deletion indefinitely.
// Defaults to 10 seconds.
// NOTE: This value can be overridden while defining a Cluster.Topology using this MachinePoolClass.
// +optional
NodeDeletionTimeout *metav1.Duration `json:"nodeDeletionTimeout,omitempty"`

// Minimum number of seconds for which a newly created machine pool should
// be ready.
// Defaults to 0 (machine will be considered available as soon as it
// is ready)
// NOTE: This value can be overridden while defining a Cluster.Topology using this MachinePoolClass.
MinReadySeconds *int32 `json:"minReadySeconds,omitempty"`
}

// MachinePoolClassTemplate defines how a MachinePool generated from a MachinePoolClass
// should look like.
type MachinePoolClassTemplate struct {
willie-yao marked this conversation as resolved.
Show resolved Hide resolved
// Metadata is the metadata applied to the MachinePool.
// At runtime this metadata is merged with the corresponding metadata from the topology.
// +optional
Metadata ObjectMeta `json:"metadata,omitempty"`

// Bootstrap contains the bootstrap template reference to be used
// for the creation of the Machines in the MachinePool.
Bootstrap LocalObjectTemplate `json:"bootstrap"`

// Infrastructure contains the infrastructure template reference to be used
// for the creation of the MachinePool.
Infrastructure LocalObjectTemplate `json:"infrastructure"`
}

// IsZero returns true if none of the values of MachineHealthCheckClass are defined.
func (m MachineHealthCheckClass) IsZero() bool {
return reflect.ValueOf(m).IsZero()
Expand Down Expand Up @@ -472,6 +540,11 @@ type PatchSelectorMatch struct {
// .spec.workers.machineDeployments.
// +optional
MachineDeploymentClass *PatchSelectorMatchMachineDeploymentClass `json:"machineDeploymentClass,omitempty"`

// MachinePoolClass selects templates referenced in specific MachinePoolClasses in
// .spec.workers.machinePools.
// +optional
MachinePoolClass *PatchSelectorMatchMachinePoolClass `json:"machinePoolClass,omitempty"`
}

// PatchSelectorMatchMachineDeploymentClass selects templates referenced
Expand All @@ -482,6 +555,14 @@ type PatchSelectorMatchMachineDeploymentClass struct {
Names []string `json:"names,omitempty"`
}

// PatchSelectorMatchMachinePoolClass selects templates referenced
// in specific MachinePoolClasses in .spec.workers.machinePools.
type PatchSelectorMatchMachinePoolClass struct {
// Names selects templates by class names.
// +optional
Names []string `json:"names,omitempty"`
}

// JSONPatch defines a JSON patch.
type JSONPatch struct {
// Op defines the operation of the patch.
Expand Down
4 changes: 4 additions & 0 deletions api/v1beta1/common_types.go
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,10 @@ const (
// a classy Cluster to define the maximum concurrency while upgrading MachineDeployments.
ClusterTopologyUpgradeConcurrencyAnnotation = "topology.cluster.x-k8s.io/upgrade-concurrency"

// ClusterTopologyMachinePoolNameLabel is the label set on the generated MachinePool objects
// to track the name of the MachinePool topology it represents.
ClusterTopologyMachinePoolNameLabel = "topology.cluster.x-k8s.io/pool-name"

// ClusterTopologyUnsafeUpdateClassNameAnnotation can be used to disable the webhook check on
// update that disallows a pre-existing Cluster to be populated with Topology information and Class.
ClusterTopologyUnsafeUpdateClassNameAnnotation = "unsafe.topology.cluster.x-k8s.io/disable-update-class-name-check"
Expand Down
Loading