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

🌱 ClusterClass: add ref and controlPlane name builtin variables #6215

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
Original file line number Diff line number Diff line change
Expand Up @@ -382,12 +382,18 @@ In addition to variables specified in the ClusterClass, the following builtin va
referenced in patches:
- `builtin.cluster.{name,namespace}`
- `builtin.cluster.topology.{version,class}`
- `builtin.controlPlane.{replicas,version}`
- `builtin.controlPlane.{replicas,version,name}`
- Please note, these variables are only available when patching control plane or control plane
machine templates.
- `builtin.controlPlane.machineTemplate.infrastructureRef.name`
- Please note, these variables are only available when using a control plane with machines and
when patching control plane or control plane machine templates.
- `builtin.machineDeployment.{replicas,version,class,name,topologyName}`
- Please note, these variables are only available when patching the templates of a MachineDeployment
and contain the values of the current `MachineDeployment` topology.
- `builtin.machineDeployment.{infrastructureRef.name,bootstrap.configRef.name}`
- Please note, these variables are only available when patching the templates of a MachineDeployment
and contain the values of the current `MachineDeployment` topology.

Builtin variables can be referenced just like regular variables, e.g.:
```yaml
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -649,11 +649,17 @@ Note: Builtin variables are defined in [Builtin variables](#builtin-variables) b
It’s also possible to use so-called builtin variables in addition to user-defined variables. The following builtin variables are available:
- `builtin.cluster.{name,namespace}`
- `builtin.cluster.topology.{version,class}`
- `builtin.controlPlane.{replicas,version}`
- `builtin.controlPlane.{replicas,version,name}`
- **Note**: these variables are only available when patching control plane or control plane machine templates.
- `builtin.controlPlane.machineTemplate.infrastructureRef.name`
- **Note**: these variables are only available when using a control plane with machines and
when patching control plane or control plane machine templates.
- `builtin.machineDeployment.{replicas,version,class,name,topologyName}`
- **Note**: these variables are only available when patching MachineDeployment templates and contain the values
of the current `MachineDeploymentTopology`.
- `builtin.machineDeployment.{infrastructureRef.name,bootstrap.configRef.name}`
- **Note**: these variables are only available when patching the templates of a MachineDeployment
and contain the values of the current `MachineDeployment` topology.

Builtin variables are available under the `builtin.` prefix. Some examples:
- Usage of `cluster.name` via variable:
Expand Down
4 changes: 2 additions & 2 deletions internal/controllers/topology/cluster/patches/engine.go
Original file line number Diff line number Diff line change
Expand Up @@ -138,7 +138,7 @@ func createRequest(blueprint *scope.ClusterBlueprint, desired *scope.ClusterStat
req.Items = append(req.Items, t)

// Calculate controlPlane variables.
controlPlaneVariables, err := variables.ControlPlane(&blueprint.Topology.ControlPlane, desired.ControlPlane.Object)
controlPlaneVariables, err := variables.ControlPlane(&blueprint.Topology.ControlPlane, desired.ControlPlane.Object, desired.ControlPlane.InfrastructureMachineTemplate)
if err != nil {
return nil, errors.Wrapf(err, "failed to calculate ControlPlane variables")
}
Expand Down Expand Up @@ -188,7 +188,7 @@ func createRequest(blueprint *scope.ClusterBlueprint, desired *scope.ClusterStat
}

// Calculate MachineDeployment variables.
mdVariables, err := variables.MachineDeployment(mdTopology, md.Object)
mdVariables, err := variables.MachineDeployment(mdTopology, md.Object, md.BootstrapTemplate, md.InfrastructureMachineTemplate)
if err != nil {
return nil, errors.Wrapf(err, "failed to calculate variables for %s", tlog.KObj{Obj: md.Object})
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -102,6 +102,14 @@ func TestGenerate(t *testing.T) {
Variable: pointer.String("builtin.controlPlane.replicas"),
},
},
// test .builtin.controlPlane.machineTemplate.InfrastructureRef.name var.
{
Op: "replace",
Path: "/spec/template/spec/files",
ValueFrom: &clusterv1.JSONPatchValue{
Template: pointer.String(`[{"contentFrom":{"secret":{"key":"control-plane-azure.json","name":"{{ .builtin.controlPlane.machineTemplate.infrastructureRef.name }}-azure-json"}}}]`),
},
},
},
},
},
Expand All @@ -121,7 +129,7 @@ func TestGenerate(t *testing.T) {
TemplateType: api.ControlPlaneTemplateType,
},
Variables: map[string]apiextensionsv1.JSON{
"builtin": {Raw: []byte(`{"controlPlane":{"replicas":3}}`)},
"builtin": {Raw: []byte(`{"controlPlane":{"replicas":3,"machineTemplate":{"infrastructureRef":{"name":"controlPlaneInfrastructureMachineTemplate1"}}}}`)},
"variableC": {Raw: []byte(`"C-template"`)},
},
},
Expand All @@ -141,8 +149,15 @@ func TestGenerate(t *testing.T) {
{"op":"replace","path":"/spec/valueFrom/template","value":"template bbbbb"},
{"op":"replace","path":"/spec/templatePrecedent","value":"C-template"},
{"op":"replace","path":"/spec/builtinClusterName","value":"cluster-name"},
{"op":"replace","path":"/spec/builtinControlPlaneReplicas","value":3}
]`),
{"op":"replace","path":"/spec/builtinControlPlaneReplicas","value":3},
{"op":"replace","path":"/spec/template/spec/files","value":[{
"contentFrom":{
"secret":{
"key":"control-plane-azure.json",
"name":"controlPlaneInfrastructureMachineTemplate1-azure-json"
}
}
}]}]`),
PatchType: api.JSONPatchType,
},
},
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -73,8 +73,28 @@ type ControlPlaneBuiltins struct {
// being orchestrated.
Version string `json:"version,omitempty"`

// Name is the name of the ControlPlane,
// to which the current template belongs to.
Name string `json:"name,omitempty"`

// Replicas is the value of the replicas field of the ControlPlane object.
Replicas *int64 `json:"replicas,omitempty"`

// MachineTemplate is the value of the .spec.machineTemplate field of the ControlPlane object.
MachineTemplate *ControlPlaneMachineTemplateBuiltins `json:"machineTemplate,omitempty"`
}

// ControlPlaneMachineTemplateBuiltins is the value of the .spec.machineTemplate field of the ControlPlane object.
type ControlPlaneMachineTemplateBuiltins struct {
// InfrastructureRef is the value of the infrastructureRef field of ControlPlane.spec.machineTemplate.
InfrastructureRef ControlPlaneMachineTemplateInfrastructureRefBuiltins `json:"infrastructureRef,omitempty"`
}

// ControlPlaneMachineTemplateInfrastructureRefBuiltins is the value of the infrastructureRef field of
// ControlPlane.spec.machineTemplate.
type ControlPlaneMachineTemplateInfrastructureRefBuiltins struct {
// Name of the infrastructureRef.
Name string `json:"name,omitempty"`
}

// MachineDeploymentBuiltins represents builtin MachineDeployment variables.
Expand Down Expand Up @@ -102,6 +122,33 @@ type MachineDeploymentBuiltins struct {
// Replicas is the value of the replicas field of the MachineDeployment,
// to which the current template belongs to.
Replicas *int64 `json:"replicas,omitempty"`

// Bootstrap is the value of the .spec.template.spec.bootstrap field of the MachineDeployment.
Bootstrap *MachineDeploymentBootstrapBuiltins `json:"bootstrap,omitempty"`

// InfrastructureRef is the value of the .spec.template.spec.bootstrap field of the MachineDeployment.
InfrastructureRef *MachineDeploymentInfrastructureRefBuiltins `json:"infrastructureRef,omitempty"`
}

// MachineDeploymentBootstrapBuiltins is the value of the .spec.template.spec.bootstrap field
// of the MachineDeployment.
type MachineDeploymentBootstrapBuiltins struct {
// ConfigRef is the value of the .spec.template.spec.bootstrap.configRef field of the MachineDeployment.
ConfigRef *MachineDeploymentBootstrapConfigRefBuiltins `json:"configRef,omitempty"`
}

// MachineDeploymentBootstrapConfigRefBuiltins is the value of the .spec.template.spec.bootstrap.configRef
// field of the MachineDeployment.
type MachineDeploymentBootstrapConfigRefBuiltins struct {
// Name of the bootstrap.configRef.
Name string `json:"name,omitempty"`
}

// MachineDeploymentInfrastructureRefBuiltins is the value of the .spec.template.spec.infrastructureRef field
// of the MachineDeployment.
type MachineDeploymentInfrastructureRefBuiltins struct {
// Name of the infrastructureRef.
Name string `json:"name,omitempty"`
}

// VariableMap is a name/value map of variables.
Expand Down Expand Up @@ -139,32 +186,42 @@ func Global(clusterTopology *clusterv1.Topology, cluster *clusterv1.Cluster) (Va
}

// ControlPlane returns variables that apply to templates belonging to the ControlPlane.
func ControlPlane(controlPlaneTopology *clusterv1.ControlPlaneTopology, controlPlane *unstructured.Unstructured) (VariableMap, error) {
func ControlPlane(cpTopology *clusterv1.ControlPlaneTopology, cp, cpInfrastructureMachineTemplate *unstructured.Unstructured) (VariableMap, error) {
variables := VariableMap{}

// Construct builtin variable.
builtin := Builtins{
ControlPlane: &ControlPlaneBuiltins{},
ControlPlane: &ControlPlaneBuiltins{
Name: cp.GetName(),
},
}

// If it is required to manage the number of replicas for the ControlPlane, set the corresponding variable.
// NOTE: If the Cluster.spec.topology.controlPlane.replicas field is nil, the topology reconciler won't set
// the replicas field on the ControlPlane. This happens either when the ControlPlane provider does
// not implement support for this field or the default value of the ControlPlane is used.
if controlPlaneTopology.Replicas != nil {
replicas, err := contract.ControlPlane().Replicas().Get(controlPlane)
if cpTopology.Replicas != nil {
replicas, err := contract.ControlPlane().Replicas().Get(cp)
if err != nil {
return nil, errors.Wrap(err, "failed to get spec.replicas from the ControlPlane")
}
builtin.ControlPlane.Replicas = replicas
}

version, err := contract.ControlPlane().Version().Get(controlPlane)
version, err := contract.ControlPlane().Version().Get(cp)
if err != nil {
return nil, errors.Wrap(err, "failed to get spec.version from the ControlPlane")
}
builtin.ControlPlane.Version = *version

if cpInfrastructureMachineTemplate != nil {
builtin.ControlPlane.MachineTemplate = &ControlPlaneMachineTemplateBuiltins{
InfrastructureRef: ControlPlaneMachineTemplateInfrastructureRefBuiltins{
Name: cpInfrastructureMachineTemplate.GetName(),
},
}
}

if err := setVariable(variables, BuiltinsName, builtin); err != nil {
return nil, err
}
Expand All @@ -173,7 +230,7 @@ func ControlPlane(controlPlaneTopology *clusterv1.ControlPlaneTopology, controlP
}

// MachineDeployment returns variables that apply to templates belonging to a MachineDeployment.
func MachineDeployment(mdTopology *clusterv1.MachineDeploymentTopology, md *clusterv1.MachineDeployment) (VariableMap, error) {
func MachineDeployment(mdTopology *clusterv1.MachineDeploymentTopology, md *clusterv1.MachineDeployment, mdBootstrapTemplate, mdInfrastructureMachineTemplate *unstructured.Unstructured) (VariableMap, error) {
variables := VariableMap{}

// Add variables overrides for the MachineDeployment.
Expand All @@ -196,6 +253,20 @@ func MachineDeployment(mdTopology *clusterv1.MachineDeploymentTopology, md *clus
builtin.MachineDeployment.Replicas = pointer.Int64(int64(*md.Spec.Replicas))
}

if mdBootstrapTemplate != nil {
builtin.MachineDeployment.Bootstrap = &MachineDeploymentBootstrapBuiltins{
ConfigRef: &MachineDeploymentBootstrapConfigRefBuiltins{
Name: mdBootstrapTemplate.GetName(),
},
}
}

if mdInfrastructureMachineTemplate != nil {
builtin.MachineDeployment.InfrastructureRef = &MachineDeploymentInfrastructureRefBuiltins{
Name: mdInfrastructureMachineTemplate.GetName(),
}
}

if err := setVariable(variables, BuiltinsName, builtin); err != nil {
return nil, err
}
Expand Down
Loading