diff --git a/api/v1alpha1/constants.go b/api/v1alpha1/constants.go index 796f1c07..e26f4246 100644 --- a/api/v1alpha1/constants.go +++ b/api/v1alpha1/constants.go @@ -24,6 +24,9 @@ const ( OperationAnnotationForceUpdateOrDeleteInProgress = "ForceUpdateOrDeleteInProgress" // OperationAnnotationForceUpdateInProgress allows update of a resource even if it is in progress. OperationAnnotationForceUpdateInProgress = "ForceUpdateInProgress" + + // SkipBootConfiguration skips the boot configuration if set to this value. + SkipBootConfiguration = "skip-boot-configuration-enforement" // OperationAnnotationForceReset forces a reset before next operation OperationAnnotationForceReset = "ForceReset" ) diff --git a/api/v1alpha1/server_types.go b/api/v1alpha1/server_types.go index 4f06d88a..ddf13c5f 100644 --- a/api/v1alpha1/server_types.go +++ b/api/v1alpha1/server_types.go @@ -130,6 +130,7 @@ type ServerSpec struct { MaintenanceBootConfigurationRef *v1.ObjectReference `json:"maintenanceBootConfigurationRef,omitempty"` // BootOrder specifies the boot order of the server. + // Deprecated: currently not supported. // +optional BootOrder []BootOrder `json:"bootOrder,omitempty"` diff --git a/api/v1alpha1/servermaintenance_types.go b/api/v1alpha1/servermaintenance_types.go index 06b05d91..df094062 100644 --- a/api/v1alpha1/servermaintenance_types.go +++ b/api/v1alpha1/servermaintenance_types.go @@ -23,11 +23,33 @@ type ServerBootConfigurationTemplate struct { // +required Name string `json:"name"` + // BootType specifies the type of boot configuration. + // It can be either "OneOff" or "Persistent". If not specified, it defaults to "Persistent". + // "Persistent" will set the configuration reboot the server before setting the server to the desired power state mentioned in spec. + // + // "OneOff" will set the configuration to boot once. next boot-up will boot into default boot order. + // if power state mentioned in spec is "PowerOn", server will be powered on and will boot into the configuration. + // if power state is "PowerOff", server will be powered off and will boot into the configuration on next power on. + // + // +kubebuilder:validation:Enum=OneOff;Persistent + // +optional + // +kubebuilder:default=Persistent + BootType BootType `json:"bootType,omitempty"` + // Parameters specify the parameters to be used for rendering the boot configuration. // +required Spec ServerBootConfigurationSpec `json:"spec"` } +type BootType string + +const ( + // BootTypeOneOff indicates that the server should boot into this configuration one time. + BootTypeOneOff BootType = "OneOff" + // BootTypePersistent indicates that the server should boot into this configuration continuously. + BootTypePersistent BootType = "Persistent" +) + // ServerMaintenanceSpec defines the desired state of a ServerMaintenance type ServerMaintenanceSpec struct { // Policy specifies the maintenance policy to be enforced on the server. @@ -61,8 +83,46 @@ const ( type ServerMaintenanceStatus struct { // State specifies the current state of the server maintenance. State ServerMaintenanceState `json:"state,omitempty"` + + // BootOrderStatus specifies the boot order of the server before maintenance. + // is used to store the boot order of server before it is changed for maintenance. + // used only with BootType Persistent. + // +optional + BootOrderStatus *ServerMaintenanceBootOrder `json:"bootOrderStatus,omitempty"` +} + +type ServerMaintenanceBootOrder struct { + // DefaultBootOrder specifies the default boot order of the server before maintenance. + // +optional + DefaultBootOrder []string `json:"defaultBootOrder,omitempty"` + + State ServerMaintenanceBootOrderState `json:"state,omitempty"` } +// ServerMaintenanceState specifies the current state of the server maintenance. +type ServerMaintenanceBootOrderState string + +const ( + + // BootOrderConfigNoOp specifies that the server bootOrder is as expected. + BootOrderConfigNoOp ServerMaintenanceBootOrderState = "NoOp" + + // BootOrderConfigInProgress specifies that the server bootOrder configuration is InProgress. + BootOrderConfigInProgress ServerMaintenanceBootOrderState = "InProgress" + + // BootOrderConfigSuccess specifies that the server bootOrder configuration is Completed. + BootOrderConfigSuccess ServerMaintenanceBootOrderState = "Completed" + + // BootOrderConfigSuccessRevertInProgress specifies that the server bootOrder revert to default is InProgress. + BootOrderConfigSuccessRevertInProgress ServerMaintenanceBootOrderState = "RevertInProgress" + + // BootOrderConfigRevertSuccess specifies that the server bootOrder configuration is Completed. + BootOrderConfigRevertSuccess ServerMaintenanceBootOrderState = "RevertCompleted" + + // BootOrderOneOffPxeBootSuccess specifies that the server bootOrder configuration is set to boot pxe once. + BootOrderOneOffPxeBootSuccess ServerMaintenanceBootOrderState = "PxeOneOffBootSuccess" +) + // ServerMaintenanceState specifies the current state of the server maintenance. type ServerMaintenanceState string @@ -71,6 +131,8 @@ const ( ServerMaintenanceStatePending ServerMaintenanceState = "Pending" // ServerMaintenanceStateInMaintenance specifies that the server is in maintenance. ServerMaintenanceStateInMaintenance ServerMaintenanceState = "InMaintenance" + // ServerMaintenanceStatePreparing specifies that the server is in maintenance. + ServerMaintenanceStatePreparing ServerMaintenanceState = "Preparing" // ServerMaintenanceStateFailed specifies that the server maintenance has failed. ServerMaintenanceStateFailed ServerMaintenanceState = "Failed" ) diff --git a/api/v1alpha1/zz_generated.deepcopy.go b/api/v1alpha1/zz_generated.deepcopy.go index cd44503e..09d61e41 100644 --- a/api/v1alpha1/zz_generated.deepcopy.go +++ b/api/v1alpha1/zz_generated.deepcopy.go @@ -1535,7 +1535,7 @@ func (in *ServerMaintenance) DeepCopyInto(out *ServerMaintenance) { out.TypeMeta = in.TypeMeta in.ObjectMeta.DeepCopyInto(&out.ObjectMeta) in.Spec.DeepCopyInto(&out.Spec) - out.Status = in.Status + in.Status.DeepCopyInto(&out.Status) } // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ServerMaintenance. @@ -1556,6 +1556,26 @@ func (in *ServerMaintenance) DeepCopyObject() runtime.Object { return nil } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *ServerMaintenanceBootOrder) DeepCopyInto(out *ServerMaintenanceBootOrder) { + *out = *in + if in.DefaultBootOrder != nil { + in, out := &in.DefaultBootOrder, &out.DefaultBootOrder + *out = make([]string, len(*in)) + copy(*out, *in) + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ServerMaintenanceBootOrder. +func (in *ServerMaintenanceBootOrder) DeepCopy() *ServerMaintenanceBootOrder { + if in == nil { + return nil + } + out := new(ServerMaintenanceBootOrder) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *ServerMaintenanceList) DeepCopyInto(out *ServerMaintenanceList) { *out = *in @@ -1636,6 +1656,11 @@ func (in *ServerMaintenanceSpec) DeepCopy() *ServerMaintenanceSpec { // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *ServerMaintenanceStatus) DeepCopyInto(out *ServerMaintenanceStatus) { *out = *in + if in.BootOrderStatus != nil { + in, out := &in.BootOrderStatus, &out.BootOrderStatus + *out = new(ServerMaintenanceBootOrder) + (*in).DeepCopyInto(*out) + } } // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ServerMaintenanceStatus. diff --git a/bmc/bmc.go b/bmc/bmc.go index e7bd1cd0..b602d036 100644 --- a/bmc/bmc.go +++ b/bmc/bmc.go @@ -68,6 +68,9 @@ type BMC interface { // GetBootOrder retrieves the boot order for the system. GetBootOrder(ctx context.Context, systemURI string) ([]string, error) + // GetBootOptions retrieves the boot options for the system. + GetBootOptions(ctx context.Context, systemURI string) ([]*redfish.BootOption, error) + // GetBiosAttributeValues retrieves BIOS attribute values for the system. GetBiosAttributeValues(ctx context.Context, systemURI string, attributes []string) (redfish.SettingsAttributes, error) @@ -99,7 +102,7 @@ type BMC interface { GetBMCVersion(ctx context.Context, UUID string) (string, error) // SetBootOrder sets the boot order for the system. - SetBootOrder(ctx context.Context, systemURI string, order []string) error + SetBootOrder(ctx context.Context, systemURI string, order redfish.Boot) error // GetStorages retrieves storage information for the system. GetStorages(ctx context.Context, systemURI string) ([]Storage, error) diff --git a/bmc/redfish.go b/bmc/redfish.go index 37699ec6..ac8ecb25 100644 --- a/bmc/redfish.go +++ b/bmc/redfish.go @@ -320,6 +320,14 @@ func (r *RedfishBMC) GetBootOrder(ctx context.Context, systemURI string) ([]stri return system.Boot.BootOrder, nil } +func (r *RedfishBMC) GetBootOptions(ctx context.Context, systemURI string) ([]*redfish.BootOption, error) { + system, err := r.getSystemFromUri(ctx, systemURI) + if err != nil { + return nil, err + } + return system.BootOptions() +} + func (r *RedfishBMC) GetBiosVersion(ctx context.Context, systemURI string) (string, error) { system, err := r.getSystemFromUri(ctx, systemURI) if err != nil { @@ -474,21 +482,30 @@ func (r *RedfishBMC) SetBMCAttributesImmediately(ctx context.Context, bmcUUID st } // SetBootOrder sets bios boot order -func (r *RedfishBMC) SetBootOrder(ctx context.Context, systemURI string, bootOrder []string) error { +func (r *RedfishBMC) SetBootOrder(ctx context.Context, systemURI string, bootOrder redfish.Boot) error { system, err := r.getSystemFromUri(ctx, systemURI) if err != nil { return err } - return system.SetBoot( - redfish.Boot{ - BootSourceOverrideEnabled: redfish.ContinuousBootSourceOverrideEnabled, - BootSourceOverrideTarget: redfish.NoneBootSourceOverrideTarget, - BootOrder: bootOrder, - }, - ) + var tSystem struct { + Settings common.Settings `json:"@Redfish.Settings"` + } + // Unfortunately, some vendors (like Dell) support setting through different url. + // Hence we need to set it through this url. + err = json.Unmarshal(system.RawData, &tSystem) + if err != nil { + return err + } + if tSystem.Settings.SettingsObject.String() == "" { + return system.SetBoot(bootOrder) + } + return system.SetBoot(bootOrder) } -func (r *RedfishBMC) getFilteredBiosRegistryAttributes(readOnly bool, immutable bool) (map[string]RegistryEntryAttributes, error) { +func (r *RedfishBMC) getFilteredBiosRegistryAttributes( + readOnly bool, + immutable bool, +) (map[string]RegistryEntryAttributes, error) { registries, err := r.client.Service.Registries() if err != nil { return nil, err diff --git a/cmd/manager/main.go b/cmd/manager/main.go index 0dfba887..70ccdf31 100644 --- a/cmd/manager/main.go +++ b/cmd/manager/main.go @@ -366,6 +366,15 @@ func main() { // nolint: gocyclo if err = (&controller.ServerMaintenanceReconciler{ Client: mgr.GetClient(), Scheme: mgr.GetScheme(), + BMCOptions: bmc.Options{ + BasicAuth: true, + PowerPollingInterval: powerPollingInterval, + PowerPollingTimeout: powerPollingTimeout, + ResourcePollingInterval: resourcePollingInterval, + ResourcePollingTimeout: resourcePollingTimeout, + }, + Insecure: insecure, + ResyncInterval: serverResyncInterval, }).SetupWithManager(mgr); err != nil { setupLog.Error(err, "unable to create controller", "controller", "ServerMaintenance") os.Exit(1) diff --git a/config/crd/bases/metal.ironcore.dev_servermaintenances.yaml b/config/crd/bases/metal.ironcore.dev_servermaintenances.yaml index 730c1943..33051382 100644 --- a/config/crd/bases/metal.ironcore.dev_servermaintenances.yaml +++ b/config/crd/bases/metal.ironcore.dev_servermaintenances.yaml @@ -66,6 +66,20 @@ spec: description: ServerBootConfigurationTemplate specifies the boot configuration to be applied to the server during maintenance. properties: + bootType: + default: Persistent + description: |- + BootType specifies the type of boot configuration. + It can be either "OneOff" or "Persistent". If not specified, it defaults to "Persistent". + "Persistent" will set the configuration reboot the server before setting the server to the desired power state mentioned in spec. + + "OneOff" will set the configuration to boot once. next boot-up will boot into default boot order. + if power state mentioned in spec is "PowerOn", server will be powered on and will boot into the configuration. + if power state is "PowerOff", server will be powered off and will boot into the configuration on next power on. + enum: + - OneOff + - Persistent + type: string name: description: Name specifies the name of the boot configuration. type: string @@ -141,6 +155,23 @@ spec: status: description: ServerMaintenanceStatus defines the observed state of a ServerMaintenance properties: + bootOrderStatus: + description: |- + BootOrderStatus specifies the boot order of the server before maintenance. + is used to store the boot order of server before it is changed for maintenance. + used only with BootType Persistent. + properties: + defaultBootOrder: + description: DefaultBootOrder specifies the default boot order + of the server before maintenance. + items: + type: string + type: array + state: + description: ServerMaintenanceState specifies the current state + of the server maintenance. + type: string + type: object state: description: State specifies the current state of the server maintenance. type: string diff --git a/config/crd/bases/metal.ironcore.dev_servers.yaml b/config/crd/bases/metal.ironcore.dev_servers.yaml index dd699246..5bb78870 100644 --- a/config/crd/bases/metal.ironcore.dev_servers.yaml +++ b/config/crd/bases/metal.ironcore.dev_servers.yaml @@ -200,7 +200,9 @@ spec: type: object x-kubernetes-map-type: atomic bootOrder: - description: BootOrder specifies the boot order of the server. + description: |- + BootOrder specifies the boot order of the server. + Deprecated: currently not supported. items: description: BootOrder represents the boot order of the server. properties: diff --git a/config/samples/metal_v1alpha1_servermaintenance.yaml b/config/samples/metal_v1alpha1_servermaintenance.yaml index 5e440cc1..f19a3b12 100644 --- a/config/samples/metal_v1alpha1_servermaintenance.yaml +++ b/config/samples/metal_v1alpha1_servermaintenance.yaml @@ -5,5 +5,17 @@ metadata: app.kubernetes.io/name: metal-operator app.kubernetes.io/managed-by: kustomize name: servermaintenance-sample + namespace: default spec: - # TODO(user): Add fields here + serverRef: + name: node005-ap046-system-0 + policy: metalv1alpha1.ServerMaintenancePolicyEnforced + serverPower: metalv1alpha1.PowerOn + serverBootConfigurationTemplate: + name: "test-boot" + spec: + ignitionSecretRef: + name: ignition-secret + serverRef: + name: server-system-0 + image: "ghcr.io//foo/linux:C.X" diff --git a/dist/chart/templates/crd/metal.ironcore.dev_servermaintenances.yaml b/dist/chart/templates/crd/metal.ironcore.dev_servermaintenances.yaml index fa0d9b8b..11766888 100755 --- a/dist/chart/templates/crd/metal.ironcore.dev_servermaintenances.yaml +++ b/dist/chart/templates/crd/metal.ironcore.dev_servermaintenances.yaml @@ -72,6 +72,20 @@ spec: description: ServerBootConfigurationTemplate specifies the boot configuration to be applied to the server during maintenance. properties: + bootType: + default: Persistent + description: |- + BootType specifies the type of boot configuration. + It can be either "OneOff" or "Persistent". If not specified, it defaults to "Persistent". + "Persistent" will set the configuration reboot the server before setting the server to the desired power state mentioned in spec. + + "OneOff" will set the configuration to boot once. next boot-up will boot into default boot order. + if power state mentioned in spec is "PowerOn", server will be powered on and will boot into the configuration. + if power state is "PowerOff", server will be powered off and will boot into the configuration on next power on. + enum: + - OneOff + - Persistent + type: string name: description: Name specifies the name of the boot configuration. type: string @@ -147,6 +161,23 @@ spec: status: description: ServerMaintenanceStatus defines the observed state of a ServerMaintenance properties: + bootOrderStatus: + description: |- + BootOrderStatus specifies the boot order of the server before maintenance. + is used to store the boot order of server before it is changed for maintenance. + used only with BootType Persistent. + properties: + defaultBootOrder: + description: DefaultBootOrder specifies the default boot order + of the server before maintenance. + items: + type: string + type: array + state: + description: ServerMaintenanceState specifies the current state + of the server maintenance. + type: string + type: object state: description: State specifies the current state of the server maintenance. type: string diff --git a/dist/chart/templates/crd/metal.ironcore.dev_servers.yaml b/dist/chart/templates/crd/metal.ironcore.dev_servers.yaml index 9e84b616..00d0cf46 100755 --- a/dist/chart/templates/crd/metal.ironcore.dev_servers.yaml +++ b/dist/chart/templates/crd/metal.ironcore.dev_servers.yaml @@ -206,7 +206,9 @@ spec: type: object x-kubernetes-map-type: atomic bootOrder: - description: BootOrder specifies the boot order of the server. + description: |- + BootOrder specifies the boot order of the server. + Deprecated: currently not supported. items: description: BootOrder represents the boot order of the server. properties: diff --git a/docs/api-reference/api.md b/docs/api-reference/api.md index ac1fe38b..1284f4dc 100644 --- a/docs/api-reference/api.md +++ b/docs/api-reference/api.md @@ -2628,6 +2628,28 @@ string +
string alias)+(Appears on:ServerBootConfigurationTemplate) +
+| Value | +Description | +
|---|---|
"OneOff" |
+BootTypeOneOff indicates that the server should boot into this configuration one time. + |
+
"Persistent" |
+BootTypePersistent indicates that the server should boot into this configuration continuously. + |
+
@@ -3554,7 +3576,8 @@ the boot configuration for this server during maintenance. This field is optiona
BootOrder specifies the boot order of the server.
+BootOrder specifies the boot order of the server. +Deprecated: currently not supported.
bootTypeBootType specifies the type of boot configuration. +It can be either “OneOff” or “Persistent”. If not specified, it defaults to “Persistent”. +“Persistent” will set the configuration reboot the server before setting the server to the desired power state mentioned in spec.
+“OneOff” will set the configuration to boot once. next boot-up will boot into default boot order. +if power state mentioned in spec is “PowerOn”, server will be powered on and will boot into the configuration. +if power state is “PowerOff”, server will be powered off and will boot into the configuration on next power on.
+spec+(Appears on:ServerMaintenanceStatus) +
+| Field | +Description | +
|---|---|
+defaultBootOrder+ +[]string + + |
+
+(Optional)
+ DefaultBootOrder specifies the default boot order of the server before maintenance. + |
+
+state+ + +ServerMaintenanceBootOrderState + + + |
++ | +
string alias)+(Appears on:ServerMaintenanceBootOrder) +
+ServerMaintenanceState specifies the current state of the server maintenance.
+| Value | +Description | +
|---|---|
"InProgress" |
+BootOrderConfigInProgress specifies that the server bootOrder configuration is InProgress. + |
+
"NoOp" |
+BootOrderConfigNoOp specifies that the server bootOrder is as expected. + |
+
"RevertCompleted" |
+BootOrderConfigRevertSuccess specifies that the server bootOrder configuration is Completed. + |
+
"Completed" |
+BootOrderConfigSuccess specifies that the server bootOrder configuration is Completed. + |
+
"RevertInProgress" |
+BootOrderConfigSuccessRevertInProgress specifies that the server bootOrder revert to default is InProgress. + |
+
"PxeOneOffBootSuccess" |
+BootOrderOneOffPxeBootSuccess specifies that the server bootOrder configuration is set to boot pxe once. + |
+
string alias)@@ -4400,6 +4518,9 @@ ServerBootConfigurationTemplate
"Pending"
ServerMaintenanceStatePending specifies that the server maintenance is pending.
"Preparing"
ServerMaintenanceStatePreparing specifies that the server is in maintenance.
+State specifies the current state of the server maintenance.
+bootOrderStatusBootOrderStatus specifies the boot order of the server before maintenance. +is used to store the boot order of server before it is changed for maintenance. +used only with BootType Persistent.
+BootOrder specifies the boot order of the server.
+BootOrder specifies the boot order of the server. +Deprecated: currently not supported.